Skip to content

Commit

Permalink
Added support to variable length string arguments longer than 128 cha…
Browse files Browse the repository at this point in the history
…racters. (#84)
  • Loading branch information
MiranDMC authored Aug 8, 2023
1 parent b625a5c commit 1d7dd7c
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 44 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
- added string arguments support to 0AB1 (cleo_call)
- fix an issue when PRINT_STRING and PRINT_BIG_STRING would overwrite each other (see https://github.com/cleolibrary/CLEO4/issues/80)
- update BASS.dll to the latest to solve some issues with audio in game (see https://github.com/cleolibrary/CLEO4/issues/70)
- added support of variable length arguments longer than 128 characters

## 4.4.3

Expand Down
105 changes: 61 additions & 44 deletions source/CCustomOpcodeSystem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -400,40 +400,57 @@ namespace CLEO {
// read string parameter according to convention on strings
char *readString(CRunningScript *thread, char* buf = nullptr, BYTE size = 0)
{
if (size == 0) size = MAX_STR_LEN;

auto paramType = *thread->GetBytePointer();
if (!paramType) return nullptr;
if (paramType >= 1 && paramType <= 8)

if (paramType >= DT_DWORD && paramType <= DT_LVAR_ARRAY) // process parameter as a pointer to string
{
// process parameter as a pointer to string
GetScriptParams(thread, 1);

if (buf != nullptr)
{
size = size > 128 || !size ? 128 : size;
strncpy(buf, opcodeParams[0].pcParam, size - 1);

buf[size - 1] = 0;
buf[size - 1] = '\0';
}

return opcodeParams[0].pcParam;
return opcodeParams[0].pcParam; // original string pointer
}
else
else // process as scm string
{
// process as scm string
if (!buf)
// no user output buffer provided
if (buf == nullptr)
{
static char result[128];
std::fill(result, result + 128, '\0');
GetScriptStringParam(thread, result, 128);
return result;
static char result[MAX_STR_LEN];
buf = result;
size = sizeof(result);
}

std::fill(buf, buf + size, '\0');

if (paramType == DT_VARLEN_STRING)
{
// prococess here as GetScriptStringParam can not obtain strings with lenght greater than 128
thread->IncPtr(1); // already read paramType

BYTE length = *thread->GetBytePointer(); // as unsigned!
thread->IncPtr(1); // length

if (length > 0)
{
auto count = min(size, length);
memcpy(buf, thread->GetBytePointer(), count);

thread->IncPtr(length); // read text
}
}
else
{
size = size > 128 || !size ? 128 : size;
std::fill(buf, buf + size, '\0');
GetScriptStringParam(thread, buf, size);
return buf;
}

return buf;
}
}

Expand Down Expand Up @@ -1278,7 +1295,7 @@ namespace CLEO {
//0AA5=-1,call %1d% num_params %2h% pop %3h%
OpcodeResult __stdcall opcode_0AA5(CRunningScript *thread)
{
static char textParams[5][128]; unsigned currTextParam = 0;
static char textParams[5][MAX_STR_LEN]; unsigned currTextParam = 0;
static SCRIPT_VAR arguments[50] = { 0 };
void(*func)();
DWORD numParams;
Expand Down Expand Up @@ -1311,7 +1328,7 @@ namespace CLEO {
break;
case DT_VARLEN_STRING:
case DT_TEXTLABEL:
(*arg).pcParam = readString(thread, textParams[currTextParam++], 128);
(*arg).pcParam = readString(thread, textParams[currTextParam++], MAX_STR_LEN);
}
}

Expand All @@ -1337,7 +1354,7 @@ namespace CLEO {
//0AA6=-1,call_method %1d% struct %2d% num_params %3h% pop %4h%
OpcodeResult __stdcall opcode_0AA6(CRunningScript *thread)
{
static char textParams[5][128]; unsigned currTextParam = 0;
static char textParams[5][MAX_STR_LEN]; unsigned currTextParam = 0;
static SCRIPT_VAR arguments[50] = { 0 };
void(*func)();
void *struc;
Expand Down Expand Up @@ -1371,7 +1388,7 @@ namespace CLEO {
break;
case DT_VARLEN_STRING:
case DT_TEXTLABEL:
arg->pcParam = readString(thread, textParams[currTextParam++], 128);
arg->pcParam = readString(thread, textParams[currTextParam++], MAX_STR_LEN);
}
}

Expand All @@ -1397,7 +1414,7 @@ namespace CLEO {
//0AA7=-1,call_function %1d% num_params %2h% pop %3h%
OpcodeResult __stdcall opcode_0AA7(CRunningScript *thread)
{
static char textParams[5][128];
static char textParams[5][MAX_STR_LEN];
static SCRIPT_VAR arguments[50] = { 0 };
DWORD currTextParam = 0;
void(*func)();
Expand Down Expand Up @@ -1430,7 +1447,7 @@ namespace CLEO {
break;
case DT_VARLEN_STRING:
case DT_TEXTLABEL:
arg->pcParam = readString(thread, textParams[currTextParam++], 128);
arg->pcParam = readString(thread, textParams[currTextParam++], MAX_STR_LEN);
break;
}
}
Expand Down Expand Up @@ -1460,7 +1477,7 @@ namespace CLEO {
//0AA8=-1,call_function_method %1d% struct %2d% num_params %3h% pop %4h%
OpcodeResult __stdcall opcode_0AA8(CRunningScript *thread)
{
static char textParams[5][128];
static char textParams[5][MAX_STR_LEN];
static SCRIPT_VAR arguments[50] = { 0 };
DWORD currTextParam = 0;
void(*func)();
Expand Down Expand Up @@ -1495,7 +1512,7 @@ namespace CLEO {
break;
case DT_VARLEN_STRING:
case DT_TEXTLABEL:
arg->pcParam = readString(thread, textParams[currTextParam++], 128);
arg->pcParam = readString(thread, textParams[currTextParam++], MAX_STR_LEN);
}
}

Expand Down Expand Up @@ -2006,8 +2023,8 @@ namespace CLEO {
//0ACE=-1,show_formatted_text_box %1d%
OpcodeResult __stdcall opcode_0ACE(CRunningScript *thread)
{
char fmt[128];
char text[128];
char fmt[MAX_STR_LEN];
char text[MAX_STR_LEN];
readString(thread, fmt, sizeof(fmt));
format(thread, text, sizeof(text), fmt);
PrintHelp(text);
Expand All @@ -2018,7 +2035,7 @@ namespace CLEO {
//0ACF=-1,show_formatted_styled_text %1d% time %2d% style %3d%
OpcodeResult __stdcall opcode_0ACF(CRunningScript *thread)
{
char fmt[128]; char text[128];
char fmt[MAX_STR_LEN]; char text[MAX_STR_LEN];
DWORD time, style;
readString(thread, fmt, sizeof(fmt));
*thread >> time >> style;
Expand All @@ -2031,7 +2048,7 @@ namespace CLEO {
//0AD0=-1,show_formatted_text_lowpriority %1d% time %2d%
OpcodeResult __stdcall opcode_0AD0(CRunningScript *thread)
{
char fmt[128]; char text[128];
char fmt[MAX_STR_LEN]; char text[MAX_STR_LEN];
DWORD time;
readString(thread, fmt, sizeof(fmt));
*thread >> time;
Expand All @@ -2044,7 +2061,7 @@ namespace CLEO {
//0AD1=-1,show_formatted_text_highpriority %1d% time %2d%
OpcodeResult __stdcall opcode_0AD1(CRunningScript *thread)
{
char fmt[128]; char text[128];
char fmt[MAX_STR_LEN]; char text[MAX_STR_LEN];
DWORD time;
readString(thread, fmt, sizeof(fmt));
*thread >> time;
Expand Down Expand Up @@ -2078,7 +2095,7 @@ namespace CLEO {
//0AD3=-1,string %1d% format %2d% ...
OpcodeResult __stdcall opcode_0AD3(CRunningScript *thread)
{
char fmt[128], *dst;
char fmt[MAX_STR_LEN], *dst;

if (*thread->GetBytePointer() >= 1 && *thread->GetBytePointer() <= 8) *thread >> dst;
else dst = &GetScriptParamPointer(thread)->cParam;
Expand All @@ -2092,7 +2109,7 @@ namespace CLEO {
//0AD4=-1,%3d% = scan_string %1d% format %2d% //IF and SET
OpcodeResult __stdcall opcode_0AD4(CRunningScript *thread)
{
char fmt[128], *format, *src;
char fmt[MAX_STR_LEN], *format, *src;
src = readString(thread);
format = readString(thread, fmt, sizeof(fmt));

Expand Down Expand Up @@ -2181,7 +2198,7 @@ namespace CLEO {
//0AD9=-1,write_formated_text %2d% to_file %1d%
OpcodeResult __stdcall opcode_0AD9(CRunningScript *thread)
{
char fmt[128]; char text[128];
char fmt[MAX_STR_LEN]; char text[MAX_STR_LEN];
DWORD hFile;
*thread >> hFile;
readString(thread, fmt, sizeof(fmt));
Expand Down Expand Up @@ -2285,12 +2302,12 @@ namespace CLEO {
//0ADF=2,add_dynamic_GXT_entry %1d% text %2d%
OpcodeResult __stdcall opcode_0ADF(CRunningScript *thread)
{
char *entryName;
char text[128];
char *str;
entryName = readString(thread);
str = readString(thread, text, sizeof(text));
GetInstance().TextManager.AddFxt(entryName, str);
char gxtLabel[8]; // 7 + terminator character
readString(thread, gxtLabel, sizeof(gxtLabel));

char *text = readString(thread);

GetInstance().TextManager.AddFxt(gxtLabel, text);
return OR_CONTINUE;
}

Expand Down Expand Up @@ -2691,19 +2708,19 @@ extern "C"

LPSTR WINAPI CLEO_ReadStringOpcodeParam(CRunningScript* thread, char *buf, int size)
{
static char internal_buf[128];
if (!buf) { buf = internal_buf; size = 128; }
if (!size) size = 128;
static char internal_buf[MAX_STR_LEN];
if (!buf) { buf = internal_buf; size = MAX_STR_LEN; }
if (!size) size = MAX_STR_LEN;
std::fill(buf, buf + size, '\0');
GetScriptStringParam(thread, buf, size);
return buf;
}

LPSTR WINAPI CLEO_ReadStringPointerOpcodeParam(CRunningScript* thread, char *buf, int size)
{
static char internal_buf[128];
if (!buf) { buf = internal_buf; size = 128; }
if (!size) size = 128;
static char internal_buf[MAX_STR_LEN];
if (!buf) { buf = internal_buf; size = MAX_STR_LEN; }
if (!size) size = MAX_STR_LEN;
std::fill(buf, buf + size, '\0');
return readString(thread, buf, size);
}
Expand Down
1 change: 1 addition & 0 deletions source/CCustomOpcodeSystem.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

namespace CLEO
{
const size_t MAX_STR_LEN = 0xff; // max length of string type parameter
enum OpcodeResult : char
{
OR_CONTINUE = 0,
Expand Down

0 comments on commit 1d7dd7c

Please sign in to comment.