Cheat menu performance (#643)

* Modify cheat_rec_t data type for planned changes to active cheat handling.

* Reorganized cheats_toogle and cheats_send to cache activated cheats and prevent opening files for all active cheats with each toggle.

* Added consistency checks.
This commit is contained in:
arit
2022-06-18 21:17:12 +02:00
committed by GitHub
parent 8d60ab7779
commit 35b4e8f6fa

View File

@@ -19,8 +19,26 @@
struct cheat_rec_t
{
char enabled;
bool enabled;
char name[256];
int cheatSize;
char *cheatData;
cheat_rec_t()
{
this->enabled = false;
this->cheatData = NULL;
this->cheatSize = 0;
memset(name, 0, sizeof(name));
}
~cheat_rec_t()
{
if (this->cheatData)
{
delete[] this->cheatData;
}
}
};
typedef std::vector<cheat_rec_t> CheatVector;
@@ -395,54 +413,31 @@ void cheats_print()
static void cheats_send()
{
static char filename[1024];
static uint8_t buff[CHEAT_SIZE];
int pos = 0;
for (int i = 0; i < cheats_available(); i++)
{
fileTYPE f = {};
if (cheats[i].enabled)
{
snprintf(filename, sizeof(filename), "%s/%s", cheat_zip, cheats[i].name);
if (FileOpen(&f, filename))
if (cheats[i].cheatData)
{
int len = f.size;
if (!len || (len & 15))
{
printf("Cheat file %s has incorrect length %d -> skipping.", filename, len);
}
else
{
if (len + pos > CHEAT_SIZE)
{
len = CHEAT_SIZE - pos;
}
if (FileReadAdv(&f, buff + pos, len) == len)
{
pos += len;
}
else
{
printf("Cannot read cheat file %s.", filename);
}
}
FileClose(&f);
memcpy(&buff[pos],cheats[i].cheatData,cheats[i].cheatSize);
pos += cheats[i].cheatSize;
}
else
{
printf("Cannot open cheat file %s.", filename);
printf("Consistency error, memory for cheat not allocated, but cheat was enabled -> disable.\n");
cheats[i].cheatSize = 0;
cheats[i].enabled = false;
}
}
if (pos >= CHEAT_SIZE) break;
}
loaded = pos / 16;
printf("Cheat codes: %d\n", loaded);
user_io_set_index(255);
user_io_set_download(1);
user_io_file_tx_data(buff, pos ? pos : 2);
user_io_set_download(0);
@@ -450,8 +445,83 @@ static void cheats_send()
void cheats_toggle()
{
cheats[iSelectedEntry].enabled = !cheats[iSelectedEntry].enabled;
cheats_send();
bool changedCheats = false;
if (cheats[iSelectedEntry].enabled == true)
{
/* disabled loaded cheat, free data */
if (cheats[iSelectedEntry].cheatData)
{
delete[] cheats[iSelectedEntry].cheatData;
cheats[iSelectedEntry].cheatData = NULL;
}
cheats[iSelectedEntry].enabled = false;
cheats[iSelectedEntry].cheatSize = 0;
changedCheats = true;
}
else
{
/* enabled cheat, load data */
static char filename[1024];
fileTYPE f = {};
if (cheats[iSelectedEntry].cheatData)
{
printf("Consistency error, memory for cheat already allocated -> cleanup.\n");
delete[] cheats[iSelectedEntry].cheatData;
cheats[iSelectedEntry].cheatData = NULL;
cheats[iSelectedEntry].cheatSize = 0;
}
snprintf(filename, sizeof(filename), "%s/%s", cheat_zip, cheats[iSelectedEntry].name);
if (FileOpen(&f, filename))
{
int len = f.size;
if (!len || (len & 15))
{
printf("Cheat file %s has incorrect length %d -> skipping.\n", filename, len);
}
else if ( (len + cheats_loaded()*16) <= CHEAT_SIZE )
{
cheats[iSelectedEntry].cheatData = new char[len];
if (cheats[iSelectedEntry].cheatData)
{
if (FileReadAdv(&f, cheats[iSelectedEntry].cheatData, len) == len)
{
cheats[iSelectedEntry].cheatSize = len;
cheats[iSelectedEntry].enabled = true;
changedCheats = true;
}
else
{
printf("Cannot read cheat file %s.\n", filename);
delete[] cheats[iSelectedEntry].cheatData;
cheats[iSelectedEntry].cheatData = NULL;
cheats[iSelectedEntry].cheatSize = 0;
}
}
else
{
printf("Could not allocate required memory (%d) for cheat file %s.\n",len,filename);
}
}
else
{
printf("No more room in current selection for cheat file %s.\n", filename);
}
FileClose(&f);
}
else
{
printf("Cannot open cheat file %s.\n", filename);
}
}
if (changedCheats)
{
cheats_send();
}
}
int cheats_loaded()