Compare commits

..

1 Commits

Author SHA1 Message Date
Josh Pearson
986921cc9c Preserve low res textures
Any texture less than 64x64 keep original size.  Improves building LOD texture quality, and doesn't blow VRAM budget
2025-01-09 14:07:43 -07:00
30 changed files with 65 additions and 1821 deletions

View File

@@ -79,10 +79,6 @@ OBJS_TEXCONV += \
../vendor/librw/src/d3d-x/d3d.texconv.o \
../vendor/librw/src/d3d-x/d3d8.texconv.o \
../vendor/librw/src/d3d-x/d3d8render.texconv.o \
../vendor/librw/src/bmp.texconv.o \
../vendor/librw/src/png.texconv.o \
../vendor/librw/src/lodepng/lodepng.texconv.o \
../vendor/tlsf/tlsf.texconv.o
# Add compilation units to this list to explicity compile them with
# -O3 optimizations, while the rest get the default (-Os) treatment
@@ -278,9 +274,6 @@ aud2adpcm: aud2adpcm.c
texconv: $(OBJS_TEXCONV) | pvrtex # You'll have to rebuild pvrtex manually if you change it
$(CXX) -o $@ $(OBJS_TEXCONV)
%.texconv.o: %.c
$(CXX) -c -O3 -g -MMD -MP -o $@ -I../vendor/koshle $(INCLUDE) -I../vendor/emu -I../vendor/crypto -I../vendor/TriStripper/include $(DEFINES) -DDC_TEXCONV -DDC_SIM -D_INC_WINDOWS $(TEXCONV_FLAGS) $<
%.texconv.o: %.cpp
$(CXX) -std=c++2a -c -O3 -g -MMD -MP -o $@ -I../vendor/koshle $(INCLUDE) -I../vendor/emu -I../vendor/crypto -I../vendor/TriStripper/include $(DEFINES) -DDC_TEXCONV -DDC_SIM -D_INC_WINDOWS $(TEXCONV_FLAGS) $<
@@ -323,22 +316,6 @@ TXD_OPTS_NEWS = 512 512
TXD_OPTS_SPLASH1 = 512 512
TXD_OPTS_SPLASH2 = 512 512
TXD_OPTS_SPLASH3 = 512 512
TXD_OPTS_frontend = 512 512 \
--delete-tex "fe_arrows4" \
--delete-tex "fe_arrows2" \
--delete-tex "fe_arrows1" \
--delete-tex "fe_controllersh" \
--delete-tex "fe_controller" \
\
--include-tex assets/dc_ps2d.png dc_ps2d \
--include-tex assets/dc_ps2f.png dc_ps2f \
--include-tex assets/dc_xboxd.png dc_xboxd \
--include-tex assets/dc_xboxf.png dc_xboxf \
--include-tex assets/ps4_d.png ps4_d \
--include-tex assets/ps4_f.png ps4_f \
--include-tex assets/xbox_d.png xbox_d \
--include-tex assets/xbox_f.png xbox_f
DEFAULT_RES = 512
PVR_ENCODER ?= PVRTEX

Binary file not shown.

Before

Width:  |  Height:  |  Size: 88 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 91 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 87 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 90 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 77 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 79 KiB

View File

@@ -269,7 +269,6 @@ RE3_OBJS = \
../src/vmu/vmu.o \
../vendor/miniLZO/minilzo.o \
\
../vendor/tlsf/tlsf.o
# Excluded \
../src/extras/custompipes.o \
@@ -381,9 +380,7 @@ INCLUDE = \
\
-I../vendor/librw \
\
-I../vendor/miniLZO \
\
-I../vendor/tlsf
-I../vendor/miniLZO
DEFINES = -DRW_DC -DLIBRW $(if $(WITH_LOGGING),-DWITH_LOGGING) $(if $(WITH_DCLOAD),-DDC_CHDIR=/pc) \
$(if $(WITH_BEEPS),-DWITH_BEEPS)

View File

@@ -3,7 +3,6 @@
#include <cstring>
#include <set>
#include <vector>
#include <iostream>
using namespace std;
@@ -239,40 +238,6 @@ PluginAttach(void)
const char* currentFile;
namespace rw {
Image* readBMP(const char *filename);
Image* readPNG(const char *filename);
}
void InsertImage(RwTexDictionary* texDict, const char* file, const char* texName) {
RwTexture *tex;
RwRaster *raster;
RwInt32 width, height, depth, format;
RwImage *image = rw::readBMP(file);
if (!image) {
image = rw::readPNG(file);
}
assert(image);
RwImageFindRasterFormat(image, rwRASTERTYPETEXTURE, &width, &height, &depth, &format);
raster = RwRasterCreate(width, height, depth, format);
RwRasterSetFromImage(raster, image);
tex = RwTextureCreate(raster);
RwTextureSetName(tex, texName);
RwTextureSetFilterMode(tex, rwFILTERLINEAR);
RwTexDictionaryAddTexture(texDict, tex);
RwImageDestroy(image);
}
std::vector<std::pair<const char*, const char*>> ImagesToAdd;
std::vector<const char*> ImagesToRemove;
bool listTextures = false;
int main(int argc, const char** argv) {
if (argc >= 5) {
int width = atoi(argv[3]);
@@ -282,7 +247,7 @@ int main(int argc, const char** argv) {
if(height >= 16 && height <= 1024)
rw::dc::maxRasterHeight = height;
}
for (int i = 5; i < argc; i++) {
for (int i = 0; i < argc; i++) {
if (argv[i] != nullptr) {
// Downsample Parameter
if (strcmp(argv[i], "-d") == 0 || strcmp(argv[i], "-D") == 0) {
@@ -306,22 +271,6 @@ int main(int argc, const char** argv) {
}
}
}
if (strcmp(argv[i], "--include-tex") == 0) {
assert(i + 2 < argc);
ImagesToAdd.emplace_back(argv[i+1], argv[i+2]);
i += 2;
}
if (strcmp(argv[i], "--delete-tex") == 0) {
assert(i + 1 < argc);
ImagesToRemove.emplace_back(argv[i+1]);
i += 1;
}
if (strcmp(argv[i], "--list-tex") == 0) {
listTextures = true;
}
}
}
@@ -349,31 +298,6 @@ int main(int argc, const char** argv) {
RwStreamClose(stream, nil);
if (listTextures) {
fprintf(stdout, "Incoming textures:\n");
FORLIST(lnk, texDict->textures) {
auto tex = rw::Texture::fromDict(lnk);
fprintf(stdout, "texture: '%s'\n", tex->name);
}
}
for (auto&& removedTextureName: ImagesToRemove) {
auto removedTexture = texDict->find(removedTextureName);
assert(removedTexture);
texDict->remove(removedTexture);
}
for (auto&& extraTexture: ImagesToAdd) {
InsertImage(texDict, extraTexture.first, extraTexture.second);
}
if (listTextures) {
fprintf(stdout, "Processing textures:\n");
FORLIST(lnk, texDict->textures) {
auto tex = rw::Texture::fromDict(lnk);
fprintf(stdout, "texture: '%s'\n", tex->name);
}
}
auto streamOut = RwStreamOpen(rwSTREAMFILENAME, rwSTREAMWRITE, argv[2]);
assert(streamOut && "failed to open output");

View File

@@ -52,7 +52,7 @@ CAnimBlendHierarchy::RemoveAnimSequences(void)
numSequences = 0;
}
#if 0
#ifdef USE_CUSTOM_ALLOCATOR
void
CAnimBlendHierarchy::MoveMemory(bool onlyone)
{
@@ -61,4 +61,4 @@ CAnimBlendHierarchy::MoveMemory(bool onlyone)
if(sequences[i].MoveMemory() && onlyone)
return;
}
#endif
#endif

View File

@@ -140,7 +140,7 @@ CAnimBlendNode::GetCurrentTranslation(CVector &trans, float weight)
float blend = association->GetBlendAmount(weight);
if(blend > 0.0f){
auto kfAdt = sequence->GetDeltaTime(frameA);
float t = kfAdt == 0.0f ? 0.0f : (kfAdt - remainingTime)/kfAdt;
float t = (kfAdt - remainingTime)/kfAdt;
if(sequence->type & CAnimBlendSequence::KF_TRANS){
auto kfAt = sequence->GetTranslation(frameA);
auto kfBt = sequence->GetTranslation(frameB);

View File

@@ -1,9 +1,3 @@
#include <cstddef>
void* obj_alloc(size_t size, void** storage);
void obj_free(void* ptr);
void* obj_move(void* ptr);
#include "common.h"
#include "AnimBlendSequence.h"
@@ -22,7 +16,7 @@ CAnimBlendSequence::CAnimBlendSequence(void)
CAnimBlendSequence::~CAnimBlendSequence(void)
{
if(keyFrames)
obj_free(keyFrames);
RwFree(keyFrames);
}
void
@@ -48,8 +42,7 @@ CAnimBlendSequence::SetNumFrames(int numFrames, bool translation, bool compress)
sz = sizeof(KeyFrame);
type |= KF_ROT;
}
keyFrames = obj_alloc(sz * numFrames, &(void*&)keyFrames);
assert(keyFrames != nullptr);
keyFrames = RwMalloc(sz * numFrames);
this->numFrames = numFrames;
}
@@ -71,17 +64,24 @@ CAnimBlendSequence::RemoveQuaternionFlips(void)
}
}
#if 0
#ifdef USE_CUSTOM_ALLOCATOR
bool
CAnimBlendSequence::MoveMemory(void)
{
if (keyFrames) {
void* newaddr = obj_move(keyFrames);
if (newaddr) {
if(keyFrames){
void *newaddr = gMainHeap.MoveMemory(keyFrames);
if(newaddr != keyFrames){
keyFrames = newaddr;
return true;
}
}else if(keyFramesCompressed){
void *newaddr = gMainHeap.MoveMemory(keyFramesCompressed);
if(newaddr != keyFramesCompressed){
keyFramesCompressed = newaddr;
return true;
}
}
return false;
}
#endif
#endif

View File

@@ -3789,10 +3789,6 @@ cAudioManager::ProcessPedOneShots(cPedParams &params)
if (iSound > 60)
iSound = 21;
}
// In some cases the left and right channels have different loop points
// This looks like a data file issue where the left and right channels have different loop points
// This is a hot fix to always have the correct loop point for each channel individually
SET_LOOP_OFFSETS(m_sQueueSample.m_nSampleIndex)
AddSampleToRequestedQueue();
}
}

View File

@@ -174,10 +174,6 @@ public:
void UpdateEffectsVolume(void);
#ifdef DC_SH4
void UpdateChannelVolume(uint32 nChannel);
#endif
void SetEffectsMasterVolume(uint8 nVolume);
void SetMusicMasterVolume (uint8 nVolume);
void SetEffectsFadeVolume (uint8 nVolume);

View File

@@ -151,6 +151,7 @@ void aica_snd_sfx_freq_vol(int chn, int freq, int vol) {
cSampleManager SampleManager;
bool8 _bSampmanInitialised = FALSE;
bool _dcAudioInitialized = false;
uint32 BankStartOffset[MAX_SFX_BANKS];
char SampleBankDescFilename[] = "sfx/sfx_all.dsc";
@@ -172,12 +173,6 @@ file_t fdPedSfx;
volatile uint32 nPedSfxReqReadId = 1;
volatile uint32 nPedSfxReqNextId = 1;
// this is very wasteful and temporary
#define BANK_STAGE_SIZE 16 * 2048
static uint8_t stagingBufferBank[BANK_STAGE_SIZE] __attribute__((aligned(32)));
static uint8_t stagingBufferPedSFX[PED_BLOCKSIZE_ADPCM] __attribute__((aligned(32)));
struct WavHeader {
// RIFF Header
char riff[4]; // RIFF Header Magic header
@@ -467,7 +462,7 @@ cSampleManager::Initialise(void)
assert(fdPedSfx >= 0);
_bSampmanInitialised = true;
_dcAudioInitialized = true;
return TRUE;
}
@@ -490,14 +485,7 @@ char cSampleManager::GetCDAudioDriveLetter(void)
void
cSampleManager::UpdateEffectsVolume(void)
{
if(_bSampmanInitialised) {
std::lock_guard<std::mutex> lk(channel_mtx);
for (int i = 0; i < MAXCHANNELS+MAX2DCHANNELS; i++) {
if (channels[i].ch != -1) {
UpdateChannelVolume(i);
}
}
}
// TODO
}
@@ -532,7 +520,6 @@ cSampleManager::SetMonoMode(uint8 nMode)
{
}
bool8
cSampleManager::LoadSampleBank(uint8 nBank)
{
@@ -562,8 +549,8 @@ cSampleManager::LoadSampleBank(uint8 nBank)
// TODO: Split per-bank sfx file
int fd = fs_open(SampleBankDataFilename, O_RDONLY);
assert(fd >= 0);
auto stagingBuffer = stagingBufferBank;
// this is very wasteful and temporary
void* stagingBuffer = memalign(32, 32 * 2048);
assert(stagingBuffer != 0);
// Ideally, we'd suspend the CdStream thingy here or read via that instead
@@ -571,7 +558,7 @@ cSampleManager::LoadSampleBank(uint8 nBank)
fs_seek(fd, fileStart, SEEK_SET);
while (fileSize > 0) {
size_t readSize = fileSize > BANK_STAGE_SIZE ? BANK_STAGE_SIZE : fileSize;
size_t readSize = fileSize > 32 * 2048 ? 32 * 2048 : fileSize;
int rs = fs_read(fd, stagingBuffer, readSize);
debugf("Read %d bytes, expected %d\n", rs, readSize);
assert(rs == readSize);
@@ -581,6 +568,7 @@ cSampleManager::LoadSampleBank(uint8 nBank)
debugf("Loaded %d bytes, %d remaining\n", readSize, fileSize);
}
fs_close(fd);
free(stagingBuffer);
for (int nSfx = BankStartOffset[nBank]; nSfx < BankStartOffset[nBank+1]; nSfx++) {
@@ -729,8 +717,7 @@ cSampleManager::LoadPedComment(uint32 nComment)
// TODO: When we can dma directly to AICA, we can use this instead
// fs_read(fdPedSfx, SPU_BASE_U8 + (uintptr_t)cmd->dest, cmd->size);
// TODO: Merge stagingBufferPedSFX with stagingBuffer
void* stagingBuffer = stagingBufferPedSFX;
void* stagingBuffer = memalign(32, cmd->size);
assert(stagingBuffer != 0);
debugf("Allocated %d bytes at %p\n", cmd->size, stagingBuffer);
int rs = fs_read(fdPedSfx, stagingBuffer, cmd->size);
@@ -738,6 +725,7 @@ cSampleManager::LoadPedComment(uint32 nComment)
assert(rs == cmd->size);
spu_memload((uintptr_t)cmd->dest, stagingBuffer, cmd->size);
free(stagingBuffer);
nPedSfxReqReadId = nPedSfxReqReadId + 1;
});
@@ -863,10 +851,9 @@ cSampleManager::InitialiseChannel(uint32 nChannel, uint32 nSfx, uint8 nBank)
return TRUE;
}
void cSampleManager::UpdateChannelVolume(uint32 nChannel) {
void updateVol(uint32 nChannel) {
auto newVol = channels[nChannel].emittingVol * channels[nChannel].attenuationVol / 255;
newVol = m_nEffectsFadeVolume * newVol * m_nEffectsVolume >> 14;
// newVol = 255;
// printf("updateVol(nChannel: %d) vol: %d, newVol: %d\n", nChannel, channels[nChannel].vol, newVol);
if (channels[nChannel].vol != newVol) {
@@ -889,7 +876,7 @@ cSampleManager::SetChannelVolume(uint32 nChannel, uint32 nVolume)
channels[nChannel].emittingVol = linearlize_volume(nVolume);// nVolume * 255 / MAX_VOLUME;
channels[nChannel].attenuationVol = 255;
UpdateChannelVolume(nChannel);
updateVol(nChannel);
verbosef("SetChannelVolume(nChannel: %d) vol: %d\n", nChannel, nVolume);
}
@@ -1145,8 +1132,7 @@ cSampleManager::StartStreamedFile(uint8 nFile, uint32 nPos, uint8 nStream)
debugf("StartStreamedFile(%d, %d, %d)\n", nFile, nPos, nStream);
uint32_t seek_aligned = 0;
if (nPos) {
uint64_t seek_bytes = (uint64_t)nPos * streams[nStream].rate / (streams[nStream].stereo ? 1000: 2000);
assert(seek_bytes <= INT32_MAX);
uint32 seek_bytes = nPos * streams[nStream].rate / (streams[nStream].stereo ? 1000: 2000);
seek_aligned = seek_bytes & ~(streams[nStream].stereo ? (STREAM_STAGING_READ_SIZE_STEREO-1) : (STREAM_STAGING_READ_SIZE_MONO-1));
}
PreloadStreamedFile(nFile, nStream, seek_aligned);
@@ -1178,9 +1164,7 @@ cSampleManager::GetStreamedFilePosition(uint8 nStream)
ASSERT( nStream < MAX_STREAMS );
int32 rv = 0;
int64_t rv64 = (int64_t)streams[nStream].played_samples * 1000 / streams[nStream].rate;
assert(rv64 <= INT32_MAX);
rv = (int32)rv64;
return streams[nStream].played_samples * 1000 / streams[nStream].rate;
// if(streams[nStream].fd >= 0) {
// rv = fs_tell(streams[nStream].fd);
// }
@@ -1195,7 +1179,6 @@ cSampleManager::SetStreamedVolumeAndPan(uint8 nVolume, uint8 nPan, uint8 nEffect
if (nVolume > MAX_VOLUME)
nVolume = MAX_VOLUME;
nVolume = linearlize_volume(nVolume); //nVolume * 255 / MAX_VOLUME;
nVolume = m_nMusicFadeVolume * nVolume * m_nMusicVolume >> 14;
if (streams[nStream].vol != nVolume || streams[nStream].nPan != nPan) {
streams[nStream].vol = nVolume;
streams[nStream].nPan = nPan;
@@ -1224,10 +1207,7 @@ cSampleManager::GetStreamedFileLength(uint8 nFile)
WavHeader hdr;
assert(fs_read(fd, &hdr, sizeof(hdr)) == sizeof(hdr));
uint64_t rv64 = (uint64_t)hdr.dataSize * 2000 / hdr.numOfChan / hdr.samplesPerSec;
assert(rv64 <= INT32_MAX);
rv = (int32)rv64;
rv = hdr.dataSize * 2000 / hdr.numOfChan / hdr.samplesPerSec;
fs_close(fd);
@@ -1307,17 +1287,9 @@ void cSampleManager::SetChannelEmittingVolume(uint32 nChannel, uint32 nVolume)
if (nVolume > MAX_VOLUME)
nVolume = MAX_VOLUME;
// reduce channel volume when JB.MP3 or S4_BDBD.MP3 playing
if ( MusicManager.GetMusicMode() == MUSICMODE_CUTSCENE
&& MusicManager.GetNextTrack() != STREAMED_SOUND_NEWS_INTRO
&& MusicManager.GetNextTrack() != STREAMED_SOUND_CUTSCENE_SAL4_BDBD )
{
nVolume /= 4;
}
std::lock_guard<std::mutex> lk(channel_mtx);
channels[nChannel].emittingVol = linearlize_volume(nVolume); // nVolume * 255 / MAX_VOLUME;
UpdateChannelVolume(nChannel);
updateVol(nChannel);
}
float calculatePan(float x, float z) {
@@ -1362,7 +1334,7 @@ void cSampleManager::SetChannel3DPosition (uint32 nChannel, float fX, float
channels[nChannel].fY = fY;
channels[nChannel].fZ = fZ;
channels[nChannel].attenuationVol = calculateAttenuation(channels[nChannel].fX, channels[nChannel].fY, channels[nChannel].fZ, channels[nChannel].distMin, channels[nChannel].distMax) * 255;
UpdateChannelVolume(nChannel);
updateVol(nChannel);
}
SetChannelPan(nChannel, calculatePan(-fX, fZ) * 63 + 64);
@@ -1375,7 +1347,7 @@ void cSampleManager::SetChannel3DDistances (uint32 nChannel, float fMax, floa
channels[nChannel].distMin = fMin;
channels[nChannel].distMax = fMax;
channels[nChannel].attenuationVol = calculateAttenuation(channels[nChannel].fX, channels[nChannel].fY, channels[nChannel].fZ, channels[nChannel].distMin, channels[nChannel].distMax) * 255;
UpdateChannelVolume(nChannel);
updateVol(nChannel);
}
#endif

View File

@@ -34,9 +34,6 @@ CPathInfoForObject *InfoForTilePeds;
CTempDetachedNode *DetachedNodesCars;
CTempDetachedNode *DetachedNodesPeds;
void* obj_alloc(size_t size, void** storage);
void obj_free(void* ptr);
bool
CPedPath::CalcPedRoute(int8 pathType, CVector position, CVector destination, CVector *pointPoses, int16 *pointsFound, int16 maxPoints)
{
@@ -248,22 +245,15 @@ CPathFind::Init(void)
void
CPathFind::AllocatePathFindInfoMem(int16 numPathGroups)
{
assert(numPathGroups == 4500);
if (InfoForTileCars) {
obj_free(InfoForTileCars);
InfoForTileCars = nil;
}
if (InfoForTilePeds) {
obj_free(InfoForTilePeds);
InfoForTilePeds = nil;
}
delete[] InfoForTileCars;
InfoForTileCars = nil;
delete[] InfoForTilePeds;
InfoForTilePeds = nil;
// NB: MIAMI doesn't use numPathGroups here but hardcodes 4500
InfoForTileCars = (CPathInfoForObject*) obj_alloc(sizeof(CPathInfoForObject)*12*numPathGroups, nil);
InfoForTileCars = new CPathInfoForObject[12*numPathGroups];
memset(InfoForTileCars, 0, 12*numPathGroups*sizeof(CPathInfoForObject));
InfoForTilePeds = (CPathInfoForObject*) obj_alloc(sizeof(CPathInfoForObject)*12*numPathGroups, nil);
InfoForTilePeds = new CPathInfoForObject[12*numPathGroups];
memset(InfoForTilePeds, 0, 12*numPathGroups*sizeof(CPathInfoForObject));
// unused
@@ -448,15 +438,10 @@ CPathFind::PreparePathData(void)
CountFloodFillGroups(PATH_CAR);
CountFloodFillGroups(PATH_PED);
if (InfoForTileCars) {
obj_free(InfoForTileCars);
InfoForTileCars = nil;
}
if (InfoForTilePeds) {
obj_free(InfoForTilePeds);
InfoForTilePeds = nil;
}
delete[] InfoForTileCars;
InfoForTileCars = nil;
delete[] InfoForTilePeds;
InfoForTilePeds = nil;
delete[] DetachedNodesCars;
DetachedNodesCars = nil;

View File

@@ -1721,8 +1721,8 @@ int8 CRunningScript::ProcessCommands900To999(int32 command)
return 0;
int attempts;
int model = -1;
int index = CGeneral::GetRandomNumberInRange(0, MAXVEHICLESLOADED);
for (attempts = 0; attempts < MAXVEHICLESLOADED; attempts++) {
int index = CGeneral::GetRandomNumberInRange(0, 50);
for (attempts = 0; attempts < 50; attempts++) {
if (model != -1)
break;
model = CStreaming::ms_vehiclesLoaded[index];

View File

@@ -1012,12 +1012,8 @@ void CGame::InitialiseWhenRestarting(void)
DMAudio.ChangeMusicMode(MUSICMODE_GAME);
}
bool obj_relocate();
void CGame::Process(void)
{
obj_relocate();
CPad::UpdatePads();
#ifdef USE_CUSTOM_ALLOCATOR
ProcessTidyUpMemory();

View File

@@ -2785,22 +2785,22 @@ bool CPad::WeaponJustDown(void)
case 0: //Xbox Mode
if (CPad::GetPad(0)->IsDualAnalog)
{
if (NewState.RightTrigger > 128 && !(OldState.RightTrigger > 128))
if (NewState.RightTrigger > 128)
return true;
}
else
{
if (NewState.RightTrigger > 128 && !(OldState.RightTrigger > 128))
if (NewState.RightTrigger > 128)
return true;
}
case 1: //PS2 Mode
if (CPad::GetPad(0)->IsDualAnalog)
{
return NewState.B && !OldState.B;
return NewState.B;
}
else
{
return NewState.B && !OldState.B;
return NewState.B;
}
}

View File

@@ -1164,12 +1164,6 @@ bool re3RemoveLeastUsedModel() {
return CStreaming::RemoveLeastUsedModel();
}
bool re3EmergencyRemoveModel() {
auto initial = CStreaming::ms_memoryUsed;
CStreaming::DeleteRwObjectsBehindCamera(CStreaming::ms_memoryUsed);
return CStreaming::ms_memoryUsed < initial;
}
bool
CStreaming::RemoveLeastUsedModel(void)
{

View File

@@ -83,11 +83,6 @@ CEntity::~CEntity(void)
ResolveReferences();
}
bool
CEntity::IsFence(void) {
return IsObject() && ::IsFence(static_cast<CObject *>(this)->GetModelIndex());
}
void
CEntity::SetModelIndex(uint32 id)
{

View File

@@ -131,7 +131,6 @@ public:
bool IsPed(void) { return m_type == ENTITY_TYPE_PED; }
bool IsObject(void) { return m_type == ENTITY_TYPE_OBJECT; }
bool IsDummy(void) { return m_type == ENTITY_TYPE_DUMMY; }
bool IsFence(void);
RpAtomic *GetAtomic(void) {
assert(RwObjectGetType(m_rwObject) == rpATOMIC);

View File

@@ -59,7 +59,7 @@ CPhysical::CPhysical(void)
bInfiniteMass = false;
bIsInWater = false;
bHitByTrain = false;
bSkipLineCol = IsFence();
bSkipLineCol = false;
m_fDistanceTravelled = 0.0f;
m_treadable[PATH_CAR] = nil;
@@ -1461,10 +1461,6 @@ CPhysical::ProcessCollisionSectorList(CPtrList *lists)
skipCollision = false;
altcollision = false;
if(A->IsFence() && B->IsFence()) {
skipCollision = true;
A->bSkipLineCol = true;
}
if(B->IsBuilding())
skipCollision = false;
else if(IsStreetLight(A->GetModelIndex()) &&
@@ -1926,12 +1922,12 @@ CPhysical::ProcessCollision(void)
n = NUMSTEPS(0.09f);
step = savedTimeStep / n;
}
}else if(responsecase == COLLRESPONSE_SMALLBOX){
}else if(responsecase == COLLRESPONSE_SMALLBOX || responsecase == COLLRESPONSE_FENCEPART){
if(distSq >= sq(0.15f)){
n = NUMSTEPS(0.15f);
step = savedTimeStep / n;
}
}else if(responsecase != COLLRESPONSE_FENCEPART){
}else{
if(distSq >= sq(0.3f)){
n = NUMSTEPS(0.3f);
step = savedTimeStep / n;

View File

@@ -10,7 +10,7 @@
# include <dc/sound/sound.h>
# endif
extern bool _bSampmanInitialised;
extern bool _dcAudioInitialized;
// ====== STATIC METHODS =====
@@ -86,7 +86,7 @@ void VmuProfiler::run() {
#ifdef DC_SH4
if(auto *dev = maple_enum_type(0, MAPLE_FUNC_MEMCARD);
dev && _bSampmanInitialised && updated_)
dev && _dcAudioInitialized && updated_)
{
pvr_stats_t pvrStats; pvr_get_stats(&pvrStats);
uint32_t sramStats = snd_mem_available();

View File

@@ -16,8 +16,6 @@ extern const char* currentFile;
#define texconvf(...) // printf(__VA_ARGS__)
#endif
#include "tlsf.h"
#include "../../../src/vmu/vmu.h"
#include "../rwbase.h"
#include "../rwerror.h"
@@ -41,86 +39,6 @@ extern const char* currentFile;
#define logf(...) // printf(__VA_ARGS__)
bool re3RemoveLeastUsedModel();
bool re3EmergencyRemoveModel();
std::map<void*, void**> relocatableAllocs;
uint8_t obj_heap[4 * 1024 * 1024];
tlsf_t obj_pool;
void obj_init() {
obj_pool = tlsf_create_with_pool(obj_heap, sizeof(obj_heap));
}
void* last_relocation;
bool obj_relocate();
void* obj_alloc(size_t size, void** storage) {
auto rv = tlsf_malloc(obj_pool, size);
while (rv == nullptr) {
if (!re3RemoveLeastUsedModel() && !re3EmergencyRemoveModel()) {
fprintf(stderr, "obj_alloc: out of memory, doing full compaction\n");
last_relocation = 0;
while (obj_relocate())
;
// last chance
}
fprintf(stderr, "obj_alloc: soft out of memory\n");
rv = tlsf_malloc(obj_pool, size);
}
relocatableAllocs[rv] = storage;
return rv;
}
void obj_free(void* p) {
relocatableAllocs.erase(p);
tlsf_free(obj_pool, p);
}
void* obj_move(void* p) {
return tlsf_move(obj_pool, p);
}
bool obj_relocate() {
// FILE* f = fopen("/pc/Users/skmp/projects/dca3-game/dreamcast/chunks-sorted-with.txt.native.tmp", "w");
// fprintf(f, "ALLOC: %p, %d\n", (uintptr_t)obj_heap & 0xFFFFFF, sizeof(obj_heap));
// for(auto allocation: relocatableAllocs) {
// fprintf(f, "ALLOC: %p, %d\n", (uintptr_t&)allocation.first & 0xFFFFFF, tlsf_block_size(allocation.first));
// }
// fclose(f);
// fs_unlink("/pc/Users/skmp/projects/dca3-game/dreamcast/chunks-sorted-with.txt.native");
// fs_rename("/pc/Users/skmp/projects/dca3-game/dreamcast/chunks-sorted-with.txt.native.tmp", "/pc/Users/skmp/projects/dca3-game/dreamcast/chunks-sorted-with.txt.native");
// fprintf(stderr, "obj_relocate: %p\n", last_relocation);
int toRelocate = 10 * 1024;
auto start = relocatableAllocs.upper_bound(last_relocation);
if (start == relocatableAllocs.end())
start = relocatableAllocs.begin();
while(start != relocatableAllocs.end()) {
auto old = start->first;
auto storage = start->second;
auto oldSize = tlsf_block_size(old);
auto newp = obj_move(start->first);
if (newp) {
toRelocate -= oldSize;
*storage = newp;
start = relocatableAllocs.erase(start, std::next(start));
relocatableAllocs[newp] = storage;
last_relocation = newp;
// fprintf(stderr, "obj_relocate: %p -> %p, %d\n", old, newp, oldSize);
if (toRelocate <= 0)
return true;
} else {
start++;
}
}
last_relocation = 0;
return false;
}
// #include "rwdcimpl.h"
@@ -387,8 +305,6 @@ void rw_mat_load_4x4(rw::Matrix* mtx) {
#define mat_identity(a)
#define pvr_fog_table_color(a,r,g,b)
#define pvr_fog_table_linear(s,e)
#define pvr_fog_table_exp(d)
#define pvr_fog_table_custom(d)
#endif
#define mat_trans_single3_nomod(x_, y_, z_, x2, y2, z2) do { \
@@ -747,10 +663,7 @@ void malloc_stats() { }
#define UNIMPL_LOGV(...)
#endif
Camera* rwdcCam;
void beginUpdate(Camera* cam) {
rwdcCam = cam;
float view[16], proj[16];
// View Matrix
@@ -1185,7 +1098,6 @@ static bool doAlphaTest;
static uint8_t fogFuncPvr = PVR_FOG_DISABLE;
static uint32_t fogColor = 0;
static float fogStart = 0.0f;
static uint32 cullModePvr;
static inline unsigned pvrCullMode(uint32_t cullMode) {
@@ -1286,9 +1198,8 @@ setRenderState(int32 state, void *pvalue)
fogFuncPvr = value ? PVR_FOG_TABLE : PVR_FOG_DISABLE;
break;
case FOGCOLOR:
#if !defined(DC_TEXCONV)
// Set fog color when state changes
if(fogColor != value || fogStart != RwCameraGetFogDistance(rwdcCam)) {
if(fogColor != value) {
fogColor = value;
RGBA c;
c.red = value;
@@ -1296,22 +1207,9 @@ setRenderState(int32 state, void *pvalue)
c.blue = value>>16;
c.alpha = value>>24;
pvr_fog_table_color(c.alpha / 255.0f, c.red / 255.0f, c.green / 255.0f, c.blue / 255.0f);
fogStart = RwCameraGetFogDistance(rwdcCam);
float fogEnd = RwCameraGetFarClipPlane(rwdcCam);
float fogIntensity[129];
uint8_t idx = 0;
float startIntensity = (-fogStart) / (fogEnd - fogStart); //interpolate between start and end to get initial intensity
float step = (1.0f - startIntensity) / 129; // we have 129 entries, create a step such that start + (step*129) = 1.0
for(int i = 128; i >= 0; i--) {
fogIntensity[i] = startIntensity + (idx++ * step);
}
pvr_fog_far_depth(fogEnd);
pvr_fog_table_custom(fogIntensity);
pvr_fog_table_linear(50.0f, 450.0f);
}
#endif
break;
// case CULLMODE:
// if(rwStateCache.cullmode != value){
// rwStateCache.cullmode = value;
@@ -3989,19 +3887,19 @@ imageFindRasterFormat(Image *img, int32 type,
;
if(downsampleMode >= HALF) {
if(height / 2 >= 16) {
if(height / 2 >= 64) {
height /= 2;
}
if(width / 2 >= 16) {
if(width / 2 >= 64) {
width /= 2;
}
}
if(downsampleMode >= QUARTER) {
if(height / 2 >= 16) {
if(height / 2 >= 32) {
height /= 2;
}
if(width / 2 >= 16) {
if(width / 2 >= 32) {
width /= 2;
}
}
@@ -4464,7 +4362,6 @@ ObjPipeline* makeDefaultPipeline(void)
static void*
driverOpen(void *o, int32, int32)
{
obj_init();
pvr_init(&pvr_params);
fake_tex = pvr_mem_malloc(sizeof(fake_tex_data));
@@ -4686,7 +4583,7 @@ void*
destroyNativeData(void *object, int32, int32)
{
auto geo = (Geometry*)object;
obj_free(geo->instData);
rwFree(geo->instData);
geo->instData = nil;
return object;
@@ -4703,9 +4600,7 @@ readNativeData(Stream *stream, int32 length, void *object, int32, int32)
return nil;
}
DCModelDataHeader *header = (DCModelDataHeader *)obj_alloc(sizeof(DCModelDataHeader) + chunkLen - 8, &(void*&)geo->instData);
assert(header != nullptr);
DCModelDataHeader *header = (DCModelDataHeader *)rwNew(sizeof(DCModelDataHeader) + chunkLen - 8, MEMDUR_EVENT | ID_GEOMETRY);
geo->instData = header;
stream->read32(&header->platform, 4);
uint32_t version;

92
vendor/tlsf/README.md vendored
View File

@@ -1,92 +0,0 @@
# tlsf
Two-Level Segregated Fit memory allocator implementation.
Written by Matthew Conte (matt@baisoku.org).
Released under the BSD license.
Features
--------
* O(1) cost for malloc, free, realloc, memalign
* Extremely low overhead per allocation (4 bytes)
* Low overhead per TLSF management of pools (~3kB)
* Low fragmentation
* Compiles to only a few kB of code and data
* Support for adding and removing memory pool regions on the fly
Caveats
-------
* Currently, assumes architecture can make 4-byte aligned accesses
* Not designed to be thread safe; the user must provide this
Notes
-----
This code was based on the TLSF 1.4 spec and documentation found at:
http://www.gii.upv.es/tlsf/main/docs
It also leverages the TLSF 2.0 improvement to shrink the per-block overhead from 8 to 4 bytes.
History
-------
2016/04/10 - v3.1
* Code moved to github
* tlsfbits.h rolled into tlsf.c
* License changed to BSD
2014/02/08 - v3.0
* This version is based on improvements from 3DInteractive GmbH
* Interface changed to allow more than one memory pool
* Separated pool handling from control structure (adding, removing, debugging)
* Control structure and pools can still be constructed in the same memory block
* Memory blocks for control structure and pools are checked for alignment
* Added functions to retrieve control structure size, alignment size, min and max block size, overhead of pool structure, and overhead of a single allocation
* Minimal Pool size is tlsf_block_size_min() + tlsf_pool_overhead()
* Pool must be empty when it is removed, in order to allow O(1) removal
2011/10/20 - v2.0
* 64-bit support
* More compiler intrinsics for ffs/fls
* ffs/fls verification during TLSF creation in debug builds
2008/04/04 - v1.9
* Add tlsf_heap_check, a heap integrity check
* Support a predefined tlsf_assert macro
* Fix realloc case where block should shrink; if adjacent block is in use, execution would go down the slow path
2007/02/08 - v1.8
* Fix for unnecessary reallocation in tlsf_realloc
2007/02/03 - v1.7
* tlsf_heap_walk takes a callback
* tlsf_realloc now returns NULL on failure
* tlsf_memalign optimization for 4-byte alignment
* Usage of size_t where appropriate
2006/11/21 - v1.6
* ffs/fls broken out into tlsfbits.h
* tlsf_overhead queries per-pool overhead
2006/11/07 - v1.5
* Smart realloc implementation
* Smart memalign implementation
2006/10/11 - v1.4
* Add some ffs/fls implementations
* Minor code footprint reduction
2006/09/14 - v1.3
* Profiling indicates heavy use of blocks of size 1-128, so implement small block handling
* Reduce pool overhead by about 1kb
* Reduce minimum block size from 32 to 12 bytes
* Realloc bug fix
2006/09/09 - v1.2
* Add tlsf_block_size
* Static assertion mechanism for invariants
* Minor bugfixes
2006/09/01 - v1.1
* Add tlsf_realloc
* Add tlsf_walk_heap
2006/08/25 - v1.0
* First release

1295
vendor/tlsf/tlsf.c vendored

File diff suppressed because it is too large Load Diff

91
vendor/tlsf/tlsf.h vendored
View File

@@ -1,91 +0,0 @@
#ifndef INCLUDED_tlsf
#define INCLUDED_tlsf
/*
** Two Level Segregated Fit memory allocator, version 3.1.
** Written by Matthew Conte
** http://tlsf.baisoku.org
**
** Based on the original documentation by Miguel Masmano:
** http://www.gii.upv.es/tlsf/main/docs
**
** This implementation was written to the specification
** of the document, therefore no GPL restrictions apply.
**
** Copyright (c) 2006-2016, Matthew Conte
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in the
** documentation and/or other materials provided with the distribution.
** * Neither the name of the copyright holder nor the
** names of its contributors may be used to endorse or promote products
** derived from this software without specific prior written permission.
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
** ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
** WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
** DISCLAIMED. IN NO EVENT SHALL MATTHEW CONTE BE LIABLE FOR ANY
** DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
** LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
** ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include <stddef.h>
#if defined(__cplusplus)
extern "C" {
#endif
/* tlsf_t: a TLSF structure. Can contain 1 to N pools. */
/* pool_t: a block of memory that TLSF can manage. */
typedef void* tlsf_t;
typedef void* pool_t;
/* Create/destroy a memory pool. */
tlsf_t tlsf_create(void* mem);
tlsf_t tlsf_create_with_pool(void* mem, size_t bytes);
void tlsf_destroy(tlsf_t tlsf);
pool_t tlsf_get_pool(tlsf_t tlsf);
/* Add/remove memory pools. */
pool_t tlsf_add_pool(tlsf_t tlsf, void* mem, size_t bytes);
void tlsf_remove_pool(tlsf_t tlsf, pool_t pool);
/* malloc/memalign/realloc/free replacements. */
void* tlsf_malloc(tlsf_t tlsf, size_t bytes);
void* tlsf_move(tlsf_t tlsf, void* ptr);
void* tlsf_memalign(tlsf_t tlsf, size_t align, size_t bytes);
void* tlsf_realloc(tlsf_t tlsf, void* ptr, size_t size);
void tlsf_free(tlsf_t tlsf, void* ptr);
/* Returns internal block size, not original request size */
size_t tlsf_block_size(void* ptr);
/* Overheads/limits of internal structures. */
size_t tlsf_size(void);
size_t tlsf_align_size(void);
size_t tlsf_block_size_min(void);
size_t tlsf_block_size_max(void);
size_t tlsf_pool_overhead(void);
size_t tlsf_alloc_overhead(void);
/* Debugging. */
typedef void (*tlsf_walker)(void* ptr, size_t size, int used, void* user);
void tlsf_walk_pool(pool_t pool, tlsf_walker walker, void* user);
/* Returns nonzero if any internal consistency check fails. */
int tlsf_check(tlsf_t tlsf);
int tlsf_check_pool(pool_t pool);
#if defined(__cplusplus)
};
#endif
#endif