-
Notifications
You must be signed in to change notification settings - Fork 1
/
dllmain.cpp
2883 lines (2641 loc) · 98.7 KB
/
dllmain.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
// NFS Most Wanted - Xenon Effects implementation
// A port of the XenonEffect particle effect emitters from NFS Carbon
// by Xan/Tenjoin
// BUG LIST:
// - particles stay in the world after restart - MAKE A XENON EFFECT RESET
// - contrails get overwritten by sparks at high rates
// - texture filtering messes with drawing coordinates - if it's disabled, sparks are rendered off screen...
//
#include "stdafx.h"
#include "stdio.h"
#include "includes\injector\injector.hpp"
#include "includes\mINI\src\mini\ini.h"
#include <d3d9.h>
#pragma comment(lib, "d3d9.lib")
#include <d3dx9.h>
#include <cmath>
#include <vector>
using namespace std;
#pragma runtime_checks( "", off )
// uncomment to enable contrail test near the SkipFE start location in MW's map (next to car lot in College/Rosewood)
//#define CONTRAIL_TEST
bool bContrails = true;
bool bLimitContrailRate = true;
bool bLimitSparkRate = true;
bool bNISContrails = false;
bool bUseCGStyle = false;
bool bPassShadowMap = false;
bool bUseD3DDeviceTexture = false;
float ContrailTargetFPS = 30.0f;
float SparkTargetFPS = 60.0f;
float ContrailSpeed = 44.0f;
float ContrailMinIntensity = 0.1f;
float ContrailMaxIntensity = 0.75f;
float SparkIntensity = 1.0f;
char TPKfilename[128] = { "GLOBAL\\XenonEffects.tpk" };
uint32_t MaxParticles = 10000;
uint32_t NGEffectListSize = 500;
uint32_t ContrailFrameDelay = 1;
uint32_t SparkFrameDelay = 1;
#define GLOBAL_D3DDEVICE 0x00982BDC
#define GAMEFLOWSTATUS_ADDR 0x00925E90
#define FASTMEM_ADDR 0x00925B30
#define NISINSTANCE_ADDR 0x009885C8
#define WORLDPRELITSHADER_OBJ_ADDR 0x0093DEBC
#define CURRENTSHADER_OBJ_ADDR 0x00982C80
#define FRAMECOUNTER_ADDR 0x00982B78
#define eFrameCounter *(uint32_t*)FRAMECOUNTER_ADDR
struct bVector3
{
float x;
float y;
float z;
};
struct bVector4
{
float x;
float y;
float z;
float w;
};
struct bMatrix4
{
bVector4 v0;
bVector4 v1;
bVector4 v2;
bVector4 v3;
};
void*(__thiscall* FastMem_Alloc)(void* FastMem, unsigned int bytes, char* kind) = (void*(__thiscall*)(void*, unsigned int, char*))0x005D29D0;
void* (__thiscall* FastMem_Free)(void* FastMem, void* ptr, unsigned int bytes, char* kind) = (void* (__thiscall*)(void*, void*, unsigned int, char*))0x005D0370;
void (__stdcall* __CxxThrowException)(int arg1, int arg2) = (void (__stdcall*)(int, int))0x007C56B0;
void* (__thiscall* Attrib_Instance_MW)(void* Attrib, void* AttribCollection, unsigned int unk, void* ucomlist) = (void* (__thiscall*)(void*, void*, unsigned int, void*))0x00452380;
void*(__cdecl* Attrib_DefaultDataArea)(unsigned int size) = (void*(__cdecl*)(unsigned int))0x006269B0;
void* (__thiscall* Attrib_Instance_Get)(void* AttribCollection, unsigned int unk, unsigned int hash) = (void* (__thiscall*)(void*, unsigned int, unsigned int))0x004546C0;
void* (__thiscall* Attrib_Attribute_GetLength)(void* AttribCollection) = (void* (__thiscall*)(void*))0x00452D40;
void* (__thiscall* Attrib_Dtor)(void* AttribCollection) = (void* (__thiscall*)(void*))0x00452BD0;
void* (__thiscall* Attrib_Instance_GetAttributePointer)(void* AttribCollection, unsigned int hash, unsigned int unk) = (void* (__thiscall*)(void*, unsigned int, unsigned int))0x00454810;
void* (__thiscall* Attrib_RefSpec_GetCollection)(void* Attrib) = (void* (__thiscall*)(void*))0x004560D0;
void* (__thiscall* Attrib_Instance_Dtor)(void* AttribInstance) = (void* (__thiscall*)(void*))0x0045A430;
void* (__thiscall* Attrib_Instance_Refspec)(void* AttribCollection, void* refspec, unsigned int unk, void* ucomlist) = (void* (__thiscall*)(void*, void*, unsigned int, void*))0x00456CB0;
void* (__cdecl* Attrib_FindCollection)(uint32_t param1, uint32_t param2) = (void* (__cdecl*)(uint32_t, uint32_t))0x00455FD0;
float (__cdecl* bRandom_Float_Int)(float range, int unk) = (float (__cdecl*)(float, int))0x0045D9E0;
int(__cdecl* bRandom_Int_Int)(int range, uint32_t* unk) = (int(__cdecl*)(int, uint32_t*))0x0045D9A0;
unsigned int(__cdecl* bStringHash)(char* str) = (unsigned int(__cdecl*)(char*))0x00460BF0;
void*(__cdecl* GetTextureInfo)(unsigned int name_hash, int return_default_texture_if_not_found, int include_unloaded_textures) = (void*(__cdecl*)(unsigned int, int, int))0x00503400;
void (__thiscall* EmitterSystem_UpdateParticles)(void* EmitterSystem, float dt) = (void (__thiscall*)(void*, float))0x00508C30;
void(__thiscall* EmitterSystem_Render)(void* EmitterSystem, void* eView) = (void(__thiscall*)(void*, void*))0x00503D00;
void(__stdcall* sub_7286D0)() = (void(__stdcall*)())0x007286D0;
void* (__cdecl* FastMem_CoreAlloc)(uint32_t size, char* debug_line) = (void* (__cdecl*)(uint32_t, char*))0x00465A70;
void(__stdcall* sub_739600)() = (void(__stdcall*)())0x739600;
void(__thiscall* CarRenderConn_UpdateEngineAnimation)(void* CarRenderConn, float param1, void* PktCarService) = (void(__thiscall*)(void*, float, void*))0x00745F20;
void(__stdcall* sub_6CFCE0)() = (void(__stdcall*)())0x6CFCE0;
void(__cdecl* ParticleSetTransform)(D3DXMATRIX* worldmatrix, uint32_t EVIEW_ID) = (void(__cdecl*)(D3DXMATRIX*, uint32_t))0x6C8000;
bool(__thiscall* WCollisionMgr_CheckHitWorld)(void* WCollisionMgr, bMatrix4* inputSeg, void* cInfo, uint32_t primMask) = (bool(__thiscall*)(void*, bMatrix4*, void*, uint32_t))0x007854B0;
void(__cdecl* GameSetTexture)(void* TextureInfo, uint32_t unk) = (void(__cdecl*)(void*, uint32_t))0x006C68B0;
void* (*CreateResourceFile)(char* filename, int ResFileType, int unk1, int unk2, int unk3) = (void* (*)(char*, int, int, int, int))0x0065FD30;
void(__thiscall* ResourceFile_BeginLoading)(void* ResourceFile, void* callback, void* unk) = (void(__thiscall*)(void*, void*, void*))0x006616F0;
void(*ServiceResourceLoading)() = (void(*)())0x006626B0;
uint32_t(__stdcall* sub_6DFAF0)() = (uint32_t(__stdcall*)())0x6DFAF0;
uint32_t(* Attrib_StringHash32)(const char* k) = (uint32_t(*)(const char*))0x004519D0;
void __stdcall LoadResourceFile(char* filename, int ResType, int unk1, void* unk2, void* unk3, int unk4, int unk5)
{
ResourceFile_BeginLoading(CreateResourceFile(filename, ResType, unk1, unk4, unk5), unk2, unk3);
}
// bridge the difference between MW and Carbon
void* __stdcall Attrib_Instance(void* collection, uint32_t msgPort)
{
uint32_t that;
_asm mov that, ecx
auto result = Attrib_Instance_MW((void*)that, collection, msgPort, NULL);
return result;
}
// function maps from Carbon to MW
unsigned int __ftol2 = 0x007C4B80;
unsigned int sub_6016B0 = 0x5C5E80;
unsigned int sub_404A20 = 0x004048C0;
unsigned int rsqrt = 0x00410220;
unsigned int sub_478200 = 0x466520;
unsigned int sub_6012B0 = 0x4FA510;
char gNGEffectList[64];
struct NGParticle
{
struct bVector3 initialPos;
unsigned int color;
struct bVector3 vel;
float gravity;
struct bVector3 impactNormal;
float remainingLife;
float life;
float age;
unsigned char elasticity;
unsigned char pad[3];
unsigned char flags;
unsigned char rotX;
unsigned char rotY;
unsigned char rotZ;
unsigned char size;
unsigned char startX;
unsigned char startY;
unsigned char startZ;
unsigned char uv[4];
};
//struct ParticleList
//{
// NGParticle mParticles[MAX_PARTICLES];
// unsigned int mNumParticles;
//}gParticleList;
NGParticle* gParticleList;
uint32_t NumParticles = 0;
//#define numParticles dword ptr gParticleList[PARTICLELIST_SIZE]
float flt_9C92F0 = 255.0f;
float flt_9C2478 = 1.0f;
float flt_9EA540 = 42.0f;
float flt_9C2C44 = 100.0f;
float flt_9C77C8 = 0.0039215689f;
float flt_9EAFFC = 0.00048828125f;
float flt_9C248C = 0.0f;
float flt_A6C230 = 0.15000001f;
float flt_9C2A3C = 4.0f;
float flt_9C2888 = 0.5f;
unsigned int randomSeed = 0xDEADBEEF;
const char* TextureName = "MAIN";
float EmitterDeltaTime = 0.0f;
LPDIRECT3DDEVICE9 g_D3DDevice;
struct fuelcell_emitter_mw
{
bVector4 VolumeCenter;
bVector4 VelocityDelta;
bVector4 VolumeExtent;
bVector4 VelocityInherit;
bVector4 VelocityStart;
bVector4 Colour1;
uint32_t emitteruv_class;
uint32_t emitteruv_collection;
uint32_t unk;
float life;
float NumParticlesVariance;
float GravityStart;
float HeightStart;
float GravityDelta;
float LengthStart;
float LengthDelta;
float LifeVariance;
float NumParticles;
uint16_t Spin;
uint8_t unk_0xD8782949;
uint8_t zContrail;
};
struct fuelcell_emitter_carbon
{
bVector4 VolumeCenter;
bVector4 VelocityDelta;
bVector4 VolumeExtent;
bVector4 VelocityInherit;
bVector4 VelocityStart;
bVector4 Colour1;
uint32_t emitteruv_class;
uint32_t emitteruv_collection;
uint32_t unk;
float life;
float NumParticlesVariance;
float GravityStart;
float HeightStart;
float GravityDelta;
float Elasticity;
float LengthStart;
float LengthDelta;
float LifeVariance;
float NumParticles;
uint8_t zDebrisType;
uint8_t zContrail;
}bridge_instance;
struct ElasticityPair
{
uint32_t emmitter_key;
float Elasticity;
};
vector<ElasticityPair> elasticityValues;
float GetElasticityValue(uint32_t key)
{
for (int i = 0; i < elasticityValues.size(); i++)
{
if (elasticityValues.at(i).emmitter_key == key)
return elasticityValues.at(i).Elasticity;
}
return 0.0f;
}
char NGSpriteManager_ClassData[128];
uint32_t NGSpriteManager[32] = { (uint32_t)(&NGSpriteManager_ClassData), 0};
float GetTargetFrametime()
{
return **(float**)0x6612EC;
}
uint32_t bridge_oldaddr = 0;
uint32_t bridge_instance_addr = 0;
void __stdcall fuelcell_emitter_bridge()
{
uint32_t that;
_asm mov that, ecx
bridge_instance_addr = that;
uint32_t instance_pointer = *(uint32_t*)(that + 4);
uint32_t key = *(uint32_t*)((*(uint32_t*)(that)) + 0x20);
fuelcell_emitter_mw* mw_emitter = (fuelcell_emitter_mw*)instance_pointer;
memset(&bridge_instance, 0, sizeof(fuelcell_emitter_carbon));
// copy the matching data first (first 0x80 bytes)
memcpy(&bridge_instance, mw_emitter, 0x80);
// adapt
bridge_instance.LengthStart = mw_emitter->LengthStart;
bridge_instance.LengthDelta = mw_emitter->LengthDelta;
bridge_instance.LifeVariance = mw_emitter->LifeVariance;
bridge_instance.NumParticles = mw_emitter->NumParticles;
bridge_instance.zContrail = mw_emitter->zContrail;
bridge_instance.Elasticity = GetElasticityValue(key);
//printf("key: 0x%X Elasticity: %.2f\n", key, bridge_instance.Elasticity);
// no idea if this is right
//bridge_instance.zDebrisType = (*mw_emitter).unk_0xD8782949;
// save & write back the pointer
bridge_oldaddr = instance_pointer;
*(uint32_t*)(that + 4) = (uint32_t)&bridge_instance;
}
void __stdcall fuelcell_emitter_bridge_restore()
{
*(uint32_t*)(bridge_instance_addr + 4) = bridge_oldaddr;
}
void* FastMem_CoreAlloc_Wrapper(uint32_t size)
{
return FastMem_CoreAlloc(size, 0);
}
void __declspec(naked) sub_736EA0()
{
_asm
{
sub esp, 10h
push esi
push 0FE40E637h
lea eax, [esp + 8]
push eax
call Attrib_Instance_Get ; Attrib::Instance::Get(const(ulong))
mov ecx, eax
call Attrib_Attribute_GetLength ; Attrib::Attribute::GetLength(const(void))
pop esi
add esp, 10h
retn
}
}
// EASTL List stuff Start
void __declspec(naked) eastl_vector_uninitialized_copy_impl_XenonEffectDef()
{
_asm
{
mov eax, [esp+8]
mov edx, [esp+10h]
push ebx
mov ebx, [esp+10h]
cmp eax, ebx
jz short loc_74C80E
push esi
push edi
loc_74C7F3: ; CODE XREF: eastl::uninitialized_copy_impl<eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>>(eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::integral_constant<bool,0>)+2A↓j
test edx, edx
jz short loc_74C802
mov ecx, 17h
mov esi, eax
mov edi, edx
rep movsd
loc_74C802: ; CODE XREF: eastl::uninitialized_copy_impl<eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>>(eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::integral_constant<bool,0>)+15↑j
add eax, 5Ch ; '\'
add edx, 5Ch ; '\'
cmp eax, ebx
jnz short loc_74C7F3
pop edi
pop esi
loc_74C80E: ; CODE XREF: eastl::uninitialized_copy_impl<eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>>(eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::integral_constant<bool,0>)+F↑j
mov eax, [esp+8]
mov [eax], edx
pop ebx
retn
}
}
void __declspec(naked) eastl_vector_erase_XenonEffectDef()
{
_asm
{
push ecx
push ebx
mov ebx, [ecx+4]
push ebp
mov ebp, [esp+14h]
cmp ebp, ebx
push esi
mov esi, [esp+14h]
mov [esp+0Ch], ecx
mov edx, esi
mov eax, ebp
jz short loc_752BFE
push edi
lea esp, [esp+0]
loc_752BE0: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::erase(XenonEffectDef *,XenonEffectDef *)+33↓j
mov esi, eax
mov edi, edx
add eax, 5Ch ; '\'
mov ecx, 17h
add edx, 5Ch ; '\'
cmp eax, ebx
rep movsd
jnz short loc_752BE0
mov ecx, [esp+10h]
mov esi, [esp+18h]
pop edi
loc_752BFE: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::erase(XenonEffectDef *,XenonEffectDef *)+19↑j
sub ebp, esi
mov eax, 4DE9BD37h
imul ebp
sub edx, ebp
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
mov edx, [ecx+4]
imul eax, 5Ch ; '\'
add edx, eax
mov eax, esi
pop esi
pop ebp
mov [ecx+4], edx
pop ebx
pop ecx
retn 8
}
}
void __declspec(naked) eastl_vector_DoInsertValue_XenonEffectDef()
{
_asm
{
sub esp, 8
push ebx
push ebp
push esi
mov ebx, ecx
mov eax, [ebx+8]
push edi
mov edi, [ebx+4]
cmp edi, eax
jz short loc_752CAB
mov eax, [esp+20h]
mov ebp, [esp+1Ch]
cmp eax, ebp
mov [esp+20h], eax
jb short loc_752C5E
cmp eax, edi
jnb short loc_752C5E
add eax, 5Ch ; '\'
mov [esp+20h], eax
loc_752C5E: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+21↑j
; eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+25↑j
test edi, edi
jz short loc_752C6C
lea esi, [edi-5Ch]
mov ecx, 17h
rep movsd
loc_752C6C: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+30↑j
mov edx, [ebx+4]
lea eax, [edx-5Ch]
cmp eax, ebp
jz short loc_752C8B
loc_752C76: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+59↓j
sub eax, 5Ch ; '\'
sub edx, 5Ch ; '\'
cmp eax, ebp
mov ecx, 17h
mov esi, eax
mov edi, edx
rep movsd
jnz short loc_752C76
loc_752C8B: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+44↑j
mov esi, [esp+20h]
mov edi, ebp
mov ecx, 17h
rep movsd
mov eax, [ebx+4]
pop edi
pop esi
add eax, 5Ch ; '\'
pop ebp
mov [ebx+4], eax
pop ebx
add esp, 8
retn 8
; ---------------------------------------------------------------------------
loc_752CAB: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+11↑j
sub edi, [ebx]
mov eax, 0B21642C9h
imul edi
add edx, edi
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
jz short loc_752CE9
lea edi, [eax+eax]
test edi, edi
mov [esp+14h], edi
jz short loc_752CF7
loc_752CCD: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+C5↓j
mov eax, edi
imul eax, 5Ch ; '\'
test eax, eax
jz short loc_752CF7
push 0
push eax
mov ecx, FASTMEM_ADDR
call FastMem_Alloc ; FastMem::Alloc((uint,char const *))
mov [esp+10h], eax
jmp short loc_752CFF
; ---------------------------------------------------------------------------
loc_752CE9: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+90↑j
mov dword ptr [esp+14h], 1
mov edi, [esp+14h]
jmp short loc_752CCD
; ---------------------------------------------------------------------------
loc_752CF7: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+9B↑j
; eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+A4↑j
mov dword ptr [esp+10h], 0
loc_752CFF: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+B7↑j
mov ecx, [esp+1Ch]
mov edx, [esp+10h]
mov ebp, [esp+1Ch]
mov eax, [ebx]
push ecx
push edx
push ebp
push eax
lea eax, [esp+2Ch]
push eax
call eastl_vector_uninitialized_copy_impl_XenonEffectDef
mov eax, [esp+30h]
add esp, 14h
test eax, eax
jz short loc_752D37
mov esi, [esp+20h]
mov ecx, 17h
mov edi, eax
rep movsd
mov edi, [esp+14h]
loc_752D37: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+F4↑j
mov edx, [esp+1Ch]
mov ecx, [ebx+4]
push edx
add eax, 5Ch ; '\'
push eax
push ecx
lea eax, [esp+28h]
push ebp
push eax
call eastl_vector_uninitialized_copy_impl_XenonEffectDef
mov esi, [ebx]
add esp, 14h
test esi, esi
jz short loc_752D81
mov ecx, [ebx+8]
sub ecx, esi
mov eax, 0B21642C9h
imul ecx
add edx, ecx
sar edx, 6
mov ecx, edx
shr ecx, 1Fh
add ecx, edx
imul ecx, 5Ch ; '\'
push 0
push ecx
push esi
mov ecx, FASTMEM_ADDR
call FastMem_Free ; FastMem::Free((void *,uint,char const *))
loc_752D81: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)+126↑j
mov eax, [esp+10h]
imul edi, 5Ch ; '\'
mov edx, [esp+1Ch]
add edi, eax
mov [ebx+8], edi
pop edi
pop esi
pop ebp
mov [ebx], eax
mov [ebx+4], edx
pop ebx
add esp, 8
retn 8
}
}
void __declspec(naked) eastl_vector_reserve_XenonEffectDef()
{
_asm
{
push ebx
mov ebx, [esp+8]
push ebp
push esi
mov esi, ecx
mov ebp, [esi]
mov ecx, [esi+8]
sub ecx, ebp
mov eax, 0B21642C9h
imul ecx
add edx, ecx
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
cmp ebx, eax
jbe loc_752858
test ebx, ebx
mov ecx, [esi+4]
push edi
mov [esp+14h], ecx
jz short loc_7527E1
mov eax, ebx
imul eax, 5Ch ; '\'
test eax, eax
jz short loc_7527E1
push 0
push eax
mov ecx, FASTMEM_ADDR
call FastMem_Alloc ; FastMem::Alloc((uint,char const *))
mov edi, eax
jmp short loc_7527E3
; ---------------------------------------------------------------------------
loc_7527E1: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::reserve(uint)+35↑j
; eastl::vector<XenonEffectDef,bstl::allocator>::reserve(uint)+3E↑j
xor edi, edi
loc_7527E3: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::reserve(uint)+4F↑j
mov edx, [esp+14h]
mov eax, [esp+14h]
push edx
push edi
push eax
lea ecx, [esp+20h]
push ebp
push ecx
call eastl_vector_uninitialized_copy_impl_XenonEffectDef ; eastl::uninitialized_copy_impl<eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>>(eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::generic_iterator<XenonEffectDef *,void>,eastl::integral_constant<bool,0>)
mov ebp, [esi]
add esp, 14h
test ebp, ebp
jz short loc_75282B
mov ecx, [esi+8]
sub ecx, ebp
mov eax, 0B21642C9h
imul ecx
add edx, ecx
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
imul eax, 5Ch ; '\'
push 0
push eax
push ebp
mov ecx, FASTMEM_ADDR
call FastMem_Free ; FastMem::Free((void *,uint,char const *))
loc_75282B: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::reserve(uint)+70↑j
mov edx, [esi]
imul ebx, 5Ch ; '\'
mov ecx, [esi+4]
sub ecx, edx
mov eax, 0B21642C9h
imul ecx
add edx, ecx
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
imul eax, 5Ch ; '\'
add eax, edi
add ebx, edi
mov [esi], edi
mov [esi+4], eax
mov [esi+8], ebx
pop edi
loc_752858: ; CODE XREF: eastl::vector<XenonEffectDef,bstl::allocator>::reserve(uint)+25↑j
pop esi
pop ebp
pop ebx
retn 4
}
}
void(__thiscall* eastl_vector_reserve_XenonEffectDef_Abstract)(void* vector, uint32_t n) = (void(__thiscall*)(void*, uint32_t))&eastl_vector_reserve_XenonEffectDef;
void(__thiscall* eastl_vector_erase_XenonEffectDef_Abstract)(void* vector, void* first, void* last) = (void(__thiscall*)(void*, void*, void*))&eastl_vector_erase_XenonEffectDef;
void __stdcall XenonEffectList_Initialize()
{
eastl_vector_reserve_XenonEffectDef_Abstract(&gNGEffectList, NGEffectListSize);
//eastl_vector_erase_XenonEffectDef_Abstract(&gNGEffectList, gNGEffectList, (void*)((uint32_t)(gNGEffectList + 4)));
}
// EASTL List stuff End
// note: unk_9D7880 == unk_8A3028
void __declspec(naked) AddXenonEffect() // (AcidEffect *piggyback_fx, Attrib::Collection *spec, UMath::Matrix4 *mat, UMath::Vector4 *vel, float intensity)
{
_asm
{
sub esp, 5Ch
push ebx
mov ebx, dword ptr gNGEffectList[0]
push edi
mov edi, dword ptr gNGEffectList[4]
mov ecx, ebx
sub ecx, edi
mov eax, 0B21642C9h
imul ecx
add edx, ecx
sar edx, 6
mov eax, edx
shr eax, 1Fh
add eax, edx
cmp eax, NGEffectListSize; 'd'
jnb loc_754DA5
push esi
mov ecx, 10h
mov esi, 0x8A3028
lea edi, [esp+20h]
rep movsd
mov ecx, [esp+74h]
add ecx, 30h ; '0'
mov edx, [ecx]
mov eax, [ecx+4]
mov [esp+50h], edx
mov edx, [ecx+8]
mov [esp+54h], eax
mov eax, [ecx+0Ch]
mov ecx, [esp+70h]
mov [esp+58h], edx
mov edx, [esp+78h]
mov [esp+5Ch], eax
mov eax, [edx]
mov [esp+60h], ecx
mov ecx, [edx+4]
mov [esp+10h], eax
mov eax, [edx+8]
mov [esp+18h], eax
mov eax, [esp+6Ch]
mov [esp+14h], ecx
mov ecx, [edx+0Ch]
mov edx, [esp+7Ch]
mov [esp+64h], eax
cmp ebx, dword ptr gNGEffectList[8]
mov [esp+1Ch], ecx
mov [esp+0Ch], edx
jnb loc_754D94
mov edi, ebx
add ebx, 5Ch ; '\'
test edi, edi
mov dword ptr gNGEffectList[4], ebx
jz loc_754DA4
mov ecx, 17h
lea esi, [esp+0Ch]
rep movsd
pop esi
pop edi
pop ebx
add esp, 5Ch
retn
; ---------------------------------------------------------------------------
loc_754D94: ; CODE XREF: AddXenonEffect(AcidEffect *,Attrib::Collection const *,UMath::Matrix4 const *,UMath::Vector4 const *,float)+A1↑j
lea ecx, [esp+0Ch]
push ecx
push ebx
mov ecx, offset gNGEffectList
call eastl_vector_DoInsertValue_XenonEffectDef ; eastl::vector<XenonEffectDef,bstl::allocator>::DoInsertValue(XenonEffectDef *,XenonEffectDef const &)
loc_754DA4: ; CODE XREF: AddXenonEffect(AcidEffect *,Attrib::Collection const *,UMath::Matrix4 const *,UMath::Vector4 const *,float)+B0↑j
pop esi
loc_754DA5: ; CODE XREF: AddXenonEffect(AcidEffect *,Attrib::Collection const *,UMath::Matrix4 const *,UMath::Vector4 const *,float)+2B↑j
pop edi
pop ebx
add esp, 5Ch
retn
}
}
void(__cdecl* AddXenonEffect_Abstract)(void* piggyback_fx, void* spec, bMatrix4* mat, bVector4* vel, float intensity) = (void(__cdecl*)(void*, void*, bMatrix4*, bVector4*, float)) & AddXenonEffect;
void __declspec(naked) CalcCollisiontime()
{
_asm
{
sub esp, 9Ch
fld flt_A6C230
push esi
mov esi, [esp + 0A4h]
fadd dword ptr[esi + 8]
mov eax, [esi + 30h]
mov[esp + 4], eax
mov ecx, [esi]
fst dword ptr[esi + 8]
mov edx, ecx
fld dword ptr[esp + 4]
mov[esp + 24h], ecx
fmul dword ptr[esi + 10h]
mov dword ptr[esp + 18h], 3F800000h
mov[esp + 14h], edx
mov[esp + 30h], edx
fadd dword ptr[esi]
fld dword ptr[esp + 4]
fmul dword ptr[esi + 14h]
fadd dword ptr[esi + 4]
fstp dword ptr[esp + 20h]
fld dword ptr[esi + 30h]
fld dword ptr[esp + 4]
fmul dword ptr[esi + 18h]
fadd st, st(3)
fld st(1)
fmul st, st(2)
fmul dword ptr[esi + 1Ch]
faddp st(1), st
fstp st(1)
fld dword ptr[esp + 20h]
fchs
fld dword ptr[esi + 4]
fchs
fstp dword ptr[esp + 0Ch]
mov eax, [esp + 0Ch]
fxch st(3)
mov[esp + 28h], eax
mov eax, [esp + 18h]
fstp dword ptr[esp + 10h]
mov ecx, [esp + 10h]
fxch st(2)
fstp dword ptr[esp + 0Ch]
mov[esp + 2Ch], ecx
mov ecx, [esp + 0Ch]
fxch st(1)
fstp dword ptr[esp + 10h]
mov edx, [esp + 10h]
mov[esp + 38h], ecx
mov dword ptr[esp + 18h], 3F800000h
fstp dword ptr[esp + 14h]
mov ecx, [esp + 18h]
mov[esp + 34h], eax
mov eax, [esp + 14h]
mov[esp + 44h], ecx
lea ecx, [esp + 48h]
mov[esp + 3Ch], edx
mov[esp + 40h], eax
call sub_404A20
fld flt_A6C230
fadd dword ptr[esp + 2Ch]
push 3
lea edx, [esp + 4Ch]
push edx
lea eax, [esp + 30h]
fstp dword ptr[esp + 34h]
push eax
lea ecx, [esp + 28h]
mov dword ptr[esp + 28h], 0
mov dword ptr[esp + 2Ch], 3
call WCollisionMgr_CheckHitWorld
test eax, eax
jz loc_73F30F
mov ecx, [esi + 18h]
mov[esp + 4], ecx
fld dword ptr[esp + 4]
fmul dword ptr[esp + 4]
fld dword ptr[esi + 8]
fsub dword ptr[esp + 4Ch]
fmul dword ptr[esi + 1Ch]
fmul ds : flt_9C2A3C
fsubp st(1), st
fst dword ptr[esp + 8]
fcomp ds : flt_9C248C
fnstsw ax
test ah, 41h
jp loc_73F2AA
fld ds : flt_9C248C
jmp loc_73F2ED
; -------------------------------------------------------------------------- -
loc_73F2AA:; CODE XREF : CalcCollisiontime + 140↑j
mov edx, [esp + 8]
push edx; float
call sub_6016B0
fstp dword ptr[esp + 0Ch]
fld dword ptr[esi + 1Ch]
add esp, 4
fadd st, st
fstp dword ptr[esp + 1Ch]
fld dword ptr[esp + 8]
fsub dword ptr[esp + 4]
fdiv dword ptr[esp + 1Ch]
fcom ds : flt_9C248C
fnstsw ax
test ah, 5
jp loc_73F2ED
fstp st
fld dword ptr[esp + 4]
fchs
fsub dword ptr[esp + 8]
fdiv dword ptr[esp + 1Ch]
loc_73F2ED:; CODE XREF : CalcCollisiontime + 148↑j
; CalcCollisiontime + 17B↑j
mov al, [esi + 3Ch]
fstp dword ptr[esi + 30h]
fld dword ptr[esp + 58h]
mov ecx, [esp + 5Ch]
or al, 2
fchs
mov[esi + 3Ch], al
fstp dword ptr[esi + 24h]
mov eax, [esp + 60h]
mov[esi + 20h], eax
mov[esi + 28h], ecx
loc_73F30F : ; CODE XREF : CalcCollisiontime + 10A↑j
pop esi
add esp, 9Ch
retn
}
}
void __declspec(naked) BounceParticle()
{
_asm
{
sub esp, 18h
push esi
mov esi, [esp+20h]
fld dword ptr [esi+30h]
push edi
fld st
lea edi, [esi+10h]
fmul dword ptr [edi]
mov eax, esi
fadd dword ptr [esi]
fstp dword ptr [esp+14h]
mov ecx, [esp+14h]
fld st
fmul dword ptr [edi+4]
fadd dword ptr [esi+4]
fstp dword ptr [esp+18h]
mov edx, [esp+18h]
fld st
fmul dword ptr [esi+1Ch]
fld st(1)
fmul dword ptr [edi+8]
fadd dword ptr [esi+8]
fld st(1)
mov [eax], ecx
fmul st, st(3)
mov [eax+4], edx
mov edx, edi
faddp st(1), st
fstp dword ptr [esp+1Ch]
mov ecx, [esp+1Ch]
mov [eax+8], ecx
mov eax, [edx]
fadd st, st
mov ecx, [edx+4]
mov edx, [edx+8]
mov [esp+1Ch], edx
fadd dword ptr [esp+1Ch]
mov [esp+0Ch], ecx
mov [esp+8], eax
fstp dword ptr [esp+1Ch]
mov eax, [esp+1Ch]
lea ecx, [esp+8]
push ecx ; float
fstp st
mov [esp+14h], eax
call rsqrt
fld dword ptr [esp+14h]
fmul dword ptr [esi+28h]
movzx edx, byte ptr [esi+38h]
fld dword ptr [esp+10h]
fmul dword ptr [esi+24h]
faddp st(1), st
fld dword ptr [esp+0Ch]
fmul dword ptr [esi+20h]
faddp st(1), st
fadd st, st
fld st
fmul dword ptr [esi+20h]
fld st(1)
fmul dword ptr [esi+24h]
fstp dword ptr [esp+1Ch]
fxch st(1)
fmul dword ptr [esi+28h]
fstp dword ptr [esp+20h]
fld dword ptr [esp+0Ch]
fsub st, st(1)
fstp dword ptr [esp+18h]
fstp st
fld dword ptr [esp+10h]
fsub dword ptr [esp+1Ch]
fstp dword ptr [esp+1Ch]