summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/animation/AnimBlendAssocGroup.cpp4
-rw-r--r--src/animation/CutsceneMgr.cpp2
-rw-r--r--src/audio/DMAudio.cpp1
-rw-r--r--src/audio/oal/aldlist.cpp10
-rw-r--r--src/audio/oal/channel.cpp6
-rw-r--r--src/audio/oal/stream.cpp27
-rw-r--r--src/audio/sampman_oal.cpp22
-rw-r--r--src/control/CarCtrl.cpp2
-rw-r--r--src/control/Phones.cpp8
-rw-r--r--src/control/Pickups.cpp12
-rw-r--r--src/control/Script.cpp203
-rw-r--r--src/core/CdStream.cpp10
-rw-r--r--src/core/CdStream.h6
-rw-r--r--src/core/CdStreamPosix.cpp516
-rw-r--r--src/core/ControllerConfig.cpp29
-rw-r--r--src/core/FileMgr.cpp59
-rw-r--r--src/core/Fire.cpp8
-rw-r--r--src/core/Frontend.cpp41
-rw-r--r--src/core/Frontend.h1
-rw-r--r--src/core/Game.cpp2
-rw-r--r--src/core/Streaming.cpp8
-rw-r--r--src/core/Timer.cpp31
-rw-r--r--src/core/ZoneCull.cpp5
-rw-r--r--src/core/Zones.cpp12
-rw-r--r--src/core/config.h11
-rw-r--r--src/core/main.cpp3
-rw-r--r--src/core/patcher.cpp20
-rw-r--r--src/core/re3.cpp51
-rw-r--r--src/extras/debugmenu.cpp3
-rw-r--r--src/fakerw/fake.cpp19
-rw-r--r--src/modelinfo/VehicleModelInfo.cpp6
-rw-r--r--src/peds/Ped.cpp10
-rw-r--r--src/peds/PlayerPed.cpp2
-rw-r--r--src/render/Console.cpp2
-rw-r--r--src/render/ParticleMgr.h12
-rw-r--r--src/render/PlayerSkin.cpp2
-rw-r--r--src/render/Shadows.cpp6
-rw-r--r--src/render/Shadows.h12
-rw-r--r--src/rw/RwHelper.cpp40
-rw-r--r--src/rw/TexRead.cpp1
-rw-r--r--src/rw/VisibilityPlugins.cpp8
-rw-r--r--src/save/GenericGameStorage.cpp2
-rw-r--r--src/save/PCSave.cpp2
-rw-r--r--src/skel/crossplatform.cpp130
-rw-r--r--src/skel/crossplatform.h81
-rw-r--r--src/skel/glfw/glfw.cpp175
-rw-r--r--src/skel/platform.h18
-rw-r--r--src/skel/skeleton.cpp6
-rw-r--r--src/skel/skeleton.h6
-rw-r--r--src/skel/win/win.cpp16
-rw-r--r--src/skel/win/win.h1
-rw-r--r--src/vehicles/Cranes.cpp8
52 files changed, 1336 insertions, 342 deletions
diff --git a/src/animation/AnimBlendAssocGroup.cpp b/src/animation/AnimBlendAssocGroup.cpp
index 5a6d10b4..fe419f2a 100644
--- a/src/animation/AnimBlendAssocGroup.cpp
+++ b/src/animation/AnimBlendAssocGroup.cpp
@@ -1,6 +1,10 @@
#include "common.h"
+#if defined _WIN32 && !defined __MINGW32__
#include "ctype.h"
+#else
+#include <cwctype>
+#endif
#include "General.h"
#include "RwHelper.h"
diff --git a/src/animation/CutsceneMgr.cpp b/src/animation/CutsceneMgr.cpp
index 0db54c4b..230e22fb 100644
--- a/src/animation/CutsceneMgr.cpp
+++ b/src/animation/CutsceneMgr.cpp
@@ -103,7 +103,7 @@ const struct {
{ "MT_PH2", STREAMED_SOUND_CUTSCENE_MARTY_PH2 },
{ "MT_PH3", STREAMED_SOUND_CUTSCENE_MARTY_PH3 },
{ "MT_PH4", STREAMED_SOUND_CUTSCENE_MARTY_PH4 },
- { NULL, NULL }
+ { NULL, 0 }
};
int
diff --git a/src/audio/DMAudio.cpp b/src/audio/DMAudio.cpp
index f1b9707b..888081b7 100644
--- a/src/audio/DMAudio.cpp
+++ b/src/audio/DMAudio.cpp
@@ -6,6 +6,7 @@
#include "AudioScriptObject.h"
#include "sampman.h"
#include "Text.h"
+#include "crossplatform.h"
cDMAudio DMAudio;
diff --git a/src/audio/oal/aldlist.cpp b/src/audio/oal/aldlist.cpp
index 2c2f13a8..768ace30 100644
--- a/src/audio/oal/aldlist.cpp
+++ b/src/audio/oal/aldlist.cpp
@@ -23,6 +23,12 @@
*/
#include "aldlist.h"
+
+#ifndef _WIN32
+#define _stricmp strcasecmp
+#define _strnicmp strncasecmp
+#endif
+
#ifdef AUDIO_OAL
/*
* Init call
@@ -67,7 +73,7 @@ ALDeviceList::ALDeviceList()
if ((bNewName) && (actualDeviceName != NULL) && (strlen(actualDeviceName) > 0)) {
memset(&ALDeviceInfo, 0, sizeof(ALDEVICEINFO));
ALDeviceInfo.bSelected = true;
- ALDeviceInfo.strDeviceName = std::string(actualDeviceName, strlen(actualDeviceName));
+ ALDeviceInfo.strDeviceName.assign(actualDeviceName, strlen(actualDeviceName));
alcGetIntegerv(device, ALC_MAJOR_VERSION, sizeof(int), &ALDeviceInfo.iMajorVersion);
alcGetIntegerv(device, ALC_MINOR_VERSION, sizeof(int), &ALDeviceInfo.iMinorVersion);
@@ -326,4 +332,4 @@ unsigned int ALDeviceList::GetMaxNumSources()
return iSourceCount;
}
-#endif \ No newline at end of file
+#endif
diff --git a/src/audio/oal/channel.cpp b/src/audio/oal/channel.cpp
index 7742a06a..6fe1d856 100644
--- a/src/audio/oal/channel.cpp
+++ b/src/audio/oal/channel.cpp
@@ -4,6 +4,10 @@
#include "common.h"
#include "sampman.h"
+#ifndef _WIN32
+#include <float.h>
+#endif
+
extern bool IsFXSupported();
CChannel::CChannel()
@@ -207,4 +211,4 @@ void CChannel::UpdateReverb(ALuint slot)
alSource3i(alSource, AL_AUXILIARY_SEND_FILTER, slot, 0, alFilter);
}
-#endif \ No newline at end of file
+#endif
diff --git a/src/audio/oal/stream.cpp b/src/audio/oal/stream.cpp
index 9bca0546..5a9c7d7d 100644
--- a/src/audio/oal/stream.cpp
+++ b/src/audio/oal/stream.cpp
@@ -4,13 +4,15 @@
#include "common.h"
#include "sampman.h"
-typedef long ssize_t;
-
#include <sndfile.h>
#include <mpg123.h>
-
+#ifdef _WIN32
+typedef long ssize_t;
#pragma comment( lib, "libsndfile-1.lib" )
#pragma comment( lib, "libmpg123.lib" )
+#else
+#include "crossplatform.h"
+#endif
class CSndFile : public IDecoder
{
@@ -192,7 +194,22 @@ CStream::CStream(char *filename, ALuint &source, ALuint (&buffers)[NUM_STREAMBUF
m_nPosBeforeReset(0)
{
- strcpy(m_aFilename, filename);
+// Be case-insensitive on linux (from https://github.com/OneSadCookie/fcaseopen/)
+#if !defined(_WIN32)
+ FILE *test = fopen(filename, "r");
+ if (!test) {
+ char *r = (char*)alloca(strlen(filename) + 2);
+ if (casepath(filename, r))
+ {
+ strcpy(m_aFilename, r);
+ }
+ } else {
+ fclose(test);
+#else
+ {
+#endif
+ strcpy(m_aFilename, filename);
+ }
DEV("Stream %s\n", m_aFilename);
@@ -517,4 +534,4 @@ void CStream::ProviderTerm()
ClearBuffers();
}
-#endif \ No newline at end of file
+#endif
diff --git a/src/audio/sampman_oal.cpp b/src/audio/sampman_oal.cpp
index bbaeae4c..64b763ec 100644
--- a/src/audio/sampman_oal.cpp
+++ b/src/audio/sampman_oal.cpp
@@ -5,16 +5,18 @@
#include "sampman.h"
#include <time.h>
-#include <io.h>
#include "eax.h"
#include "eax-util.h"
+#ifdef _WIN32
+#include <io.h>
#include <AL/al.h>
#include <AL/alc.h>
#include <AL/alext.h>
#include <AL/efx.h>
#include <AL/efx-presets.h>
+#endif
#include "oal/oal_utils.h"
#include "oal/aldlist.h"
@@ -31,7 +33,9 @@
//TODO: loop count
//TODO: mp3 player
+#ifdef _WIN32
#pragma comment( lib, "OpenAL32.lib" )
+#endif
cSampleManager SampleManager;
bool _bSampmanInitialised = false;
@@ -61,15 +65,15 @@ struct
int defaultProvider;
-char SampleBankDescFilename[] = "AUDIO\\SFX.SDT";
-char SampleBankDataFilename[] = "AUDIO\\SFX.RAW";
+char SampleBankDescFilename[] = "audio/sfx.SDT";
+char SampleBankDataFilename[] = "audio/sfx.RAW";
FILE *fpSampleDescHandle;
FILE *fpSampleDataHandle;
bool bSampleBankLoaded [MAX_SAMPLEBANKS];
int32 nSampleBankDiscStartOffset [MAX_SAMPLEBANKS];
int32 nSampleBankSize [MAX_SAMPLEBANKS];
-int32 nSampleBankMemoryStartAddress[MAX_SAMPLEBANKS];
+uintptr nSampleBankMemoryStartAddress[MAX_SAMPLEBANKS];
int32 _nSampleDataEndOffset;
int32 nPedSlotSfx [MAX_PEDSFX];
@@ -88,7 +92,7 @@ struct
{
ALuint buffer;
ALuint timer;
-
+
bool IsEmpty() { return timer == 0; }
void Set(ALuint buf) { buffer = buf; }
void Wait() { timer = 10000; }
@@ -573,7 +577,7 @@ cSampleManager::Initialise(void)
return false;
}
- nSampleBankMemoryStartAddress[SAMPLEBANK_MAIN] = (int32)malloc(nSampleBankSize[SAMPLEBANK_MAIN]);
+ nSampleBankMemoryStartAddress[SAMPLEBANK_MAIN] = (uintptr)malloc(nSampleBankSize[SAMPLEBANK_MAIN]);
ASSERT(nSampleBankMemoryStartAddress[SAMPLEBANK_MAIN] != NULL);
if ( nSampleBankMemoryStartAddress[SAMPLEBANK_MAIN] == NULL )
@@ -582,7 +586,7 @@ cSampleManager::Initialise(void)
return false;
}
- nSampleBankMemoryStartAddress[SAMPLEBANK_PED] = (int32)malloc(PED_BLOCKSIZE*MAX_PEDSFX);
+ nSampleBankMemoryStartAddress[SAMPLEBANK_PED] = (uintptr)malloc(PED_BLOCKSIZE*MAX_PEDSFX);
ASSERT(nSampleBankMemoryStartAddress[SAMPLEBANK_PED] != NULL);
}
@@ -985,7 +989,7 @@ cSampleManager::InitialiseChannel(uint32 nChannel, uint32 nSfx, uint8 nBank)
if ( !IsSampleBankLoaded(nBank) )
return false;
- int32 addr = nSampleBankMemoryStartAddress[nBank] + m_aSamples[nSfx].nOffset - m_aSamples[BankStartOffset[nBank]].nOffset;
+ uintptr addr = nSampleBankMemoryStartAddress[nBank] + m_aSamples[nSfx].nOffset - m_aSamples[BankStartOffset[nBank]].nOffset;
if ( ALBuffers[nSfx].IsEmpty() )
{
@@ -1401,4 +1405,4 @@ cSampleManager::InitialiseSampleBanks(void)
return true;
}
-#endif \ No newline at end of file
+#endif
diff --git a/src/control/CarCtrl.cpp b/src/control/CarCtrl.cpp
index 71236580..fcd1e83f 100644
--- a/src/control/CarCtrl.cpp
+++ b/src/control/CarCtrl.cpp
@@ -2523,7 +2523,7 @@ CCarCtrl::RegisterVehicleOfInterest(CVehicle* pVehicle)
return;
}
}
- uint32 oldestCarWeKeepTime = UINT_MAX;
+ uint32 oldestCarWeKeepTime = UINT32_MAX;
int oldestCarWeKeepIndex = 0;
for (int i = 0; i < MAX_CARS_TO_KEEP; i++) {
if (apCarsToKeep[i] && aCarsToKeepTime[i] < oldestCarWeKeepTime) {
diff --git a/src/control/Phones.cpp b/src/control/Phones.cpp
index 136ef7db..ee01b6c4 100644
--- a/src/control/Phones.cpp
+++ b/src/control/Phones.cpp
@@ -38,7 +38,7 @@ CPed* crimeReporters[NUMPHONES] = {};
bool
isPhoneAvailable(int m_phoneId)
{
- return gPhoneInfo.m_aPhones[m_phoneId].m_nState == PHONE_STATE_FREE &&
+ return gPhoneInfo.m_aPhones[m_phoneId].m_nState == PHONE_STATE_FREE &&
(crimeReporters[m_phoneId] == nil || !crimeReporters[m_phoneId]->IsPointerValid() || !crimeReporters[m_phoneId]->bRunningToPhone || crimeReporters[m_phoneId]->m_objective > OBJECTIVE_IDLE ||
crimeReporters[m_phoneId]->m_nLastPedState != PED_SEEK_POS &&
(crimeReporters[m_phoneId]->m_nPedState != PED_MAKE_CALL && crimeReporters[m_phoneId]->m_nPedState != PED_FACE_PHONE && crimeReporters[m_phoneId]->m_nPedState != PED_SEEK_POS));
@@ -194,10 +194,10 @@ CPhoneInfo::HasMessageBeenDisplayed(int phoneId)
{
if (bDisplayingPhoneMessage)
return false;
-
+
int state = m_aPhones[phoneId].m_nState;
- return state == PHONE_STATE_REPEATED_MESSAGE_SHOWN_ONCE ||
+ return state == PHONE_STATE_REPEATED_MESSAGE_SHOWN_ONCE ||
state == PHONE_STATE_ONETIME_MESSAGE_STARTED ||
state == PHONE_STATE_REPEATED_MESSAGE_STARTED;
}
@@ -218,7 +218,7 @@ INITSAVEBUF
m_aPhones[i] = ReadSaveBuf<CPhone>(buf);
// It's saved as building pool index in save file, convert it to true entity
if (m_aPhones[i].m_pEntity) {
- m_aPhones[i].m_pEntity = CPools::GetBuildingPool()->GetSlot((int)m_aPhones[i].m_pEntity - 1);
+ m_aPhones[i].m_pEntity = CPools::GetBuildingPool()->GetSlot((uintptr)m_aPhones[i].m_pEntity - 1);
}
}
VALIDATESAVEBUF(size)
diff --git a/src/control/Pickups.cpp b/src/control/Pickups.cpp
index 6b56cd8f..569af776 100644
--- a/src/control/Pickups.cpp
+++ b/src/control/Pickups.cpp
@@ -630,15 +630,15 @@ CPickups::Update()
float mult;
if ( dist < 10.0f )
mult = 1.0f - (dist / 10.0f );
- else
+ else
mult = 0.0f;
-
+
CVector pos = StaticCamCoors;
pos.z += (pPlayerVehicle->GetColModel()->boundingBox.GetSize().z + 2.0f) * mult;
-
+
if ( (CTimer::GetTimeInMilliseconds() - StaticCamStartTime) > 750 )
{
- TheCamera.SetCamPositionForFixedMode(pos, CVector(0.0f, 0.0f, 0.0f));
+ TheCamera.SetCamPositionForFixedMode(pos, CVector(0.0f, 0.0f, 0.0f));
TheCamera.TakeControl(FindPlayerVehicle(), CCam::MODE_FIXED, JUMP_CUT, CAMCONTROL_SCRIPT);
}
@@ -988,7 +988,7 @@ INITSAVEBUF
aPickUps[i] = ReadSaveBuf<CPickup>(buf);
if (aPickUps[i].m_eType != PICKUP_NONE && aPickUps[i].m_pObject != nil)
- aPickUps[i].m_pObject = CPools::GetObjectPool()->GetSlot((int32)aPickUps[i].m_pObject - 1);
+ aPickUps[i].m_pObject = CPools::GetObjectPool()->GetSlot((uintptr)aPickUps[i].m_pObject - 1);
}
CollectedPickUpIndex = ReadSaveBuf<uint16>(buf);
@@ -1029,7 +1029,7 @@ CPacManPickup::Update()
if (FindPlayerVehicle() == nil) return;
CVehicle *veh = FindPlayerVehicle();
-
+
if (DistanceSqr2D(FindPlayerVehicle()->GetPosition(), m_vecPosn.x, m_vecPosn.y) < 100.0f && veh->IsSphereTouchingVehicle(m_vecPosn.x, m_vecPosn.y, m_vecPosn.z, 1.5f)) {
switch (m_eType)
{
diff --git a/src/control/Script.cpp b/src/control/Script.cpp
index df3a489a..30793f55 100644
--- a/src/control/Script.cpp
+++ b/src/control/Script.cpp
@@ -131,7 +131,7 @@ int32 ScriptParams[32];
const uint32 CRunningScript::nSaveStructSize =
#ifdef COMPATIBLE_SAVES
- 136;
+ 136;
#else
sizeof(CRunningScript);
#endif
@@ -508,13 +508,14 @@ int open_script()
{
static int scriptToLoad = 0;
+#ifdef _WIN32
if (GetAsyncKeyState('G') & 0x8000)
scriptToLoad = 0;
if (GetAsyncKeyState('R') & 0x8000)
scriptToLoad = 1;
if (GetAsyncKeyState('D') & 0x8000)
scriptToLoad = 2;
-
+#endif
switch (scriptToLoad) {
case 0: return CFileMgr::OpenFile("main.scm", "rb");
case 1: return CFileMgr::OpenFile("main_freeroam.scm", "rb");
@@ -750,6 +751,8 @@ int8 CRunningScript::ProcessOneCommand()
int8 CRunningScript::ProcessCommands0To99(int32 command)
{
+ float *fScriptVar1;
+ int *nScriptVar1;
switch (command) {
case COMMAND_NOP:
return 0;
@@ -1358,7 +1361,7 @@ int8 CRunningScript::ProcessCommands0To99(int32 command)
UpdateCompareFlag(ped->m_pMyVehicle->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
@@ -1379,46 +1382,58 @@ int8 CRunningScript::ProcessCommands0To99(int32 command)
UpdateCompareFlag(ped->IsWithinArea(x1, y1, z1, x2, y2, z2));
if (!ScriptParams[7])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugCube(x1, y1, z1, x2, y2, z2);
return 0;
}
case COMMAND_ADD_INT_VAR_TO_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 += *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_INT_LVAR_TO_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 += *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_ADD_INT_VAR_TO_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 += *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_INT_LVAR_TO_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 += *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_ADD_FLOAT_VAR_TO_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_FLOAT_LVAR_TO_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_ADD_FLOAT_VAR_TO_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_FLOAT_LVAR_TO_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 += *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_INT_VAR_FROM_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 -= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_SUB_INT_LVAR_FROM_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 -= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_FLOAT_VAR_FROM_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_SUB_FLOAT_LVAR_FROM_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
default:
assert(0);
@@ -1429,66 +1444,88 @@ int8 CRunningScript::ProcessCommands0To99(int32 command)
int8 CRunningScript::ProcessCommands100To199(int32 command)
{
+ float *fScriptVar1;
+ int *nScriptVar1;
switch (command) {
case COMMAND_SUB_INT_LVAR_FROM_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 -= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_INT_VAR_FROM_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 -= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_SUB_FLOAT_LVAR_FROM_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_FLOAT_VAR_FROM_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 -= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_MULT_INT_VAR_BY_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) *= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 *= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_MULT_INT_LVAR_BY_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) *= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 *= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_MULT_INT_VAR_BY_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) *= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 *= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_MULT_INT_LVAR_BY_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) *= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 *= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_MULT_FLOAT_VAR_BY_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_MULT_FLOAT_LVAR_BY_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_MULT_FLOAT_VAR_BY_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_MULT_FLOAT_LVAR_BY_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 *= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_DIV_INT_VAR_BY_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) /= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 /= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_DIV_INT_LVAR_BY_INT_VAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) /= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *nScriptVar1 /= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_DIV_INT_VAR_BY_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) /= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 /= *GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_DIV_INT_LVAR_BY_INT_LVAR:
- *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) /= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ nScriptVar1 = GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *nScriptVar1 /= *GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_DIV_FLOAT_VAR_BY_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_DIV_FLOAT_LVAR_BY_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_DIV_FLOAT_VAR_BY_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_DIV_FLOAT_LVAR_BY_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 /= *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_ADD_TIMED_VAL_TO_FLOAT_VAR:
{
@@ -1505,16 +1542,20 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
return 0;
}
case COMMAND_ADD_TIMED_FLOAT_VAR_TO_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_TIMED_FLOAT_LVAR_TO_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_ADD_TIMED_FLOAT_VAR_TO_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_ADD_TIMED_FLOAT_LVAR_TO_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 += CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_TIMED_VAL_FROM_FLOAT_VAR:
{
@@ -1531,16 +1572,20 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
return 0;
}
case COMMAND_SUB_TIMED_FLOAT_VAR_FROM_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_SUB_TIMED_FLOAT_LVAR_FROM_FLOAT_VAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL) -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ *fScriptVar1 -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SUB_TIMED_FLOAT_VAR_FROM_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_GLOBAL);
return 0;
case COMMAND_SUB_TIMED_FLOAT_LVAR_FROM_FLOAT_LVAR:
- *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL) -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ fScriptVar1 = (float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
+ *fScriptVar1 -= CTimer::GetTimeStep() * *(float*)GetPointerToScriptVariable(&m_nIp, VAR_LOCAL);
return 0;
case COMMAND_SET_VAR_INT_TO_VAR_INT:
{
@@ -1897,7 +1942,7 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
UpdateCompareFlag(ped->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
@@ -1924,7 +1969,7 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
UpdateCompareFlag(ped->IsWithinArea(x1, y1, z1, x2, y2, z2));
if (!ScriptParams[7])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugCube(x1, y1, z1, x2, y2, z2);
return 0;
@@ -2136,7 +2181,7 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
UpdateCompareFlag(vehicle->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
@@ -2155,7 +2200,7 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
UpdateCompareFlag(vehicle->IsWithinArea(x1, y1, z1, x2, y2, z2));
if (!ScriptParams[7])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugCube(x1, y1, z1, x2, y2, z2);
return 0;
@@ -2240,7 +2285,7 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
case COMMAND_RETURN_FALSE:
UpdateCompareFlag(false);
return 0;
- /* Special command only used by compiler.
+ /* Special command only used by compiler.
case COMMAND_VAR_INT:
*/
default:
@@ -2251,9 +2296,9 @@ int8 CRunningScript::ProcessCommands100To199(int32 command)
}
int8 CRunningScript::ProcessCommands200To299(int32 command)
-{
+{
switch (command) {
- /* Special commands.
+ /* Special commands.
case COMMAND_VAR_FLOAT:
case COMMAND_LVAR_INT:
case COMMAND_LVAR_FLOAT:
@@ -2645,7 +2690,7 @@ int8 CRunningScript::ProcessCommands200To299(int32 command)
pPed->m_fearFlags |= ScriptParams[1];
return 0;
}
- /* Not implemented.
+ /* Not implemented.
case COMMAND_SET_CHAR_THREAT_REACTION:
*/
case COMMAND_SET_CHAR_OBJ_NO_OBJ:
@@ -2657,7 +2702,7 @@ int8 CRunningScript::ProcessCommands200To299(int32 command)
pPed->ClearObjective();
return 0;
}
- /* Not implemented.
+ /* Not implemented.
case COMMAND_ORDER_DRIVER_OUT_OF_CAR:
case COMMAND_ORDER_CHAR_TO_DRIVE_CAR:
case COMMAND_ADD_PATROL_POINT:
@@ -2704,7 +2749,7 @@ int8 CRunningScript::ProcessCommands200To299(int32 command)
UpdateCompareFlag(pPed->bScriptObjectiveCompleted);
return 0;
}
- /* Not implemented.
+ /* Not implemented.
case COMMAND_SET_CHAR_DRIVE_AGGRESSION:
case COMMAND_SET_CHAR_MAX_DRIVESPEED:
*/
@@ -2820,7 +2865,7 @@ int8 CRunningScript::ProcessCommands200To299(int32 command)
CTheScripts::ClearSpaceForMissionEntity(pos, pPlayer->m_pPed);
return 0;
}
- /* Not implemented.
+ /* Not implemented.
case COMMAND_MAKE_CHAR_DO_NOTHING:
*/
default:
@@ -2890,7 +2935,7 @@ int8 CRunningScript::ProcessCommands300To399(int32 command)
pVehicle->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
@@ -2910,7 +2955,7 @@ int8 CRunningScript::ProcessCommands300To399(int32 command)
pVehicle->IsWithinArea(x1, y1, z1, x2, y2, z2));
if (!ScriptParams[7])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, (z1 + z2) / 2);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugCube(x1, y1, z1, x2, y2, z2);
return 0;
@@ -4334,7 +4379,7 @@ int8 CRunningScript::ProcessCommands400To499(int32 command)
CWanted::SetMaximumWantedLevel(ScriptParams[0]);
return 0;
}
- /* Debug commands?
+ /* Debug commands?
case COMMAND_SAVE_VAR_INT:
case COMMAND_SAVE_VAR_FLOAT:
*/
@@ -5129,7 +5174,7 @@ int8 CRunningScript::ProcessCommands500To599(int32 command)
CVector pos = *(CVector*)&ScriptParams[0];
if (pos.z <= MAP_Z_LOW_LIMIT)
pos.z = CWorld::FindGroundZForCoord(pos.x, pos.y);
- CCoronas::RegisterCorona((uint32)this + m_nIp, ScriptParams[6], ScriptParams[7], ScriptParams[8],
+ CCoronas::RegisterCorona((uintptr)this + m_nIp, ScriptParams[6], ScriptParams[7], ScriptParams[8],
255, pos, *(float*)&ScriptParams[3], 150.0f, ScriptParams[4], ScriptParams[5], 1, 0, 0, 0.0f);
return 0;
}
@@ -5741,7 +5786,7 @@ int8 CRunningScript::ProcessCommands700To799(int32 command)
UpdateCompareFlag(pPed->bIsShooting && pPed->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
@@ -5758,14 +5803,14 @@ int8 CRunningScript::ProcessCommands700To799(int32 command)
UpdateCompareFlag(pPed->bIsShooting && pPed->IsWithinArea(x1, y1, x2, y2));
if (!ScriptParams[5])
return 0;
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, x1, y1, x2, y2, MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag)
CTheScripts::DrawDebugSquare(x1, y1, x2, y2);
return 0;
}
case COMMAND_IS_CURRENT_PLAYER_WEAPON:
{
- CollectParameters(&m_nIp, 2);
+ CollectParameters(&m_nIp, 2);
CPed* pPed = CWorld::Players[ScriptParams[0]].m_pPed;
assert(pPed);
UpdateCompareFlag(ScriptParams[1] == pPed->m_weapons[pPed->m_currentWeapon].m_eWeaponType);
@@ -7781,7 +7826,7 @@ int8 CRunningScript::ProcessCommands900To999(int32 command)
CVector pos = *(CVector*)&ScriptParams[0];
if (pos.z <= MAP_Z_LOW_LIMIT)
pos.z = CWorld::FindGroundZForCoord(pos.x, pos.y);
- C3dMarkers::PlaceMarkerSet((uint32)this + m_nIp, 4, pos, *(float*)&ScriptParams[3],
+ C3dMarkers::PlaceMarkerSet((uintptr)this + m_nIp, 4, pos, *(float*)&ScriptParams[3],
SPHERE_MARKER_R, SPHERE_MARKER_G, SPHERE_MARKER_B, SPHERE_MARKER_A,
SPHERE_MARKER_PULSE_PERIOD, SPHERE_MARKER_PULSE_FRACTION, 0);
return 0;
@@ -7988,7 +8033,7 @@ int8 CRunningScript::ProcessCommands900To999(int32 command)
pos.z = CWorld::FindGroundZForCoord(pos.x, pos.y);
float radius = *(float*)&ScriptParams[3];
CTheScripts::GetActualScriptSphereIndex(CollectNextParameterWithoutIncreasingPC(m_nIp));
- ScriptParams[0] = CTheScripts::AddScriptSphere((uint32)this + m_nIp, pos, radius);
+ ScriptParams[0] = CTheScripts::AddScriptSphere((uintptr)this + m_nIp, pos, radius);
StoreParameters(&m_nIp, 1);
return 0;
}
@@ -9920,7 +9965,7 @@ void CRunningScript::LocatePlayerCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10004,9 +10049,9 @@ void CRunningScript::LocatePlayerCharCommand(int32 command, uint32* pIp)
UpdateCompareFlag(result);
if (debug)
#ifdef FIX_BUGS
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
#else
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dX, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dX, b3D ? Z : MAP_Z_LOW_LIMIT);
#endif
if (CTheScripts::DbgFlag) {
if (b3D)
@@ -10084,7 +10129,7 @@ void CRunningScript::LocatePlayerCarCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10188,7 +10233,7 @@ void CRunningScript::LocateCharCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10274,9 +10319,9 @@ void CRunningScript::LocateCharCharCommand(int32 command, uint32* pIp)
UpdateCompareFlag(result);
if (debug)
#ifdef FIX_BUGS
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
#else
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dX, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dX, b3D ? Z : MAP_Z_LOW_LIMIT);
#endif
if (CTheScripts::DbgFlag) {
if (b3D)
@@ -10355,7 +10400,7 @@ void CRunningScript::LocateCharCarCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10433,7 +10478,7 @@ void CRunningScript::LocateCharObjectCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10505,7 +10550,7 @@ void CRunningScript::LocateCarCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10544,7 +10589,7 @@ void CRunningScript::LocateSniperBulletCommand(int32 command, uint32* pIp)
result = CBulletInfo::TestForSniperBullet(X - dX, X + dX, Y - dY, Y + dY, b3D ? Z - dZ : -1000.0f, b3D ? Z + dZ : 1000.0f);
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, X - dX, Y - dY, X + dX, Y + dY, b3D ? Z : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(X - dX, Y - dY, Z - dZ, X + dX, Y + dY, Z + dZ);
@@ -10661,7 +10706,7 @@ void CRunningScript::PlayerInAreaCheckCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(infX, infY, infZ, supX, supY, supZ);
@@ -10783,7 +10828,7 @@ void CRunningScript::PlayerInAngledAreaCheckCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantAngledArea((uint32)this + m_nIp, infX, infY, supX, supY,
+ CTheScripts::HighlightImportantAngledArea((uintptr)this + m_nIp, infX, infY, supX, supY,
rotatedSupX, rotatedSupY, rotatedInfX, rotatedInfY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
@@ -10904,7 +10949,7 @@ void CRunningScript::CharInAreaCheckCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(infX, infY, infZ, supX, supY, supZ);
@@ -11002,7 +11047,7 @@ void CRunningScript::CarInAreaCheckCommand(int32 command, uint32* pIp)
}
UpdateCompareFlag(result);
if (debug)
- CTheScripts::HighlightImportantArea((uint32)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
+ CTheScripts::HighlightImportantArea((uintptr)this + m_nIp, infX, infY, supX, supY, b3D ? (infZ + supZ) / 2 : MAP_Z_LOW_LIMIT);
if (CTheScripts::DbgFlag) {
if (b3D)
CTheScripts::DrawDebugCube(infX, infY, infZ, supX, supY, supZ);
diff --git a/src/core/CdStream.cpp b/src/core/CdStream.cpp
index 666041e1..d9978040 100644
--- a/src/core/CdStream.cpp
+++ b/src/core/CdStream.cpp
@@ -1,3 +1,4 @@
+#ifdef _WIN32
#define WITHWINDOWS
#include "common.h"
@@ -16,9 +17,8 @@ struct CdReadInfo
char field_C;
bool bLocked;
bool bInUse;
- char _pad0;
int32 nStatus;
- HANDLE hSemaphore;
+ HANDLE hSemaphore; // used for CdStreamSync
HANDLE hFile;
OVERLAPPED Overlapped;
};
@@ -32,7 +32,7 @@ int32 gNumChannels;
HANDLE gImgFiles[MAX_CDIMAGES];
HANDLE _gCdStreamThread;
-HANDLE gCdStreamSema;
+HANDLE gCdStreamSema; // released when we have new thing to read(so channel is set)
DWORD _gCdStreamThreadId;
CdReadInfo *gpReadInfo;
@@ -296,6 +296,7 @@ CdStreamGetLastPosn(void)
return lastPosnRead;
}
+// wait for channel to finish reading
int32
CdStreamSync(int32 channel)
{
@@ -324,6 +325,7 @@ CdStreamSync(int32 channel)
if ( _gbCdStreamOverlapped && pChannel->hFile )
{
ASSERT(pChannel->hFile != nil );
+ // Beware: This is blocking call (because of last parameter)
if ( GetOverlappedResult(pChannel->hFile, &pChannel->Overlapped, &NumberOfBytesTransferred, TRUE) )
return STREAM_NONE;
else
@@ -406,6 +408,7 @@ WINAPI CdStreamThread(LPVOID lpThreadParameter)
{
pChannel->nStatus = STREAM_NONE;
}
+ // Beware: This is blocking call (because of last parameter)
else if ( GetLastError() == ERROR_IO_PENDING
&& GetOverlappedResult(pChannel->hFile, &pChannel->Overlapped, &NumberOfBytesTransferred, TRUE) )
{
@@ -508,3 +511,4 @@ CdStreamGetNumImages(void)
{
return gNumImages;
}
+#endif
diff --git a/src/core/CdStream.h b/src/core/CdStream.h
index ba6c63a3..d0f9a855 100644
--- a/src/core/CdStream.h
+++ b/src/core/CdStream.h
@@ -41,4 +41,8 @@ void RemoveFirstInQueue(Queue *queue);
bool CdStreamAddImage(char const *path);
char *CdStreamGetImageName(int32 cd);
void CdStreamRemoveImages(void);
-int32 CdStreamGetNumImages(void); \ No newline at end of file
+int32 CdStreamGetNumImages(void);
+
+#ifndef _WIN32
+extern bool flushStream[MAX_CDCHANNELS];
+#endif
diff --git a/src/core/CdStreamPosix.cpp b/src/core/CdStreamPosix.cpp
new file mode 100644
index 00000000..7c49f5f1
--- /dev/null
+++ b/src/core/CdStreamPosix.cpp
@@ -0,0 +1,516 @@
+#ifndef _WIN32
+#include "common.h"
+#include "crossplatform.h"
+#include <pthread.h>
+#include <signal.h>
+#include <semaphore.h>
+#include <sys/types.h>
+#include <unistd.h>
+#include <sys/time.h>
+#include <sys/statvfs.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <sys/resource.h>
+#include <sys/syscall.h>
+
+#include "CdStream.h"
+#include "rwcore.h"
+#include "RwHelper.h"
+
+#define CDDEBUG(f, ...) debug ("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
+#define CDTRACE(f, ...) printf("%s: " f "\n", "cdvd_stream", ## __VA_ARGS__)
+
+// #define ONE_THREAD_PER_CHANNEL // Don't use if you're not on SSD/Flash. (Also you may want to benefit from this via using all channels in Streaming.cpp)
+
+bool flushStream[MAX_CDCHANNELS];
+
+struct CdReadInfo
+{
+ uint32 nSectorOffset;
+ uint32 nSectorsToRead;
+ void *pBuffer;
+ bool bLocked;
+ bool bReading;
+ int32 nStatus;
+#ifdef ONE_THREAD_PER_CHANNEL
+ int8 nThreadStatus; // 0: created 1:initalized 2:abort now
+ pthread_t pChannelThread;
+ sem_t pStartSemaphore;
+#endif
+ sem_t pDoneSemaphore; // used for CdStreamSync
+ int32 hFile;
+};
+
+char gCdImageNames[MAX_CDIMAGES+1][64];
+int32 gNumImages;
+int32 gNumChannels;
+
+int32 gImgFiles[MAX_CDIMAGES]; // -1: error 0:unused otherwise: fd
+char *gImgNames[MAX_CDIMAGES];
+
+#ifndef ONE_THREAD_PER_CHANNEL
+pthread_t _gCdStreamThread;
+sem_t gCdStreamSema; // released when we have new thing to read(so channel is set)
+int8 gCdStreamThreadStatus; // 0: created 1:initalized 2:abort now
+Queue gChannelRequestQ;
+bool _gbCdStreamOverlapped;
+#endif
+
+CdReadInfo *gpReadInfo;
+
+int32 lastPosnRead;
+
+int _gdwCdStreamFlags;
+
+void *CdStreamThread(void* channelId);
+
+void
+CdStreamInitThread(void)
+{
+ int status;
+
+#ifndef ONE_THREAD_PER_CHANNEL
+ gChannelRequestQ.items = (int32 *)calloc(gNumChannels + 1, sizeof(int32));
+ gChannelRequestQ.head = 0;
+ gChannelRequestQ.tail = 0;
+ gChannelRequestQ.size = gNumChannels + 1;
+ ASSERT(gChannelRequestQ.items != nil );
+ status = sem_init(&gCdStreamSema, 0, 0);
+#endif
+
+
+ if (status == -1) {
+ CDTRACE("failed to create stream semaphore");
+ ASSERT(0);
+ return;
+ }
+
+
+ if ( gNumChannels > 0 )
+ {
+ for ( int32 i = 0; i < gNumChannels; i++ )
+ {
+ status = sem_init(&gpReadInfo[i].pDoneSemaphore, 0, 0);
+
+ if (status == -1)
+ {
+ CDTRACE("failed to create sync semaphore");
+ ASSERT(0);
+ return;
+ }
+#ifdef ONE_THREAD_PER_CHANNEL
+ status = sem_init(&gpReadInfo[i].pStartSemaphore, 0, 0);
+
+ if (status == -1)
+ {
+ CDTRACE("failed to create start semaphore");
+ ASSERT(0);
+ return;
+ }
+ gpReadInfo[i].nThreadStatus = 0;
+ int *channelI = (int*)malloc(sizeof(int));
+ *channelI = i;
+ status = pthread_create(&gpReadInfo[i].pChannelThread, NULL, CdStreamThread, (void*)channelI);
+
+ if (status == -1)
+ {
+ CDTRACE("failed to create sync thread");
+ ASSERT(0);
+ return;
+ }
+#endif
+ }
+ }
+
+#ifndef ONE_THREAD_PER_CHANNEL
+ debug("Using one streaming thread for all channels\n");
+ status = pthread_create(&_gCdStreamThread, NULL, CdStreamThread, nil);
+ gCdStreamThreadStatus = 0;
+
+ if (status == -1)
+ {
+ CDTRACE("failed to create sync thread");
+ ASSERT(0);
+ return;
+ }
+#else
+ debug("Using seperate streaming threads for each channel\n");
+#endif
+}
+
+void
+CdStreamInit(int32 numChannels)
+{
+ struct statvfs fsInfo;
+
+ if((statvfs("models/gta3.img", &fsInfo)) < 0)
+ {
+ CDTRACE("can't get filesystem info");
+ ASSERT(0);
+ return;
+ }
+
+ _gdwCdStreamFlags = O_RDONLY | O_NOATIME;
+
+ // People say it's slower
+/*
+ if ( fsInfo.f_bsize <= CDSTREAM_SECTOR_SIZE )
+ {
+ _gdwCdStreamFlags |= O_DIRECT;
+ debug("Using no buffered loading for streaming\n");
+ }
+*/
+ void *pBuffer = (void *)RwMallocAlign(CDSTREAM_SECTOR_SIZE, fsInfo.f_bsize);
+ ASSERT( pBuffer != nil );
+
+ gNumImages = 0;
+
+ gNumChannels = numChannels;
+
+ gpReadInfo = (CdReadInfo *)calloc(sizeof(CdReadInfo), numChannels);
+ ASSERT( gpReadInfo != nil );
+
+ CDDEBUG("read info %p", gpReadInfo);
+
+ CdStreamInitThread();
+
+ ASSERT( pBuffer != nil );
+ RwFreeAlign(pBuffer);
+}
+
+uint32
+GetGTA3ImgSize(void)
+{
+ ASSERT( gImgFiles[0] > 0 );
+ struct stat statbuf;
+
+ char path[PATH_MAX];
+ realpath(gImgNames[0], path);
+ if (stat(path, &statbuf) == -1) {
+ // Try case-insensitivity
+ char *r = (char*)alloca(strlen(gImgNames[0]) + 2);
+ if (casepath(gImgNames[0], r))
+ {
+ realpath(r, path);
+ if (stat(path, &statbuf) != -1)
+ goto ok;
+ }
+
+ CDTRACE("can't get size of gta3.img");
+ ASSERT(0);
+ return 0;
+ }
+ok:
+ return statbuf.st_size;
+}
+
+void
+CdStreamShutdown(void)
+{
+ // Destroying semaphores and free(gpReadInfo) will be done at threads
+#ifndef ONE_THREAD_PER_CHANNEL
+ free(gChannelRequestQ.items);
+ gCdStreamThreadStatus = 2;
+ sem_post(&gCdStreamSema);
+#endif
+
+#ifdef ONE_THREAD_PER_CHANNEL
+ for ( int32 i = 0; i < gNumChannels; i++ ) {
+ gpReadInfo[i].nThreadStatus = 2;
+ sem_post(&gpReadInfo[i].pStartSemaphore);
+ }
+#endif
+}
+
+
+int32
+CdStreamRead(int32 channel, void *buffer, uint32 offset, uint32 size)
+{
+ ASSERT( channel < gNumChannels );
+ ASSERT( buffer != nil );
+
+ lastPosnRead = size + offset;
+
+ ASSERT( _GET_INDEX(offset) < MAX_CDIMAGES );
+ int32 hImage = gImgFiles[_GET_INDEX(offset)];
+ ASSERT( hImage > 0 );
+
+ CdReadInfo *pChannel = &gpReadInfo[channel];
+ ASSERT( pChannel != nil );
+
+ pChannel->hFile = hImage - 1;
+
+ if ( pChannel->nSectorsToRead != 0 || pChannel->bReading )
+ return STREAM_NONE;
+
+ pChannel->nStatus = STREAM_NONE;
+ pChannel->nSectorOffset = _GET_OFFSET(offset);
+ pChannel->nSectorsToRead = size;
+ pChannel->pBuffer = buffer;
+ pChannel->bLocked = 0;
+
+#ifndef ONE_THREAD_PER_CHANNEL
+ AddToQueue(&gChannelRequestQ, channel);
+ if ( sem_post(&gCdStreamSema) != 0 )
+ printf("Signal Sema Error\n");
+#else
+ if ( sem_post(&gpReadInfo[channel].pStartSemaphore) != 0 )
+ printf("Signal Sema Error\n");
+#endif
+
+ return STREAM_SUCCESS;
+}
+
+int32
+CdStreamGetStatus(int32 channel)
+{
+ ASSERT( channel < gNumChannels );
+ CdReadInfo *pChannel = &gpReadInfo[channel];
+ ASSERT( pChannel != nil );
+
+#ifdef ONE_THREAD_PER_CHANNEL
+ if (pChannel->nThreadStatus == 2)
+ return STREAM_NONE;
+#else
+ if (gCdStreamThreadStatus == 2)
+ return STREAM_NONE;
+#endif
+
+ if ( pChannel->bReading )
+ return STREAM_READING;
+
+ if ( pChannel->nSectorsToRead != 0 )
+ return STREAM_WAITING;
+
+ if ( pChannel->nStatus != STREAM_NONE )
+ {
+ int32 status = pChannel->nStatus;
+
+ pChannel->nStatus = STREAM_NONE;
+
+ return status;
+ }
+
+ return STREAM_NONE;
+}
+
+int32
+CdStreamGetLastPosn(void)
+{
+ return lastPosnRead;
+}
+
+// wait for channel to finish reading
+int32
+CdStreamSync(int32 channel)
+{
+ ASSERT( channel < gNumChannels );
+ CdReadInfo *pChannel = &gpReadInfo[channel];
+ ASSERT( pChannel != nil );
+
+ if (flushStream[channel]) {
+#ifdef ONE_THREAD_PER_CHANNEL
+ pChannel->nSectorsToRead = 0;
+ pthread_kill(gpReadInfo[channel].pChannelThread, SIGINT);
+#else
+ if (pChannel->bReading) {
+ pChannel->nSectorsToRead = 0;
+ pthread_kill(_gCdStreamThread, SIGINT);
+ } else {
+ pChannel->nSectorsToRead = 0;
+ }
+#endif
+ pChannel->bReading = false;
+ flushStream[channel] = false;
+ return STREAM_NONE;
+ }
+
+ if ( pChannel->nSectorsToRead != 0 )
+ {
+ pChannel->bLocked = true;
+
+ sem_wait(&pChannel->pDoneSemaphore);
+ }
+
+ pChannel->bReading = false;
+
+ return pChannel->nStatus;
+}
+
+void
+AddToQueue(Queue *queue, int32 item)
+{
+ ASSERT( queue != nil );
+ ASSERT( queue->items != nil );
+ queue->items[queue->tail] = item;
+
+ queue->tail = (queue->tail + 1) % queue->size;
+
+ if ( queue->head == queue->tail )
+ debug("Queue is full\n");
+}
+
+int32
+GetFirstInQueue(Queue *queue)
+{
+ ASSERT( queue != nil );
+ if ( queue->head == queue->tail )
+ return -1;
+
+ ASSERT( queue->items != nil );
+ return queue->items[queue->head];
+}
+
+void
+RemoveFirstInQueue(Queue *queue)
+{
+ ASSERT( queue != nil );
+ if ( queue->head == queue->tail )
+ {
+ debug("Queue is empty\n");
+ return;
+ }
+
+ queue->head = (queue->head + 1) % queue->size;
+}
+
+void *CdStreamThread(void *param)
+{
+ debug("Created cdstream thread\n");
+
+#ifndef ONE_THREAD_PER_CHANNEL
+ while (gCdStreamThreadStatus != 2) {
+ sem_wait(&gCdStreamSema);
+ int32 channel = GetFirstInQueue(&gChannelRequestQ);
+#else
+ int channel = *((int*)param);
+ while (gpReadInfo[channel].nThreadStatus != 2){
+ sem_wait(&gpReadInfo[channel].pStartSemaphore);
+#endif
+ ASSERT( channel < gNumChannels );
+
+ CdReadInfo *pChannel = &gpReadInfo[channel];
+ ASSERT( pChannel != nil );
+
+#ifdef ONE_THREAD_PER_CHANNEL
+ if (gpReadInfo[channel].nThreadStatus == 0){
+ gpReadInfo[channel].nThreadStatus = 1;
+#else
+ if (gCdStreamThreadStatus == 0){
+ gCdStreamThreadStatus = 1;
+#endif
+ pid_t tid = syscall(SYS_gettid);
+ int ret = setpriority(PRIO_PROCESS, tid, getpriority(PRIO_PROCESS, getpid()) + 1);
+ }
+
+ // spurious wakeup or we sent interrupt signal for flushing
+ if(pChannel->nSectorsToRead == 0)
+ continue;
+
+ pChannel->bReading = true;
+
+ if ( pChannel->nStatus == STREAM_NONE )
+ {
+ ASSERT(pChannel->hFile >= 0);
+ ASSERT(pChannel->pBuffer != nil );
+
+ lseek(pChannel->hFile, pChannel->nSectorOffset * CDSTREAM_SECTOR_SIZE, SEEK_SET);
+ if (read(pChannel->hFile, pChannel->pBuffer, pChannel->nSectorsToRead * CDSTREAM_SECTOR_SIZE) == -1) {
+ // pChannel->nSectorsToRead == 0 at this point means we wanted to flush channel
+ pChannel->nStatus = pChannel->nSectorsToRead == 0 ? STREAM_NONE : STREAM_ERROR;
+ } else {
+ pChannel->nStatus = STREAM_NONE;
+ }
+ }
+
+#ifndef ONE_THREAD_PER_CHANNEL
+ RemoveFirstInQueue(&gChannelRequestQ);
+#endif
+
+ pChannel->nSectorsToRead = 0;
+
+ if ( pChannel->bLocked )
+ {
+ sem_post(&pChannel->pDoneSemaphore);
+ }
+ pChannel->bReading = false;
+ }
+#ifndef ONE_THREAD_PER_CHANNEL
+ for ( int32 i = 0; i < gNumChannels; i++ )
+ {
+ sem_destroy(&gpReadInfo[i].pDoneSemaphore);
+ }
+ sem_destroy(&gCdStreamSema);
+#else
+ sem_destroy(&gpReadInfo[channel].pStartSemaphore);
+ sem_destroy(&gpReadInfo[channel].pDoneSemaphore);
+#endif
+ free(gpReadInfo);
+ pthread_exit(nil);
+}
+
+bool
+CdStreamAddImage(char const *path)
+{
+ ASSERT(path != nil);
+ ASSERT(gNumImages < MAX_CDIMAGES);
+
+ gImgFiles[gNumImages] = open(path, _gdwCdStreamFlags);
+
+ // Fix case sensitivity and backslashes.
+ if (gImgFiles[gNumImages] == -1) {
+ char *r = (char*)alloca(strlen(path) + 2);
+ if (casepath(path, r))
+ {
+ gImgFiles[gNumImages] = open(r, _gdwCdStreamFlags);
+ }
+ }
+
+ if ( gImgFiles[gNumImages] == -1 ) {
+ assert(false);
+ return false;
+ }
+
+ gImgNames[gNumImages] = strdup(path);
+ gImgFiles[gNumImages]++; // because -1: error 0: not used
+
+ strcpy(gCdImageNames[gNumImages], path);
+
+ gNumImages++;
+
+ return true;
+}
+
+char *
+CdStreamGetImageName(int32 cd)
+{
+ ASSERT(cd < MAX_CDIMAGES);
+ if ( gImgFiles[cd] > 0)
+ return gCdImageNames[cd];
+
+ return nil;
+}
+
+void
+CdStreamRemoveImages(void)
+{
+ for ( int32 i = 0; i < gNumChannels; i++ )
+ CdStreamSync(i);
+
+ for ( int32 i = 0; i < gNumImages; i++ )
+ {
+ close(gImgFiles[i] - 1);
+ free(gImgNames[i]);
+ gImgFiles[i] = 0;
+ }
+
+ gNumImages = 0;
+}
+
+int32
+CdStreamGetNumImages(void)
+{
+ return gNumImages;
+}
+#endif
diff --git a/src/core/ControllerConfig.cpp b/src/core/ControllerConfig.cpp
index cba8186f..dcd9f125 100644
--- a/src/core/ControllerConfig.cpp
+++ b/src/core/ControllerConfig.cpp
@@ -4,7 +4,8 @@
#endif
#include "common.h"
-#include "crossplatform.h"
+#include "platform.h"
+#include "crossplatform.h" // for Windows version
#include "ControllerConfig.h"
#include "Pad.h"
#include "FileMgr.h"
@@ -163,14 +164,14 @@ void CControllerConfigManager::InitDefaultControlConfiguration()
SetControllerKeyAssociatedWithAction (VEHICLE_LOOKRIGHT, rsPADDOWN, KEYBOARD);
SetControllerKeyAssociatedWithAction (VEHICLE_LOOKRIGHT, 'E', OPTIONAL_EXTRA);
-
- if ( _dwOperatingSystemVersion != OS_WIN98 )
- {
+
+ if ( _dwOperatingSystemVersion == OS_WIN98 )
+ SetControllerKeyAssociatedWithAction(VEHICLE_HORN, rsSHIFT, OPTIONAL_EXTRA); // BUG: must be KEYBOARD ?
+ else
+ {
SetControllerKeyAssociatedWithAction(VEHICLE_HORN, rsLSHIFT, OPTIONAL_EXTRA);
SetControllerKeyAssociatedWithAction(VEHICLE_HORN, rsRSHIFT, KEYBOARD);
- }
- else
- SetControllerKeyAssociatedWithAction(VEHICLE_HORN, rsSHIFT, OPTIONAL_EXTRA); // BUG: must be KEYBOARD ?
+ }
SetControllerKeyAssociatedWithAction (VEHICLE_HANDBRAKE, rsRCTRL, KEYBOARD);
SetControllerKeyAssociatedWithAction (VEHICLE_HANDBRAKE, ' ', OPTIONAL_EXTRA);
@@ -216,19 +217,19 @@ void CControllerConfigManager::InitDefaultControlConfiguration()
SetControllerKeyAssociatedWithAction (PED_JUMPING, rsRCTRL, KEYBOARD);
SetControllerKeyAssociatedWithAction (PED_JUMPING, ' ', OPTIONAL_EXTRA);
-
- if ( _dwOperatingSystemVersion != OS_WIN98 )
- {
+
+ if ( _dwOperatingSystemVersion == OS_WIN98 )
+ SetControllerKeyAssociatedWithAction(PED_SPRINT, rsSHIFT, OPTIONAL_EXTRA); // BUG: must be KEYBOARD ?
+ else
+ {
SetControllerKeyAssociatedWithAction(PED_SPRINT, rsLSHIFT, OPTIONAL_EXTRA);
#ifndef FIX_BUGS
SetControllerKeyAssociatedWithAction(PED_SPRINT, rsRSHIFT, OPTIONAL_EXTRA); // BUG: must be KEYBOARD
#else
SetControllerKeyAssociatedWithAction(PED_SPRINT, rsRSHIFT, KEYBOARD);
#endif
- }
- else
- SetControllerKeyAssociatedWithAction(PED_SPRINT, rsSHIFT, OPTIONAL_EXTRA); // BUG: must be KEYBOARD ?
-
+ }
+
SetControllerKeyAssociatedWithAction (PED_CYCLE_TARGET_LEFT, '[', KEYBOARD);
SetControllerKeyAssociatedWithAction (PED_CYCLE_TARGET_RIGHT, ']', OPTIONAL_EXTRA); // BUG: must be KEYBOARD ?
diff --git a/src/core/FileMgr.cpp b/src/core/FileMgr.cpp
index 46d725cd..1939c861 100644
--- a/src/core/FileMgr.cpp
+++ b/src/core/FileMgr.cpp
@@ -1,6 +1,8 @@
#define _CRT_SECURE_NO_WARNINGS
#include <fcntl.h>
+#ifdef _WIN32
#include <direct.h>
+#endif
#include "common.h"
#include "FileMgr.h"
@@ -24,6 +26,31 @@ struct myFILE
#define NUMFILES 20
static myFILE myfiles[NUMFILES];
+
+#if !defined(_WIN32)
+#include <dirent.h>
+#include <errno.h>
+#include <unistd.h>
+#include "crossplatform.h"
+#define _getcwd getcwd
+
+// Case-insensitivity on linux (from https://github.com/OneSadCookie/fcaseopen)
+void mychdir(char const *path)
+{
+ char *r = (char*)alloca(strlen(path) + 2);
+ if (casepath(path, r))
+ {
+ chdir(r);
+ }
+ else
+ {
+ errno = ENOENT;
+ }
+}
+#else
+#define mychdir chdir
+#endif
+
/* Force file to open as binary but remember if it was text mode */
static int
myfopen(const char *filename, const char *mode)
@@ -45,7 +72,31 @@ found:
mode++;
*p++ = 'b';
*p = '\0';
- myfiles[fd].file = fopen(filename, realmode);
+
+#if !defined(_WIN32)
+ char *newPath = strdup(filename);
+ // Normally casepath() fixes backslashes, but if the mode is sth other than r/rb it will create new file with backslashes on linux, so fix backslashes here
+ char *nextBs;
+ while(nextBs = strstr(newPath, "\\")){
+ *nextBs = '/';
+ }
+#else
+ const char *newPath = filename;
+#endif
+
+ myfiles[fd].file = fopen(newPath, realmode);
+// Be case-insensitive on linux (from https://github.com/OneSadCookie/fcaseopen/)
+#if !defined(_WIN32)
+ if (!myfiles[fd].file) {
+ char *r = (char*)alloca(strlen(newPath) + 2);
+ if (casepath(newPath, r))
+ {
+ myfiles[fd].file = fopen(r, realmode);
+ }
+ }
+
+ free(newPath);
+#endif
if(myfiles[fd].file == nil)
return 0;
return fd;
@@ -191,7 +242,7 @@ CFileMgr::ChangeDir(const char *dir)
if(dir[strlen(dir)-1] != '\\')
strcat(ms_dirName, "\\");
}
- chdir(ms_dirName);
+ mychdir(ms_dirName);
}
void
@@ -204,14 +255,14 @@ CFileMgr::SetDir(const char *dir)
if(dir[strlen(dir)-1] != '\\')
strcat(ms_dirName, "\\");
}
- chdir(ms_dirName);
+ mychdir(ms_dirName);
}
void
CFileMgr::SetDirMyDocuments(void)
{
SetDir(""); // better start at the root if user directory is relative
- chdir(_psGetUserFilesFolder());
+ mychdir(_psGetUserFilesFolder());
}
int
diff --git a/src/core/Fire.cpp b/src/core/Fire.cpp
index 65b6deb2..933c73da 100644
--- a/src/core/Fire.cpp
+++ b/src/core/Fire.cpp
@@ -128,7 +128,7 @@ CFire::ProcessFire(void)
lightpos.z = m_vecPos.z + 5.0f;
if (!m_pEntity) {
- CShadows::StoreStaticShadow((uint32)this, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &lightpos,
+ CShadows::StoreStaticShadow((uintptr)this, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &lightpos,
7.0f, 0.0f, 0.0f, -7.0f,
255, // this is 0 on PC which results in no shadow
nRandNumber / 2, nRandNumber / 2, 0,
@@ -199,7 +199,7 @@ CFireManager::StartFire(CEntity *entityOnFire, CEntity *fleeFrom, float strength
{
CPed *ped = (CPed *)entityOnFire;
CVehicle *veh = (CVehicle *)entityOnFire;
-
+
if (entityOnFire->IsPed()) {
if (ped->m_pFire)
return nil;
@@ -212,7 +212,7 @@ CFireManager::StartFire(CEntity *entityOnFire, CEntity *fleeFrom, float strength
return nil;
}
CFire *fire = GetNextFreeFire();
-
+
if (fire) {
if (entityOnFire->IsPed()) {
ped->m_pFire = fire;
@@ -243,7 +243,7 @@ CFireManager::StartFire(CEntity *entityOnFire, CEntity *fleeFrom, float strength
veh->m_pCarFire = fire;
if (fleeFrom) {
CEventList::RegisterEvent(EVENT_CAR_SET_ON_FIRE, EVENT_ENTITY_VEHICLE,
- entityOnFire, (CPed *)fleeFrom, 10000);
+ entityOnFire, (CPed *)fleeFrom, 10000);
}
}
}
diff --git a/src/core/Frontend.cpp b/src/core/Frontend.cpp
index 827e2ca7..f0d75d12 100644
--- a/src/core/Frontend.cpp
+++ b/src/core/Frontend.cpp
@@ -6,6 +6,7 @@
#define WITHWINDOWS
#include "common.h"
#include "crossplatform.h"
+#include "platform.h"
#include "Frontend.h"
#include "Font.h"
#include "Pad.h"
@@ -900,6 +901,7 @@ CMenuManager::Draw()
float smallestSliderBar = lineHeight * 0.1f;
bool foundTheHoveringItem = false;
wchar unicodeTemp[64];
+ char asciiTemp[32];
#ifdef MENU_MAP
if (m_nCurrScreen == MENUPAGE_MAP) {
@@ -1054,15 +1056,18 @@ CMenuManager::Draw()
#else
switch (m_PrefsUseWideScreen) {
case AR_AUTO:
- rightText = (wchar*)L"AUTO";
+ sprintf(asciiTemp, "AUTO");
break;
case AR_4_3:
- rightText = (wchar*)L"4:3";
+ sprintf(asciiTemp, "4:3");
break;
case AR_16_9:
- rightText = (wchar*)L"16:9";
+ sprintf(asciiTemp, "16:9");
break;
}
+
+ AsciiToUnicode(asciiTemp, unicodeTemp);
+ rightText = unicodeTemp;
#endif
break;
case MENUACTION_RADIO:
@@ -1102,13 +1107,12 @@ CMenuManager::Draw()
break;
#ifdef IMPROVED_VIDEOMODE
case MENUACTION_SCREENMODE:
- char mode[32];
if (m_nSelectedScreenMode == 0)
- sprintf(mode, "FULLSCREEN");
+ sprintf(asciiTemp, "FULLSCREEN");
else
- sprintf(mode, "WINDOWED");
+ sprintf(asciiTemp, "WINDOWED");
- AsciiToUnicode(mode, unicodeTemp);
+ AsciiToUnicode(asciiTemp, unicodeTemp);
rightText = unicodeTemp;
break;
#endif
@@ -4794,6 +4798,21 @@ CMenuManager::ProcessButtonPresses(void)
DMAudio.PlayFrontEndTrack(m_PrefsRadioStation, 1);
OutputDebugString("FRONTEND RADIO STATION CHANGED");
break;
+#ifdef ASPECT_RATIO_SCALE
+ case MENUACTION_WIDESCREEN:
+ if (changeValueBy > 0) {
+ m_PrefsUseWideScreen++;
+ if (m_PrefsUseWideScreen > 2)
+ m_PrefsUseWideScreen = 2;
+ } else {
+ m_PrefsUseWideScreen--;
+ if (m_PrefsUseWideScreen < 0)
+ m_PrefsUseWideScreen = 0;
+ }
+ DMAudio.PlayFrontEndSound(SOUND_FRONTEND_MENU_SUCCESS, 0);
+ SaveSettings();
+ break;
+#endif
case MENUACTION_SCREENRES:
if (m_bGameNotLoaded) {
RwChar** videoMods = _psGetVideoModeList();
@@ -4903,17 +4922,13 @@ CMenuManager::ProcessOnOffMenuOptions()
DMAudio.PlayFrontEndSound(SOUND_FRONTEND_MENU_SUCCESS, 0);
SaveSettings();
break;
- case MENUACTION_WIDESCREEN:
#ifndef ASPECT_RATIO_SCALE
+ case MENUACTION_WIDESCREEN:
m_PrefsUseWideScreen = !m_PrefsUseWideScreen;
-#else
- m_PrefsUseWideScreen++;
- if (m_PrefsUseWideScreen > 2)
- m_PrefsUseWideScreen = 0;
-#endif
DMAudio.PlayFrontEndSound(SOUND_FRONTEND_MENU_SUCCESS, 0);
SaveSettings();
break;
+#endif
case MENUACTION_SETDBGFLAG:
CTheScripts::InvertDebugFlag();
DMAudio.PlayFrontEndSound(SOUND_FRONTEND_MENU_SUCCESS, 0);
diff --git a/src/core/Frontend.h b/src/core/Frontend.h
index e496f9c0..65c4e178 100644
--- a/src/core/Frontend.h
+++ b/src/core/Frontend.h
@@ -662,4 +662,3 @@ VALIDATE_SIZE(CMenuManager, 0x564);
#endif
extern CMenuManager FrontEndMenuManager;
-extern unsigned long _dwOperatingSystemVersion; \ No newline at end of file
diff --git a/src/core/Game.cpp b/src/core/Game.cpp
index c50471f1..33afc956 100644
--- a/src/core/Game.cpp
+++ b/src/core/Game.cpp
@@ -2,7 +2,7 @@
#pragma warning( disable : 4005)
#pragma warning( pop )
#include "common.h"
-#include "crossplatform.h"
+#include "platform.h"
#include "Game.h"
#include "main.h"
diff --git a/src/core/Streaming.cpp b/src/core/Streaming.cpp
index e430f758..a2e6048b 100644
--- a/src/core/Streaming.cpp
+++ b/src/core/Streaming.cpp
@@ -1465,7 +1465,7 @@ CStreaming::GetCdImageOffset(int32 lastPosn)
int dist, mindist;
img = -1;
- mindist = INT_MAX;
+ mindist = INT32_MAX;
offset = ms_imageOffsets[ms_lastImageRead];
if(lastPosn <= offset || lastPosn > offset + ms_imageSize){
// last read position is not in last image
@@ -1513,8 +1513,8 @@ CStreaming::GetNextFileOnCd(int32 lastPosn, bool priority)
streamIdFirst = -1;
streamIdNext = -1;
- posnFirst = UINT_MAX;
- posnNext = UINT_MAX;
+ posnFirst = UINT32_MAX;
+ posnNext = UINT32_MAX;
for(si = ms_startRequestedList.m_next; si != &ms_endRequestedList; si = next){
next = si->m_next;
@@ -1834,7 +1834,7 @@ CStreaming::LoadAllRequestedModels(bool priority)
status = CdStreamRead(0, ms_pStreamingBuffer[0], imgOffset+posn, size);
while(CdStreamSync(0) || status == STREAM_NONE);
ms_aInfoForModel[streamId].m_loadState = STREAMSTATE_READING;
-
+
MakeSpaceFor(size * CDSTREAM_SECTOR_SIZE);
ConvertBufferToObject(ms_pStreamingBuffer[0], streamId);
if(ms_aInfoForModel[streamId].m_loadState == STREAMSTATE_STARTED)
diff --git a/src/core/Timer.cpp b/src/core/Timer.cpp
index aca7c1dc..ed5580fd 100644
--- a/src/core/Timer.cpp
+++ b/src/core/Timer.cpp
@@ -1,5 +1,6 @@
#define WITHWINDOWS
#include "common.h"
+#include "crossplatform.h"
#include "DMAudio.h"
#include "Record.h"
@@ -16,15 +17,19 @@ float CTimer::ms_fTimeStepNonClipped;
bool CTimer::m_UserPause;
bool CTimer::m_CodePause;
-uint32 oldPcTimer;
-
-uint32 suspendPcTimer;
-
uint32 _nCyclesPerMS = 1;
+#ifdef _WIN32
LARGE_INTEGER _oldPerfCounter;
-
LARGE_INTEGER perfSuspendCounter;
+#define RsTimerType uint32
+#else
+#define RsTimerType double
+#endif
+
+RsTimerType oldPcTimer;
+
+RsTimerType suspendPcTimer;
uint32 suspendDepth;
@@ -45,6 +50,7 @@ void CTimer::Initialise(void)
m_snPreviousTimeInMilliseconds = 0;
m_snTimeInMilliseconds = 1;
+#ifdef _WIN32
LARGE_INTEGER perfFreq;
if ( QueryPerformanceFrequency(&perfFreq) )
{
@@ -53,6 +59,7 @@ void CTimer::Initialise(void)
QueryPerformanceCounter(&_oldPerfCounter);
}
else
+#endif
{
OutputDebugString("Performance counter not available, using millesecond timer\n");
_nCyclesPerMS = 0;
@@ -77,6 +84,7 @@ void CTimer::Update(void)
{
m_snPreviousTimeInMilliseconds = m_snTimeInMilliseconds;
+#ifdef _WIN32
if ( (double)_nCyclesPerMS != 0.0 )
{
LARGE_INTEGER pc;
@@ -106,10 +114,11 @@ void CTimer::Update(void)
}
}
else
+#endif
{
- uint32 timer = RsTimer();
+ RsTimerType timer = RsTimer();
- uint32 updInMs = timer - oldPcTimer;
+ RsTimerType updInMs = timer - oldPcTimer;
// We need that real frame time to fix transparent menu bug.
#ifndef FIX_BUGS
@@ -158,9 +167,11 @@ void CTimer::Suspend(void)
if ( ++suspendDepth > 1 )
return;
+#ifdef _WIN32
if ( (double)_nCyclesPerMS != 0.0 )
QueryPerformanceCounter(&perfSuspendCounter);
else
+#endif
suspendPcTimer = RsTimer();
}
@@ -169,6 +180,7 @@ void CTimer::Resume(void)
if ( --suspendDepth != 0 )
return;
+#ifdef _WIN32
if ( (double)_nCyclesPerMS != 0.0 )
{
LARGE_INTEGER pc;
@@ -177,19 +189,23 @@ void CTimer::Resume(void)
_oldPerfCounter.LowPart += pc.LowPart - perfSuspendCounter.LowPart;
}
else
+#endif
oldPcTimer += RsTimer() - suspendPcTimer;
}
uint32 CTimer::GetCyclesPerMillisecond(void)
{
+#ifdef _WIN32
if (_nCyclesPerMS != 0)
return _nCyclesPerMS;
else
+#endif
return 1;
}
uint32 CTimer::GetCurrentTimeInCycles(void)
{
+#ifdef _WIN32
if ( _nCyclesPerMS != 0 )
{
LARGE_INTEGER pc;
@@ -197,6 +213,7 @@ uint32 CTimer::GetCurrentTimeInCycles(void)
return (pc.LowPart - _oldPerfCounter.LowPart); // & 0x7FFFFFFF; pointless
}
else
+#endif
return RsTimer() - oldPcTimer;
}
diff --git a/src/core/ZoneCull.cpp b/src/core/ZoneCull.cpp
index 6dcd0f18..c376e11f 100644
--- a/src/core/ZoneCull.cpp
+++ b/src/core/ZoneCull.cpp
@@ -533,7 +533,8 @@ CCullZone::IsEntityCloseEnoughToZone(CEntity *entity, bool checkLevel)
if (lodDist > distToZone) return true;
if (!checkLevel) return false;
- return CTheZones::GetLevelFromPosition(&pos) == CTheZones::GetLevelFromPosition(&CVector(minx, miny, minz));
+ CVector tempPos(minx, miny, minz);
+ return CTheZones::GetLevelFromPosition(&pos) == CTheZones::GetLevelFromPosition(&tempPos);
}
bool
@@ -560,4 +561,4 @@ CCullZones::DoWeHaveMoreThanXOccurencesOfSet(int32 count, uint16 *set)
}
}
return false;
-} \ No newline at end of file
+}
diff --git a/src/core/Zones.cpp b/src/core/Zones.cpp
index 22c0735a..5b7519dc 100644
--- a/src/core/Zones.cpp
+++ b/src/core/Zones.cpp
@@ -703,9 +703,9 @@ CTheZones::LoadAllZones(uint8 *buffer, uint32 size)
for(i = 0; i < ARRAY_SIZE(ZoneArray); i++){
ZoneArray[i] = ReadSaveBuf<CZone>(buffer);
- ZoneArray[i].child = GetPointerForZoneIndex((int32)ZoneArray[i].child);
- ZoneArray[i].parent = GetPointerForZoneIndex((int32)ZoneArray[i].parent);
- ZoneArray[i].next = GetPointerForZoneIndex((int32)ZoneArray[i].next);
+ ZoneArray[i].child = GetPointerForZoneIndex((uintptr)ZoneArray[i].child);
+ ZoneArray[i].parent = GetPointerForZoneIndex((uintptr)ZoneArray[i].parent);
+ ZoneArray[i].next = GetPointerForZoneIndex((uintptr)ZoneArray[i].next);
}
for(i = 0; i < ARRAY_SIZE(ZoneInfoArray); i++)
@@ -722,9 +722,9 @@ CTheZones::LoadAllZones(uint8 *buffer, uint32 size)
meant for a different array, but the game doesn't brake
if save data stored is -1.
*/
- MapZoneArray[i].child = GetPointerForZoneIndex((int32)MapZoneArray[i].child);
- MapZoneArray[i].parent = GetPointerForZoneIndex((int32)MapZoneArray[i].parent);
- MapZoneArray[i].next = GetPointerForZoneIndex((int32)MapZoneArray[i].next);
+ MapZoneArray[i].child = GetPointerForZoneIndex((uintptr)MapZoneArray[i].child);
+ MapZoneArray[i].parent = GetPointerForZoneIndex((uintptr)MapZoneArray[i].parent);
+ MapZoneArray[i].next = GetPointerForZoneIndex((uintptr)MapZoneArray[i].next);
assert(MapZoneArray[i].child == nil);
assert(MapZoneArray[i].parent == nil);
assert(MapZoneArray[i].next == nil);
diff --git a/src/core/config.h b/src/core/config.h
index ae30b539..d9f892a6 100644
--- a/src/core/config.h
+++ b/src/core/config.h
@@ -194,19 +194,22 @@ enum Config {
#define FIX_BUGS // fixes bugs that we've came across during reversing, TODO: use this more
#define TOGGLEABLE_BETA_FEATURES // toggleable from debug menu. not too many things
#define MORE_LANGUAGES // Add more translations to the game
-#define DEFAULT_NATIVE_RESOLUTION // Set default video mode to your native resolution (fixes Windows 10 launch)
+#define DEFAULT_NATIVE_RESOLUTION // Set default video mode to your native resolution (fixes Windows 10 launch)
#define USE_TXD_CDIMAGE // generate and load textures from txd.img
#define IMPROVED_VIDEOMODE // save and load videomode parameters instead of a magic number
//#define USE_TEXTURE_POOL
-//#define AUDIO_OAL
+#ifdef _WIN32
#define AUDIO_MSS
+#else
+#define AUDIO_OAL
+#endif
// Particle
//#define PC_PARTICLE
//#define PS2_ALTERNATIVE_CARSPLASH // unused on PS2
// Pad
-#ifndef RW_GL3
+#if !defined(RW_GL3) && defined(_WIN32)
#define XINPUT
#endif
#define DETECT_PAD_INPUT_SWITCH // Adds automatic switch of pad related stuff between controller and kb/m
@@ -224,7 +227,7 @@ enum Config {
#define SCROLLABLE_STATS_PAGE // only draggable by mouse atm
#define TRIANGLE_BACK_BUTTON
// #define CIRCLE_BACK_BUTTON
-#define HUD_ENHANCEMENTS // Adjusts some aspects to make the HUD look/behave a little bit better.
+#define HUD_ENHANCEMENTS // Adjusts some aspects to make the HUD look/behave a little bit better.
#define BETA_SLIDING_TEXT
// Script
diff --git a/src/core/main.cpp b/src/core/main.cpp
index 37a5673f..d6af0b2a 100644
--- a/src/core/main.cpp
+++ b/src/core/main.cpp
@@ -1773,6 +1773,8 @@ void GameInit()
}
}
+// Not used anyway. PS2 main() port
+#ifdef _WIN32
int
main(int argc, char *argv[])
{
@@ -1844,3 +1846,4 @@ main(int argc, char *argv[])
return 0;
}
+#endif
diff --git a/src/core/patcher.cpp b/src/core/patcher.cpp
index e5242e9d..83e06886 100644
--- a/src/core/patcher.cpp
+++ b/src/core/patcher.cpp
@@ -24,7 +24,7 @@ StaticPatcher::Apply()
}
ms_head = nil;
}
-
+#ifdef _WIN32
std::vector<uint32> usedAddresses;
static DWORD protect[2];
@@ -75,4 +75,20 @@ InjectHook_internal(uint32 address, uint32 hook, int type)
VirtualProtect((void*)(address + 1), 4, protect[0], &protect[1]);
else
VirtualProtect((void*)address, 5, protect[0], &protect[1]);
-} \ No newline at end of file
+}
+#else
+void
+Protect_internal(uint32 address, uint32 size)
+{
+}
+
+void
+Unprotect_internal(void)
+{
+}
+
+void
+InjectHook_internal(uint32 address, uint32 hook, int type)
+{
+}
+#endif
diff --git a/src/core/re3.cpp b/src/core/re3.cpp
index 0ab32999..9bc6400c 100644
--- a/src/core/re3.cpp
+++ b/src/core/re3.cpp
@@ -1,7 +1,7 @@
-#include <direct.h>
#include <csignal>
#define WITHWINDOWS
#include "common.h"
+#include "crossplatform.h"
#include "patcher.h"
#include "Renderer.h"
#include "Credits.h"
@@ -28,6 +28,11 @@
#include "debugmenu.h"
#include "Frontend.h"
+#ifndef _WIN32
+#include "assert.h"
+#include <stdarg.h>
+#endif
+
#include <list>
#ifdef RWLIBS
@@ -36,7 +41,7 @@ extern "C" int vsprintf(char* const _Buffer, char const* const _Format, va_list
#ifdef USE_PS2_RAND
-unsigned __int64 myrand_seed = 1;
+unsigned long long myrand_seed = 1;
#else
unsigned long int myrand_seed = 1;
#endif
@@ -201,13 +206,22 @@ static const char *carnames[] = {
"yankee", "escape", "borgnine", "toyz", "ghost",
};
-static std::list<CTweakVar *> TweakVarsList;
+static CTweakVar** TweakVarsList;
+static int TweakVarsListSize = -1;
static bool bAddTweakVarsNow = false;
static const char *pTweakVarsDefaultPath = NULL;
void CTweakVars::Add(CTweakVar *var)
{
- TweakVarsList.push_back(var);
+ if(TweakVarsListSize == -1) {
+ TweakVarsList = (CTweakVar**)malloc(64 * sizeof(CTweakVar*));
+ TweakVarsListSize = 0;
+ }
+ if(TweakVarsListSize > 63)
+ TweakVarsList = (CTweakVar**) realloc(TweakVarsList, (TweakVarsListSize + 1) * sizeof(var));
+
+ TweakVarsList[TweakVarsListSize++] = var;
+// TweakVarsList.push_back(var);
if ( bAddTweakVarsNow )
var->AddDBG(pTweakVarsDefaultPath);
@@ -217,8 +231,8 @@ void CTweakVars::AddDBG(const char *path)
{
pTweakVarsDefaultPath = path;
- for(auto i = TweakVarsList.begin(); i != TweakVarsList.end(); ++i)
- (*i)->AddDBG(pTweakVarsDefaultPath);
+ for(int i = 0; i < TweakVarsListSize; ++i)
+ TweakVarsList[i]->AddDBG(pTweakVarsDefaultPath);
bAddTweakVarsNow = true;
}
@@ -392,6 +406,7 @@ static char re3_buff[re3_buffsize];
void re3_assert(const char *expr, const char *filename, unsigned int lineno, const char *func)
{
+#ifdef _WIN32
int nCode;
strcpy_s(re3_buff, re3_buffsize, "Assertion failed!" );
@@ -436,13 +451,22 @@ void re3_assert(const char *expr, const char *filename, unsigned int lineno, con
return;
abort();
+#else
+ // TODO
+ printf("\nRE3 ASSERT FAILED\n\tFile: %s\n\tLine: %d\n\tFunction: %s\n\tExpression: %s\n",filename,lineno,func,expr);
+ assert(false);
+#endif
}
void re3_debug(const char *format, ...)
{
va_list va;
va_start(va, format);
+#ifdef _WIN32
vsprintf_s(re3_buff, re3_buffsize, format, va);
+#else
+ vsprintf(re3_buff, format, va);
+#endif
va_end(va);
printf("%s", re3_buff);
@@ -454,18 +478,26 @@ void re3_trace(const char *filename, unsigned int lineno, const char *func, cons
char buff[re3_buffsize *2];
va_list va;
va_start(va, format);
+#ifdef _WIN32
vsprintf_s(re3_buff, re3_buffsize, format, va);
va_end(va);
sprintf_s(buff, re3_buffsize * 2, "[%s.%s:%d]: %s", filename, func, lineno, re3_buff);
+#else
+ vsprintf(re3_buff, format, va);
+ va_end(va);
- OutputDebugStringA(buff);
+ sprintf(buff, "[%s.%s:%d]: %s", filename, func, lineno, re3_buff);
+#endif
+
+ OutputDebugString(buff);
}
void re3_usererror(const char *format, ...)
{
va_list va;
va_start(va, format);
+#ifdef _WIN32
vsprintf_s(re3_buff, re3_buffsize, format, va);
va_end(va);
@@ -474,6 +506,11 @@ void re3_usererror(const char *format, ...)
raise(SIGABRT);
_exit(3);
+#else
+ vsprintf(re3_buff, format, va);
+ printf("\nRE3 Error!\n\t%s\n",re3_buff);
+ assert(false);
+#endif
}
#ifdef VALIDATE_SAVE_SIZE
diff --git a/src/extras/debugmenu.cpp b/src/extras/debugmenu.cpp
index a31426bb..f6b6eeb8 100644
--- a/src/extras/debugmenu.cpp
+++ b/src/extras/debugmenu.cpp
@@ -9,10 +9,11 @@
#include "debugmenu.h"
#include <new>
+#ifdef _WIN32
#define snprintf _snprintf
#define strdup _strdup
-
+#endif
// Font stuff
diff --git a/src/fakerw/fake.cpp b/src/fakerw/fake.cpp
index f1531490..50d12b2f 100644
--- a/src/fakerw/fake.cpp
+++ b/src/fakerw/fake.cpp
@@ -7,6 +7,9 @@
#include <rpskin.h>
#include <assert.h>
#include <string.h>
+#ifndef _WIN32
+#include "crossplatform.h"
+#endif
using namespace rw;
@@ -371,8 +374,24 @@ RwStream *RwStreamOpen(RwStreamType type, RwStreamAccessType accessType, const v
StreamFile fakefile;
file = rwNewT(StreamFile, 1, 0);
memcpy(file, &fakefile, sizeof(StreamFile));
+#ifndef _WIN32
+ // Be case-insensitive and fix backslashes (from https://github.com/OneSadCookie/fcaseopen/)
+ FILE* first = fopen((char*)pData, "r");
+ char *r;
+ if (!first) {
+ r = (char*)alloca(strlen((char*)pData) + 2);
+ // Use default path(and pass error handling to librw) if we can't find any match
+ if (!casepath((char*)pData, r))
+ r = (char*)pData;
+ } else
+ fclose(first);
+
+ if(file->open((char*)r, mode))
+ return file;
+#else
if(file->open((char*)pData, mode))
return file;
+#endif
rwFree(file);
return nil;
}
diff --git a/src/modelinfo/VehicleModelInfo.cpp b/src/modelinfo/VehicleModelInfo.cpp
index d64146d7..74285c19 100644
--- a/src/modelinfo/VehicleModelInfo.cpp
+++ b/src/modelinfo/VehicleModelInfo.cpp
@@ -262,7 +262,7 @@ CVehicleModelInfo::HideDamagedAtomicCB(RpAtomic *atomic, void *data)
RpAtomic*
CVehicleModelInfo::HideAllComponentsAtomicCB(RpAtomic *atomic, void *data)
{
- if(CVisibilityPlugins::GetAtomicId(atomic) & (int)data)
+ if(CVisibilityPlugins::GetAtomicId(atomic) & (uintptr)data)
RpAtomicSetFlags(atomic, 0);
else
RpAtomicSetFlags(atomic, rpATOMICRENDER);
@@ -415,7 +415,7 @@ CVehicleModelInfo::SetAtomicFlagCB(RwObject *object, void *data)
{
RpAtomic *atomic = (RpAtomic*)object;
assert(RwObjectGetType(object) == rpATOMIC);
- CVisibilityPlugins::SetAtomicFlag(atomic, (int)data);
+ CVisibilityPlugins::SetAtomicFlag(atomic, (uintptr)data);
return object;
}
@@ -424,7 +424,7 @@ CVehicleModelInfo::ClearAtomicFlagCB(RwObject *object, void *data)
{
RpAtomic *atomic = (RpAtomic*)object;
assert(RwObjectGetType(object) == rpATOMIC);
- CVisibilityPlugins::ClearAtomicFlag(atomic, (int)data);
+ CVisibilityPlugins::ClearAtomicFlag(atomic, (uintptr)data);
return object;
}
diff --git a/src/peds/Ped.cpp b/src/peds/Ped.cpp
index 78f4b586..2bd5c152 100644
--- a/src/peds/Ped.cpp
+++ b/src/peds/Ped.cpp
@@ -2854,7 +2854,7 @@ CPed::SetObjective(eObjective newObj, void *entity)
case OBJECTIVE_WAIT_IN_CAR_THEN_GETOUT:
// In this special case, entity parameter isn't CEntity, but int.
- SetObjectiveTimer((int)entity);
+ SetObjectiveTimer((uintptr)entity);
break;
case OBJECTIVE_KILL_CHAR_ON_FOOT:
case OBJECTIVE_KILL_CHAR_ANY_MEANS:
@@ -3347,7 +3347,7 @@ CPed::MakePhonecall(void)
if (!IsPlayer() && CTimer::GetTimeInMilliseconds() > m_phoneTalkTimer - 7000 && bRunningToPhone) {
FindPlayerPed()->m_pWanted->RegisterCrime_Immediately(m_crimeToReportOnPhone, GetPosition(),
- (m_crimeToReportOnPhone == CRIME_POSSESSION_GUN ? (int)m_threatEntity : (int)((CPed*)m_pEventEntity)->m_threatEntity), false);
+ (m_crimeToReportOnPhone == CRIME_POSSESSION_GUN ? (uintptr)m_threatEntity : (uintptr)((CPed*)m_pEventEntity)->m_threatEntity), false);
bRunningToPhone = false;
}
#endif
@@ -4555,7 +4555,7 @@ CPed::SetPointGunAt(CEntity *to)
SetLookFlag(to, true);
SetAimFlag(to);
#ifdef VC_PED_PORTS
- SetLookTimer(INT_MAX);
+ SetLookTimer(INT32_MAX);
#endif
}
@@ -4794,8 +4794,8 @@ CPed::SetEvasiveDive(CPhysical *reason, uint8 onlyRandomJump)
if (reason->IsVehicle() && m_nPedType == PEDTYPE_COP) {
if (veh->pDriver && veh->pDriver->IsPlayer()) {
CWanted *wanted = FindPlayerPed()->m_pWanted;
- wanted->RegisterCrime_Immediately(CRIME_RECKLESS_DRIVING, GetPosition(), (int)this, false);
- wanted->RegisterCrime_Immediately(CRIME_SPEEDING, GetPosition(), (int)this, false);
+ wanted->RegisterCrime_Immediately(CRIME_RECKLESS_DRIVING, GetPosition(), (uintptr)this, false);
+ wanted->RegisterCrime_Immediately(CRIME_SPEEDING, GetPosition(), (uintptr)this, false);
}
}
}
diff --git a/src/peds/PlayerPed.cpp b/src/peds/PlayerPed.cpp
index c6c4824b..92e3d358 100644
--- a/src/peds/PlayerPed.cpp
+++ b/src/peds/PlayerPed.cpp
@@ -1077,7 +1077,7 @@ CPlayerPed::ProcessPlayerWeapon(CPad *padUsed)
SetLookFlag(limitedCam, true);
SetAimFlag(limitedCam);
#ifdef VC_PED_PORTS
- SetLookTimer(INT_MAX); // removing this makes head move for real, but I experinced some bugs.
+ SetLookTimer(INT32_MAX); // removing this makes head move for real, but I experinced some bugs.
#endif
} else {
m_fRotationDest = limitedCam;
diff --git a/src/render/Console.cpp b/src/render/Console.cpp
index 5ae5d763..8ea5b7a3 100644
--- a/src/render/Console.cpp
+++ b/src/render/Console.cpp
@@ -17,7 +17,7 @@ CConsole::AddLine(char *s, uint8 r, uint8 g, uint8 b)
char tempstr[MAX_STR_LEN+1];
while (strlen(s) > MAX_STR_LEN) {
- strncpy_s(tempstr, s, MAX_STR_LEN);
+ strncpy(tempstr, s, MAX_STR_LEN);
tempstr[MAX_STR_LEN-1] = '\0';
s += MAX_STR_LEN - 1;
AddOneLine(tempstr, r, g, b);
diff --git a/src/render/ParticleMgr.h b/src/render/ParticleMgr.h
index 42e3f132..0100bb65 100644
--- a/src/render/ParticleMgr.h
+++ b/src/render/ParticleMgr.h
@@ -4,7 +4,7 @@
class CParticle;
-enum
+enum
{
ZCHECK_FIRST = BIT(0),
ZCHECK_STEP = BIT(1),
@@ -60,14 +60,12 @@ struct tParticleSystemData
uint8 m_InitialColorVariation;
RwRGBA m_FadeDestinationColor;
uint32 m_ColorFadeTime;
-
+
RwRaster **m_ppRaster;
CParticle *m_pParticles;
};
-#ifdef CHECK_STRUCT_SIZES
VALIDATE_SIZE(tParticleSystemData, 0x88);
-#endif
class cParticleSystemMgr
{
@@ -121,14 +119,12 @@ public:
tParticleSystemData m_aParticles[MAX_PARTICLES];
cParticleSystemMgr();
-
+
void Initialise();
void LoadParticleData();
void RangeCheck(tParticleSystemData *pData) { }
};
-#ifdef CHECK_STRUCT_SIZES
VALIDATE_SIZE(cParticleSystemMgr, 0x2420);
-#endif
-extern cParticleSystemMgr mod_ParticleSystemManager; \ No newline at end of file
+extern cParticleSystemMgr mod_ParticleSystemManager;
diff --git a/src/render/PlayerSkin.cpp b/src/render/PlayerSkin.cpp
index 94af1fd1..d66f7ce4 100644
--- a/src/render/PlayerSkin.cpp
+++ b/src/render/PlayerSkin.cpp
@@ -123,7 +123,7 @@ void
CPlayerSkin::BeginFrontendSkinEdit(void)
{
LoadPlayerDff();
- RpClumpForAllAtomics(gpPlayerClump, CClumpModelInfo::SetAtomicRendererCB, CVisibilityPlugins::RenderPlayerCB);
+ RpClumpForAllAtomics(gpPlayerClump, CClumpModelInfo::SetAtomicRendererCB, (void*)CVisibilityPlugins::RenderPlayerCB);
CWorld::Players[0].LoadPlayerSkin();
gOldFov = CDraw::GetFOV();
CDraw::SetFOV(30.0f);
diff --git a/src/render/Shadows.cpp b/src/render/Shadows.cpp
index cefc1d9f..69f9dce0 100644
--- a/src/render/Shadows.cpp
+++ b/src/render/Shadows.cpp
@@ -645,7 +645,7 @@ CShadows::StoreShadowForPole(CEntity *pPole, float fOffsetX, float fOffsetY, flo
PolePos.x += -CTimeCycle::GetSunPosition().x * (fPoleHeight / 2);
PolePos.y += -CTimeCycle::GetSunPosition().y * (fPoleHeight / 2);
- StoreStaticShadow((uint32)pPole + nID + _TODOCONST(51), SHADOWTYPE_DARK, gpPostShadowTex, &PolePos,
+ StoreStaticShadow((uintptr)pPole + nID + _TODOCONST(51), SHADOWTYPE_DARK, gpPostShadowTex, &PolePos,
-CTimeCycle::GetSunPosition().x * (fPoleHeight / 2),
-CTimeCycle::GetSunPosition().y * (fPoleHeight / 2),
CTimeCycle::GetShadowSideX() * fPoleWidth,
@@ -1516,7 +1516,7 @@ CShadows::UpdatePermanentShadows(void)
// timePassed == aPermanentShadows[i].m_nLifeTime -> 0
float fMult = 1.0f - float(timePassed - (aPermanentShadows[i].m_nLifeTime * 3 / 4)) / (aPermanentShadows[i].m_nLifeTime / 4);
- StoreStaticShadow((uint32)&aPermanentShadows[i],
+ StoreStaticShadow((uintptr)&aPermanentShadows[i],
aPermanentShadows[i].m_nType,
aPermanentShadows[i].m_pTexture,
&aPermanentShadows[i].m_vecPos,
@@ -1533,7 +1533,7 @@ CShadows::UpdatePermanentShadows(void)
}
else
{
- StoreStaticShadow((uint32)&aPermanentShadows[i],
+ StoreStaticShadow((uintptr)&aPermanentShadows[i],
aPermanentShadows[i].m_nType,
aPermanentShadows[i].m_pTexture,
&aPermanentShadows[i].m_vecPos,
diff --git a/src/render/Shadows.h b/src/render/Shadows.h
index ef56d336..63aaaaf2 100644
--- a/src/render/Shadows.h
+++ b/src/render/Shadows.h
@@ -52,9 +52,7 @@ public:
{ }
};
-#ifdef CHECK_STRUCT_SIZES
VALIDATE_SIZE(CStoredShadow, 0x30);
-#endif
class CPolyBunch
{
@@ -69,9 +67,7 @@ public:
{ }
};
-#ifdef CHECK_STRUCT_SIZES
VALIDATE_SIZE(CPolyBunch, 0x6C);
-#endif
class CStaticShadow
{
@@ -93,16 +89,14 @@ public:
bool m_bRendered;
bool m_bTemp;
RwTexture *m_pTexture;
-
+
CStaticShadow()
{ }
void Free();
};
-#ifdef CHECK_STRUCT_SIZES
VALIDATE_SIZE(CStaticShadow, 0x40);
-#endif
class CPermanentShadow
{
@@ -120,7 +114,7 @@ public:
uint32 m_nTimeCreated;
uint32 m_nLifeTime;
RwTexture *m_pTexture;
-
+
CPermanentShadow()
{ }
};
@@ -168,7 +162,7 @@ public:
static void GeneratePolysForStaticShadow (int16 nStaticShadowID);
static void CastShadowSectorList (CPtrList &PtrList, float fStartX, float fStartY, float fEndX, float fEndY,
CVector *pPosn, float fFrontX, float fFrontY, float fSideX, float fSideY, int16 nIntensity, uint8 nRed, uint8 nGreen, uint8 nBlue, float fZDistance, float fScale, CPolyBunch **ppPolyBunch);
- static void CastShadowEntity (CEntity *pEntity, float fStartX, float fStartY, float fEndX, float fEndY,
+ static void CastShadowEntity (CEntity *pEntity, float fStartX, float fStartY, float fEndX, float fEndY,
CVector *pPosn, float fFrontX, float fFrontY, float fSideX, float fSideY, int16 nIntensity, uint8 nRed, uint8 nGreen, uint8 nBlue, float fZDistance, float fScale, CPolyBunch **ppPolyBunch);
static void UpdateStaticShadows (void);
static void UpdatePermanentShadows (void);
diff --git a/src/rw/RwHelper.cpp b/src/rw/RwHelper.cpp
index cb1d4ab5..5026e2c8 100644
--- a/src/rw/RwHelper.cpp
+++ b/src/rw/RwHelper.cpp
@@ -60,15 +60,15 @@ void *
RwMallocAlign(RwUInt32 size, RwUInt32 align)
{
void *mem = (void *)malloc(size + align);
-
+
ASSERT(mem != nil);
-
- void *addr = (void *)((((RwUInt32)mem) + align) & ~(align - 1));
-
+
+ void *addr = (void *)((((uintptr)mem) + align) & ~(align - 1));
+
ASSERT(addr != nil);
-
+
*(((void **)addr) - 1) = mem;
-
+
return addr;
}
@@ -76,11 +76,11 @@ void
RwFreeAlign(void *mem)
{
ASSERT(mem != nil);
-
+
void *addr = *(((void **)mem) - 1);
-
+
ASSERT(addr != nil);
-
+
free(addr);
}
@@ -381,7 +381,7 @@ CameraSize(RwCamera * camera, RwRect * rect,
RwEngineGetVideoModeInfo(&videoMode,
RwEngineGetCurrentVideoMode());
-
+
origSize.w = RwRasterGetWidth(RwCameraGetRaster(camera));
origSize.h = RwRasterGetHeight(RwCameraGetRaster(camera));
@@ -392,7 +392,7 @@ CameraSize(RwCamera * camera, RwRect * rect,
/* For full screen applications, resizing the camera just doesn't
* make sense, use the video mode size.
*/
-
+
r.x = r.y = 0;
r.w = videoMode.width;
r.h = videoMode.height;
@@ -414,11 +414,11 @@ CameraSize(RwCamera * camera, RwRect * rect,
{
RwRaster *raster;
RwRaster *zRaster;
-
+
/*
* Destroy rasters...
*/
-
+
raster = RwCameraGetRaster(camera);
if( raster )
{
@@ -430,14 +430,14 @@ CameraSize(RwCamera * camera, RwRect * rect,
{
RwRasterDestroy(zRaster);
}
-
+
/*
- * Create new rasters...
+ * Create new rasters...
*/
raster = RwRasterCreate(rect->w, rect->h, 0, rwRASTERTYPECAMERA);
zRaster = RwRasterCreate(rect->w, rect->h, 0, rwRASTERTYPEZBUFFER);
-
+
if( raster && zRaster )
{
RwCameraSetRaster(camera, raster);
@@ -460,8 +460,8 @@ CameraSize(RwCamera * camera, RwRect * rect,
rect->w = origSize.w;
rect->h = origSize.h;
- /*
- * Use default values...
+ /*
+ * Use default values...
*/
raster =
RwRasterCreate(rect->w, rect->h, 0, rwRASTERTYPECAMERA);
@@ -495,9 +495,9 @@ CameraSize(RwCamera * camera, RwRect * rect,
vw.y = viewWindow;
}
}
-
+
RwCameraSetViewWindow(camera, &vw);
-
+
RsGlobal.width = rect->w;
RsGlobal.height = rect->h;
}
diff --git a/src/rw/TexRead.cpp b/src/rw/TexRead.cpp
index 60945665..122ce655 100644
--- a/src/rw/TexRead.cpp
+++ b/src/rw/TexRead.cpp
@@ -3,6 +3,7 @@
#pragma warning( pop )
#include "common.h"
#include "crossplatform.h"
+#include "platform.h"
#include "Timer.h"
#ifdef GTA_PC
diff --git a/src/rw/VisibilityPlugins.cpp b/src/rw/VisibilityPlugins.cpp
index 46ec8ae2..d034391c 100644
--- a/src/rw/VisibilityPlugins.cpp
+++ b/src/rw/VisibilityPlugins.cpp
@@ -114,7 +114,7 @@ CVisibilityPlugins::SetRenderWareCamera(RwCamera *camera)
RpMaterial*
SetAlphaCB(RpMaterial *material, void *data)
{
- ((RwRGBA*)RpMaterialGetColor(material))->alpha = (uint8)(uint32)data;
+ ((RwRGBA*)RpMaterialGetColor(material))->alpha = (uint8)(uintptr)data;
return material;
}
@@ -837,15 +837,15 @@ void
CVisibilityPlugins::SetClumpModelInfo(RpClump *clump, CClumpModelInfo *modelInfo)
{
CVehicleModelInfo *vmi;
- SetFrameHierarchyId(RpClumpGetFrame(clump), (int32)modelInfo);
+ SetFrameHierarchyId(RpClumpGetFrame(clump), (uintptr)modelInfo);
// Unused
switch (modelInfo->GetModelType()) {
// ignore MLO
case MITYPE_VEHICLE:
vmi = (CVehicleModelInfo*)modelInfo;
- if(vmi->m_vehicleType == VEHICLE_TYPE_TRAIN ||
- vmi->m_vehicleType == VEHICLE_TYPE_HELI ||
+ if(vmi->m_vehicleType == VEHICLE_TYPE_TRAIN ||
+ vmi->m_vehicleType == VEHICLE_TYPE_HELI ||
vmi->m_vehicleType == VEHICLE_TYPE_PLANE)
CLUMPEXT(clump)->visibilityCB = VehicleVisibilityCB_BigVehicle;
else
diff --git a/src/save/GenericGameStorage.cpp b/src/save/GenericGameStorage.cpp
index bb074042..ba7bd216 100644
--- a/src/save/GenericGameStorage.cpp
+++ b/src/save/GenericGameStorage.cpp
@@ -1,5 +1,5 @@
+#define WITHWINDOWS
#include "common.h"
-#define USEALTERNATIVEWINFUNCS
#include "crossplatform.h"
#include "main.h"
diff --git a/src/save/PCSave.cpp b/src/save/PCSave.cpp
index d3aeee26..3dc80f73 100644
--- a/src/save/PCSave.cpp
+++ b/src/save/PCSave.cpp
@@ -1,5 +1,5 @@
+#define WITHWINDOWS
#include "common.h"
-#define USEALTERNATIVEWINFUNCS
#include "crossplatform.h"
#include "FileMgr.h"
diff --git a/src/skel/crossplatform.cpp b/src/skel/crossplatform.cpp
index f9464bb6..40f4f053 100644
--- a/src/skel/crossplatform.cpp
+++ b/src/skel/crossplatform.cpp
@@ -1,7 +1,9 @@
#include "common.h"
-#define USEALTERNATIVEWINFUNCS
#include "crossplatform.h"
+// Codes compatible with Windows and Linux
+#ifndef _WIN32
+
// For internal use
// wMilliseconds is not needed
void tmToSystemTime(const tm *tm, SYSTEMTIME *out) {
@@ -19,8 +21,10 @@ void GetLocalTime_CP(SYSTEMTIME *out) {
tm *localTm = localtime(&timestamp);
tmToSystemTime(localTm, out);
}
+#endif
-#if !defined _WIN32 || defined __MINGW32__
+// Compatible with Linux/POSIX and MinGW on Windows
+#ifndef _WIN32
HANDLE FindFirstFile(const char* pathname, WIN32_FIND_DATA* firstfile) {
char newpathname[32];
strncpy(newpathname, pathname, 32);
@@ -34,7 +38,7 @@ HANDLE FindFirstFile(const char* pathname, WIN32_FIND_DATA* firstfile) {
strncpy(firstfile->extension, "", sizeof(firstfile->extension));
HANDLE d;
- if ((d = opendir(path)) == NULL || !FindNextFile(d, firstfile))
+ if ((d = (HANDLE)opendir(path)) == NULL || !FindNextFile(d, firstfile))
return NULL;
return d;
@@ -45,7 +49,7 @@ bool FindNextFile(HANDLE d, WIN32_FIND_DATA* finddata) {
static struct stat fileStats;
static char path[PATH_MAX], relativepath[NAME_MAX + sizeof(finddata->folder) + 1];
int extensionLen = strlen(finddata->extension);
- while ((file = readdir(d)) != NULL) {
+ while ((file = readdir((DIR*)d)) != NULL) {
// We only want "DT_REG"ular Files, but reportedly some FS and OSes gives DT_UNKNOWN as type.
if ((file->d_type == DT_UNKNOWN || file->d_type == DT_REG) &&
@@ -78,4 +82,120 @@ void FileTimeToSystemTime(time_t* writeTime, SYSTEMTIME* out) {
tm *ptm = gmtime(writeTime);
tmToSystemTime(ptm, out);
}
-#endif \ No newline at end of file
+#endif
+
+// Funcs/features from Windows that we need on other platforms
+#ifndef _WIN32
+char *strupr(char *s) {
+ char* tmp = s;
+
+ for (;*tmp;++tmp) {
+ *tmp = toupper((unsigned char) *tmp);
+ }
+
+ return s;
+}
+char *strlwr(char *s) {
+ char* tmp = s;
+
+ for (;*tmp;++tmp) {
+ *tmp = tolower((unsigned char) *tmp);
+ }
+
+ return s;
+}
+
+char *trim(char *s) {
+ char *ptr;
+ if (!s)
+ return NULL; // handle NULL string
+ if (!*s)
+ return s; // handle empty string
+ for (ptr = s + strlen(s) - 1; (ptr >= s) && isspace(*ptr); --ptr);
+ ptr[1] = '\0';
+ return s;
+}
+
+// Case-insensitivity on linux (from https://github.com/OneSadCookie/fcaseopen)
+// r must have strlen(path) + 2 bytes
+int casepath(char const *path, char *r)
+{
+ size_t l = strlen(path);
+ char *p = (char*)alloca(l + 1);
+ strcpy(p, path);
+
+ // my addon: change \'s with /
+ char *nextBs;
+ while(nextBs = strstr(p, "\\")){
+ *nextBs = '/';
+ }
+
+ // my addon: linux doesn't handle filenames with spaces at the end nicely
+ p = trim(p);
+
+ size_t rl = 0;
+
+ DIR *d;
+ if (p[0] == '/')
+ {
+ d = opendir("/");
+ p = p + 1;
+ }
+ else
+ {
+ d = opendir(".");
+ r[0] = '.';
+ r[1] = 0;
+ rl = 1;
+ }
+
+ int last = 0;
+ char *c = strsep(&p, "/");
+ while (c)
+ {
+ if (!d)
+ {
+ return 0;
+ }
+
+ if (last)
+ {
+ closedir(d);
+ return 0;
+ }
+
+ r[rl] = '/';
+ rl += 1;
+ r[rl] = 0;
+
+ struct dirent *e = readdir(d);
+ while (e)
+ {
+ if (strcasecmp(c, e->d_name) == 0)
+ {
+ strcpy(r + rl, e->d_name);
+ rl += strlen(e->d_name);
+
+ closedir(d);
+ d = opendir(r);
+
+ break;
+ }
+
+ e = readdir(d);
+ }
+
+ if (!e)
+ {
+ strcpy(r + rl, c);
+ rl += strlen(c);
+ last = 1;
+ }
+
+ c = strsep(&p, "/");
+ }
+
+ if (d) closedir(d);
+ return 1;
+}
+#endif
diff --git a/src/skel/crossplatform.h b/src/skel/crossplatform.h
index 342aab4e..a21877c1 100644
--- a/src/skel/crossplatform.h
+++ b/src/skel/crossplatform.h
@@ -1,10 +1,38 @@
#include <time.h>
-// This is the common include for platform/renderer specific skeletons(glfw, win etc.) and cross platform things (like Windows directories wrapper, platform specific global arrays etc.)
+// This is the common include for platform/renderer specific skeletons(glfw.cpp, win.cpp etc.) and using cross platform things (like Windows directories wrapper, platform specific global arrays etc.)
+// Functions that's different on glfw and win but have same signature, should be located on platform.h.
-// This only has <windef.h> as Win header.
#ifdef _WIN32
+// This only has <windef.h> as Win header.
#include "win.h"
+extern DWORD _dwOperatingSystemVersion;
+#else
+char *strupr(char *str);
+char *strlwr(char *str);
+enum {
+ OS_WIN98,
+ OS_WIN2000,
+ OS_WINNT,
+ OS_WINXP,
+};
+
+enum {
+ LANG_OTHER,
+ LANG_GERMAN,
+ LANG_FRENCH,
+ LANG_ENGLISH,
+ LANG_ITALIAN,
+ LANG_SPANISH,
+};
+
+enum {
+ SUBLANG_OTHER,
+ SUBLANG_ENGLISH_AUS
+};
+
+extern long _dwOperatingSystemVersion;
+int casepath(char const *path, char *r);
#endif
#ifdef RW_GL3
@@ -14,8 +42,8 @@ typedef struct
RwBool fullScreen;
RwV2d lastMousePos;
double mouseWheel; // glfw doesn't cache it
- int8 joy1id;
- int8 joy2id;
+ RwInt8 joy1id;
+ RwInt8 joy2id;
}
psGlobalType;
@@ -44,17 +72,6 @@ enum eGameState
extern RwUInt32 gGameState;
RwBool IsForegroundApp();
-void InitialiseLanguage();
-RwBool _psSetVideoMode(RwInt32 subSystem, RwInt32 videoMode);
-
-RwChar** _psGetVideoModeList();
-RwInt32 _psGetNumVideModes();
-
-void _psSelectScreenVM(RwInt32 videoMode);
-void HandleExit();
-void _InputTranslateShiftKeyUpDown(RsKeyCodes* rs);
-
-// Mostly wrappers around Windows functions
#ifndef MAX_PATH
#if !defined _WIN32 || defined __MINGW32__
@@ -64,39 +81,39 @@ void _InputTranslateShiftKeyUpDown(RsKeyCodes* rs);
#endif
#endif
-// TODO: Remove USEALTERNATIVEWINFUNCS and don't use it anywhere when re3 becomes fully cross-platform, this is for testing
// Codes compatible with Windows and Linux
-#if defined USEALTERNATIVEWINFUNCS || !defined _WIN32 || defined __MINGW32__
+#ifndef _WIN32
#define DeleteFile unlink
// Needed for save games
struct SYSTEMTIME {
- uint16 wYear;
- uint16 wMonth;
- uint16 wDayOfWeek;
- uint16 wDay;
- uint16 wHour;
- uint16 wMinute;
- uint16 wSecond;
- uint16 wMilliseconds;
+ RwUInt16 wYear;
+ RwUInt16 wMonth;
+ RwUInt16 wDayOfWeek;
+ RwUInt16 wDay;
+ RwUInt16 wHour;
+ RwUInt16 wMinute;
+ RwUInt16 wSecond;
+ RwUInt16 wMilliseconds;
};
void GetLocalTime_CP(SYSTEMTIME* out);
#define GetLocalTime GetLocalTime_CP
-#define OutputDebugString(s) re3_debug("[DBG-2]: " s "\n")
+#define OutputDebugString(s) re3_debug("[DBG-2]: %s\n",s)
#endif
-// Only runs on GNU/POSIX/etc.
-#if !defined _WIN32 || defined __MINGW32__
+// Compatible with Linux/POSIX and MinGW on Windows
+#ifndef _WIN32
#include <iostream>
#include <dirent.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <langinfo.h>
+#include <unistd.h>
-typedef DIR* HANDLE;
+typedef void* HANDLE;
#define INVALID_HANDLE_VALUE NULL
-#define FindClose closedir
+#define FindClose(h) closedir((DIR*)h)
#define LOCALE_USER_DEFAULT 0
#define DATE_SHORTDATE 0
@@ -107,8 +124,8 @@ struct WIN32_FIND_DATA {
time_t ftLastWriteTime;
};
-HANDLE FindFirstFile(char*, WIN32_FIND_DATA*);
+HANDLE FindFirstFile(const char*, WIN32_FIND_DATA*);
bool FindNextFile(HANDLE, WIN32_FIND_DATA*);
void FileTimeToSystemTime(time_t*, SYSTEMTIME*);
void GetDateFormat(int, int, SYSTEMTIME*, int, char*, int);
-#endif \ No newline at end of file
+#endif
diff --git a/src/skel/glfw/glfw.cpp b/src/skel/glfw/glfw.cpp
index 63ebccee..4a35adcf 100644
--- a/src/skel/glfw/glfw.cpp
+++ b/src/skel/glfw/glfw.cpp
@@ -7,14 +7,11 @@
#pragma warning( disable : 4005)
#pragma warning( pop )
-#pragma comment( lib, "Winmm.lib" ) // Needed for time
-
#if (defined(_MSC_VER))
#include <tchar.h>
#endif /* (defined(_MSC_VER)) */
#include <stdio.h>
#include "rwcore.h"
-#include "resource.h"
#include "skeleton.h"
#include "platform.h"
#include "crossplatform.h"
@@ -69,14 +66,20 @@ static psGlobalType PsGlobal;
#define JIF(x) if (FAILED(hr=(x))) \
{debug(TEXT("FAILED(hr=0x%x) in ") TEXT(#x) TEXT("\n"), hr); return;}
+unsigned long _dwMemAvailPhys;
+RwUInt32 gGameState;
-// TODO: This is used on selecting video mode, so either think something or remove it completely
-DWORD _dwMemTotalVideo = 1024 * (1024 * 1024); // 1024 MB as placeholder
-DWORD _dwMemAvailPhys;
-
+#ifdef _WIN32
DWORD _dwOperatingSystemVersion;
-
-RwUInt32 gGameState;
+#include "resource.h"
+#else
+long _dwOperatingSystemVersion;
+#include <sys/sysinfo.h>
+#include <stddef.h>
+#include <locale.h>
+#include <signal.h>
+#include <errno.h>
+#endif
/*
*****************************************************************************
*/
@@ -144,7 +147,7 @@ const char *_psGetUserFilesFolder()
strcpy(szUserFiles, "data");
return szUserFiles;
#else
- static CHAR szUserFiles[256];
+ static char szUserFiles[256];
strcpy(szUserFiles, "userfiles");
_psCreateFolder(szUserFiles);
return szUserFiles;
@@ -185,6 +188,8 @@ psCameraShowRaster(RwCamera *camera)
/*
*****************************************************************************
*/
+#ifdef _WIN32
+#pragma comment( lib, "Winmm.lib" ) // Needed for time
RwUInt32
psTimer(void)
{
@@ -202,6 +207,16 @@ psTimer(void)
return time;
}
+#else
+double
+psTimer(void)
+{
+ struct timespec start;
+ clock_gettime(CLOCK_MONOTONIC_RAW, &start);
+ return start.tv_sec * 1000.0 + start.tv_nsec/1000000.0;
+}
+#endif
+
/*
*****************************************************************************
@@ -209,12 +224,7 @@ psTimer(void)
void
psMouseSetPos(RwV2d *pos)
{
- POINT point;
-
- point.x = (RwInt32) pos->x;
- point.y = (RwInt32) pos->y;
-
- glfwSetCursorPos(PSGLOBAL(window), point.x, point.y);
+ glfwSetCursorPos(PSGLOBAL(window), pos->x, pos->y);
PSGLOBAL(lastMousePos.x) = (RwInt32)pos->x;
@@ -285,7 +295,7 @@ psInitialise(void)
gGameState = GS_START_UP;
TRACE("gGameState = GS_START_UP");
-
+#ifdef _WIN32
OSVERSIONINFO verInfo;
verInfo.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
@@ -330,14 +340,19 @@ psInitialise(void)
_dwMemAvailPhys = memstats.dwAvailPhys;
-#ifdef FIX_BUGS
debug("Physical memory size %u\n", memstats.dwTotalPhys);
debug("Available physical memory %u\n", memstats.dwAvailPhys);
#else
- debug("Physical memory size %d\n", memstats.dwTotalPhys);
- debug("Available physical memory %d\n", memstats.dwAvailPhys);
-#endif
+ struct sysinfo systemInfo;
+ sysinfo(&systemInfo);
+
+ _dwMemAvailPhys = systemInfo.freeram;
+ _dwOperatingSystemVersion = OS_WINXP; // To fool other classes
+
+ debug("Physical memory size %u\n", systemInfo.totalram);
+ debug("Available physical memory %u\n", systemInfo.freeram);
+#endif
TheText.Unload();
return TRUE;
@@ -413,18 +428,8 @@ RwChar **_psGetVideoModeList()
if ( vm.flags & rwVIDEOMODEEXCLUSIVE )
{
- if ( vm.width >= 640
- && vm.height >= 480
- && (vm.width == 640
- && vm.height == 480)
- || !(vm.flags & rwVIDEOMODEEXCLUSIVE)
- || (_dwMemTotalVideo - vm.depth * vm.height * vm.width / 8) > (12 * 1024 * 1024)/*12 MB*/ )
- {
- _VMList[i] = (RwChar*)RwCalloc(100, sizeof(RwChar));
- rwsprintf(_VMList[i],"%lu X %lu X %lu", vm.width, vm.height, vm.depth);
- }
- else
- _VMList[i] = nil;
+ _VMList[i] = (RwChar*)RwCalloc(100, sizeof(RwChar));
+ rwsprintf(_VMList[i],"%lu X %lu X %lu", vm.width, vm.height, vm.depth);
}
else
_VMList[i] = nil;
@@ -445,6 +450,8 @@ void _psSelectScreenVM(RwInt32 videoMode)
if (!_psSetVideoMode(RwEngineGetCurrentSubSystem(), videoMode))
{
RsGlobal.quit = TRUE;
+
+ printf("ERROR: Failed to select new screen resolution\n");
}
else
FrontEndMenuManager.LoadAllTextures();
@@ -589,7 +596,7 @@ psSelectDevice()
#ifdef DEFAULT_NATIVE_RESOLUTION
GcurSelVM = 1;
#else
- MessageBox(nil, "Cannot find 640x480 video mode", "GTA3", MB_OK);
+ printf("WARNING: Cannot find 640x480 video mode, selecting device cancelled\n");
return FALSE;
#endif
}
@@ -602,8 +609,9 @@ psSelectDevice()
FrontEndMenuManager.m_nPrefsHeight == 0 ||
FrontEndMenuManager.m_nPrefsDepth == 0){
// Defaults if nothing specified
- FrontEndMenuManager.m_nPrefsWidth = GetSystemMetrics(SM_CXSCREEN);
- FrontEndMenuManager.m_nPrefsHeight = GetSystemMetrics(SM_CYSCREEN);
+ const GLFWvidmode *mode = glfwGetVideoMode(glfwGetPrimaryMonitor());
+ FrontEndMenuManager.m_nPrefsWidth = mode->width;
+ FrontEndMenuManager.m_nPrefsHeight = mode->height;
FrontEndMenuManager.m_nPrefsDepth = 32;
FrontEndMenuManager.m_nPrefsWindowed = 0;
}
@@ -632,7 +640,7 @@ psSelectDevice()
}
if(bestFsMode < 0){
- MessageBox(nil, "Cannot find desired video mode", "GTA3", MB_OK);
+ printf("WARNING: Cannot find desired video mode, selecting device cancelled\n");
return FALSE;
}
GcurSelVM = bestFsMode;
@@ -886,6 +894,30 @@ CommandLineToArgv(RwChar *cmdLine, RwInt32 *argCount)
*/
void InitialiseLanguage()
{
+#ifndef _WIN32
+ // Mandatory for Linux(Unix? Posix?) to set lang. to environment lang.
+ setlocale(LC_ALL, "");
+
+ char *systemLang, *keyboardLang;
+
+ systemLang = setlocale (LC_ALL, NULL);
+ keyboardLang = setlocale (LC_CTYPE, NULL);
+
+ short primUserLCID, primSystemLCID;
+ primUserLCID = primSystemLCID = !strncmp(systemLang, "fr_",3) ? LANG_FRENCH :
+ !strncmp(systemLang, "de_",3) ? LANG_GERMAN :
+ !strncmp(systemLang, "en_",3) ? LANG_ENGLISH :
+ !strncmp(systemLang, "it_",3) ? LANG_ITALIAN :
+ !strncmp(systemLang, "es_",3) ? LANG_SPANISH :
+ LANG_OTHER;
+
+ short primLayout = !strncmp(keyboardLang, "fr_",3) ? LANG_FRENCH : (!strncmp(keyboardLang, "de_",3) ? LANG_GERMAN : LANG_ENGLISH);
+
+ short subUserLCID, subSystemLCID;
+ subUserLCID = subSystemLCID = !strncmp(systemLang, "en_AU",5) ? SUBLANG_ENGLISH_AUS : SUBLANG_OTHER;
+ short subLayout = !strncmp(keyboardLang, "en_AU",5) ? SUBLANG_ENGLISH_AUS : SUBLANG_OTHER;
+
+#else
WORD primUserLCID = PRIMARYLANGID(GetSystemDefaultLCID());
WORD primSystemLCID = PRIMARYLANGID(GetUserDefaultLCID());
WORD primLayout = PRIMARYLANGID((DWORD)GetKeyboardLayout(0));
@@ -893,7 +925,7 @@ void InitialiseLanguage()
WORD subUserLCID = SUBLANGID(GetSystemDefaultLCID());
WORD subSystemLCID = SUBLANGID(GetUserDefaultLCID());
WORD subLayout = SUBLANGID((DWORD)GetKeyboardLayout(0));
-
+#endif
if ( primUserLCID == LANG_GERMAN
|| primSystemLCID == LANG_GERMAN
|| primLayout == LANG_GERMAN )
@@ -987,13 +1019,22 @@ void InitialiseLanguage()
TheText.Unload();
TheText.Load();
+
+#ifndef _WIN32
+ // TODO this is needed for strcasecmp to work correctly across all languages, but can these cause other problems??
+ setlocale(LC_CTYPE, "C");
+ setlocale(LC_COLLATE, "C");
+ setlocale(LC_NUMERIC, "C");
+#endif
}
/*
*****************************************************************************
*/
+
void HandleExit()
{
+#ifdef _WIN32
MSG message;
while ( PeekMessage(&message, nil, 0U, 0U, PM_REMOVE|PM_NOYIELD) )
{
@@ -1007,8 +1048,21 @@ void HandleExit()
DispatchMessage(&message);
}
}
+#else
+ // We now handle terminate message always, why handle on some cases?
+ return;
+#endif
}
-
+
+#ifndef _WIN32
+void terminateHandler(int sig, siginfo_t *info, void *ucontext) {
+ RsGlobal.quit = TRUE;
+}
+
+void dummyHandler(int sig){
+}
+#endif
+
void resizeCB(GLFWwindow* window, int width, int height) {
/*
* Handle event to ensure window contents are displayed during re-size
@@ -1210,17 +1264,36 @@ cursorCB(GLFWwindow* window, double xpos, double ypos) {
/*
*****************************************************************************
*/
+#ifdef _WIN32
int PASCAL
WinMain(HINSTANCE instance,
HINSTANCE prevInstance __RWUNUSED__,
CMDSTR cmdLine,
int cmdShow)
{
- RwV2d pos;
- RwInt32 argc, i;
+
+ RwInt32 argc;
RwChar** argv;
- StaticPatcher::Apply();
SystemParametersInfo(SPI_SETFOREGROUNDLOCKTIMEOUT, 0, nil, SPIF_SENDCHANGE);
+#else
+int
+main(int argc, char *argv[])
+{
+#endif
+ RwV2d pos;
+ RwInt32 i;
+// StaticPatcher::Apply();
+
+#ifndef _WIN32
+ struct sigaction act;
+ act.sa_sigaction = terminateHandler;
+ act.sa_flags = SA_SIGINFO;
+ sigaction(SIGTERM, &act, NULL);
+ struct sigaction sa;
+ sa.sa_handler = dummyHandler;
+ sa.sa_flags = 0;
+ sigaction(SIGINT, &sa, NULL); // Needed for CdStreamPosix
+#endif
/*
* Initialize the platform independent data.
@@ -1231,7 +1304,7 @@ WinMain(HINSTANCE instance,
return FALSE;
}
-
+#ifdef _WIN32
/*
* Get proper command line params, cmdLine passed to us does not
* work properly under all circumstances...
@@ -1248,6 +1321,7 @@ WinMain(HINSTANCE instance,
* Parse command line parameters (except program name) one at
* a time BEFORE RenderWare initialization...
*/
+#endif
for(i=1; i<argc; i++)
{
RsEventHandler(rsPREINITCOMMANDLINE, argv[i]);
@@ -1303,8 +1377,7 @@ WinMain(HINSTANCE instance,
RsEventHandler(rsCAMERASIZE, &r);
}
-
- SystemParametersInfo(SPI_SETSCREENSAVEACTIVE, FALSE, nil, SPIF_SENDCHANGE);
+#ifdef _WIN32
SystemParametersInfo(SPI_SETPOWEROFFACTIVE, FALSE, nil, SPIF_SENDCHANGE);
SystemParametersInfo(SPI_SETLOWPOWERACTIVE, FALSE, nil, SPIF_SENDCHANGE);
@@ -1319,7 +1392,7 @@ WinMain(HINSTANCE instance,
NewStickyKeys.dwFlags = SKF_TWOKEYSOFF;
SystemParametersInfo(SPI_SETSTICKYKEYS, sizeof(STICKYKEYS), &NewStickyKeys, SPIF_SENDCHANGE);
-
+#endif
{
CFileMgr::SetDirMyDocuments();
@@ -1335,7 +1408,9 @@ WinMain(HINSTANCE instance,
CFileMgr::SetDir("");
}
+#ifdef _WIN32
SetErrorMode(SEM_FAILCRITICALERRORS);
+#endif
#ifndef MASTER
if (TurnOnAnimViewer) {
@@ -1380,7 +1455,7 @@ WinMain(HINSTANCE instance,
case GS_INIT_ONCE:
{
- CoUninitialize();
+ //CoUninitialize();
LoadingScreen(nil, nil, "loadsc0");
@@ -1549,6 +1624,7 @@ WinMain(HINSTANCE instance,
*/
RsEventHandler(rsTERMINATE, nil);
+#ifdef _WIN32
/*
* Free the argv strings...
*/
@@ -1557,9 +1633,8 @@ WinMain(HINSTANCE instance,
SystemParametersInfo(SPI_SETSTICKYKEYS, sizeof(STICKYKEYS), &SavedStickyKeys, SPIF_SENDCHANGE);
SystemParametersInfo(SPI_SETPOWEROFFACTIVE, TRUE, nil, SPIF_SENDCHANGE);
SystemParametersInfo(SPI_SETLOWPOWERACTIVE, TRUE, nil, SPIF_SENDCHANGE);
- SystemParametersInfo(SPI_SETSCREENSAVEACTIVE, TRUE, nil, SPIF_SENDCHANGE);
-
SetErrorMode(0);
+#endif
return 0;
}
@@ -1681,4 +1756,4 @@ int strcasecmp(const char* str1, const char* str2)
return _strcmpi(str1, str2);
}
#endif
-#endif \ No newline at end of file
+#endif
diff --git a/src/skel/platform.h b/src/skel/platform.h
index 3e8cce3a..65e20673 100644
--- a/src/skel/platform.h
+++ b/src/skel/platform.h
@@ -9,8 +9,11 @@ extern "C"
{
#endif /* __cplusplus */
+#ifdef _WIN32
extern RwUInt32 psTimer(void);
-
+#else
+extern double psTimer(void);
+#endif
extern RwBool psInitialise(void);
extern void psTerminate(void);
@@ -31,6 +34,19 @@ extern RwBool psInstallFileSystem(void);
/* Handle native texture support */
extern RwBool psNativeTextureSupport(void);
+extern void _InputTranslateShiftKeyUpDown(RsKeyCodes* rs);
+
+extern void HandleExit();
+
+extern void _psSelectScreenVM(RwInt32 videoMode);
+
+extern void InitialiseLanguage();
+
+extern RwBool _psSetVideoMode(RwInt32 subSystem, RwInt32 videoMode);
+
+extern RwChar** _psGetVideoModeList();
+
+extern RwInt32 _psGetNumVideModes();
#ifdef __cplusplus
}
#endif /* __cplusplus */
diff --git a/src/skel/skeleton.cpp b/src/skel/skeleton.cpp
index b5ce744a..5191eda7 100644
--- a/src/skel/skeleton.cpp
+++ b/src/skel/skeleton.cpp
@@ -19,7 +19,11 @@ bool TurnOnAnimViewer = false;
RsGlobalType RsGlobal;
-RwUInt32
+#ifdef _WIN32
+RwUInt32
+#else
+double
+#endif
RsTimer(void)
{
return psTimer();
diff --git a/src/skel/skeleton.h b/src/skel/skeleton.h
index 13588411..8303bd9a 100644
--- a/src/skel/skeleton.h
+++ b/src/skel/skeleton.h
@@ -257,7 +257,11 @@ extern RwBool
RsInputDeviceAttach(RsInputDeviceType inputDevice,
RsInputEventHandler inputEventHandler);
-extern RwUInt32
+#ifdef _WIN32
+extern RwUInt32
+#else
+extern double
+#endif
RsTimer(void);
extern void
diff --git a/src/skel/win/win.cpp b/src/skel/win/win.cpp
index d20cc0bf..9a885818 100644
--- a/src/skel/win/win.cpp
+++ b/src/skel/win/win.cpp
@@ -100,10 +100,10 @@ IVideoWindow *pVW = nil;
IMediaSeeking *pMS = nil;
DWORD dwDXVersion;
-DWORD _dwMemTotalPhys;
-DWORD _dwMemAvailPhys;
-DWORD _dwMemTotalVirtual;
-DWORD _dwMemAvailVirtual;
+SIZE_T _dwMemTotalPhys;
+SIZE_T _dwMemAvailPhys;
+SIZE_T _dwMemTotalVirtual;
+SIZE_T _dwMemAvailVirtual;
DWORD _dwMemTotalVideo;
DWORD _dwMemAvailVideo;
DWORD _dwOperatingSystemVersion;
@@ -687,10 +687,10 @@ psInitialise(void)
_GetVideoMemInfo(&_dwMemTotalVideo, &_dwMemAvailVideo);
#ifdef FIX_BUGS
- debug("Physical memory size %u\n", _dwMemTotalPhys);
- debug("Available physical memory %u\n", _dwMemAvailPhys);
- debug("Video memory size %u\n", _dwMemTotalVideo);
- debug("Available video memory %u\n", _dwMemAvailVideo);
+ debug("Physical memory size %lu\n", _dwMemTotalPhys);
+ debug("Available physical memory %lu\n", _dwMemAvailPhys);
+ debug("Video memory size %lu\n", _dwMemTotalVideo);
+ debug("Available video memory %lu\n", _dwMemAvailVideo);
#else
debug("Physical memory size %d\n", _dwMemTotalPhys);
debug("Available physical memory %d\n", _dwMemAvailPhys);
diff --git a/src/skel/win/win.h b/src/skel/win/win.h
index d05e3951..444e0760 100644
--- a/src/skel/win/win.h
+++ b/src/skel/win/win.h
@@ -22,7 +22,6 @@ enum eWinVersion
OS_WINXP,
};
-extern DWORD _dwOperatingSystemVersion;
#ifdef __DINPUT_INCLUDED__
/* platform specfic global data */
diff --git a/src/vehicles/Cranes.cpp b/src/vehicles/Cranes.cpp
index 3ef11302..9c1442c4 100644
--- a/src/vehicles/Cranes.cpp
+++ b/src/vehicles/Cranes.cpp
@@ -42,7 +42,7 @@ uint32 CCranes::CarsCollectedMilitaryCrane;
int32 CCranes::NumCranes;
CCrane CCranes::aCranes[NUM_CRANES];
-void CCranes::InitCranes(void)
+void CCranes::InitCranes(void)
{
CarsCollectedMilitaryCrane = 0;
NumCranes = 0;
@@ -657,11 +657,11 @@ void CCranes::Load(uint8* buf, uint32 size)
for (int i = 0; i < NUM_CRANES; i++) {
CCrane *pCrane = &aCranes[i];
if (pCrane->m_pCraneEntity != nil)
- pCrane->m_pCraneEntity = CPools::GetBuildingPool()->GetSlot((uint32)pCrane->m_pCraneEntity - 1);
+ pCrane->m_pCraneEntity = CPools::GetBuildingPool()->GetSlot((uintptr)pCrane->m_pCraneEntity - 1);
if (pCrane->m_pHook != nil)
- pCrane->m_pHook = CPools::GetObjectPool()->GetSlot((uint32)pCrane->m_pHook - 1);
+ pCrane->m_pHook = CPools::GetObjectPool()->GetSlot((uintptr)pCrane->m_pHook - 1);
if (pCrane->m_pVehiclePickedUp != nil)
- pCrane->m_pVehiclePickedUp = CPools::GetVehiclePool()->GetSlot((uint32)pCrane->m_pVehiclePickedUp - 1);
+ pCrane->m_pVehiclePickedUp = CPools::GetVehiclePool()->GetSlot((uintptr)pCrane->m_pVehiclePickedUp - 1);
}
for (int i = 0; i < NUM_CRANES; i++) {
aCranes[i].m_nAudioEntity = DMAudio.CreateEntity(AUDIOTYPE_CRANE, &aCranes[i]);