From ab86ae0284469a9a941f5b196f9cc99a90305e3a Mon Sep 17 00:00:00 2001 From: _ov4 Date: Thu, 15 Oct 2026 08:20:37 +0800 Subject: fix(codegen): prevent NUM_TO_STR buffer overflow Size REAL buffers for the full fixed-point double range and bound writes with snprintf. Register MinGW CRT aliases for embedded execution. Co-Authored-By: Claude Fable 5.1 --- lib/CodeGen/StringConversionHandler.cc | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) (limited to 'lib/CodeGen/StringConversionHandler.cc') diff --git a/lib/CodeGen/StringConversionHandler.cc b/lib/CodeGen/StringConversionHandler.cc index 6f7461c..2263ef1 100644 --- a/lib/CodeGen/StringConversionHandler.cc +++ b/lib/CodeGen/StringConversionHandler.cc @@ -1,4 +1,5 @@ #include "cps/StringConversionHandler.h" +#include using namespace llvm; using namespace cps; @@ -9,8 +10,8 @@ StringConversionHandler::StringConversionHandler(LLVMContext &Ctx, IRBuilder<> & } void StringConversionHandler::setupExternalFunctions() { - FunctionType *SprintfType = FunctionType::get(Type::getInt32Ty(Context), {PointerType::getUnqual(Context), PointerType::getUnqual(Context)}, true); - SprintfFunc = Module.getOrInsertFunction("sprintf", SprintfType); + FunctionType *SnprintfType = FunctionType::get(Type::getInt32Ty(Context), {PointerType::getUnqual(Context), Type::getInt64Ty(Context), PointerType::getUnqual(Context)}, true); + SnprintfFunc = Module.getOrInsertFunction("snprintf", SnprintfType); FunctionType *StrtollType = FunctionType::get(Type::getInt64Ty(Context), {PointerType::getUnqual(Context), PointerType::getUnqual(Context), Type::getInt32Ty(Context)}, false); StrtollFunc = Module.getOrInsertFunction("strtoll", StrtollType); @@ -23,7 +24,9 @@ void StringConversionHandler::setupExternalFunctions() { } Value *StringConversionHandler::emitNumToStr(Value *Num, bool IsReal) { - Value *AllocSize = ConstantInt::get(Type::getInt64Ty(Context), 64); + // Allow an extra integer digit, sign, decimal point, six fractional digits and NUL. + Value *AllocSize = ConstantInt::get(Type::getInt64Ty(Context), + IsReal ? std::numeric_limits::max_exponent10 + 10 : 64); Value *Buffer = Builder.CreateCall(MallocFunc, AllocSize, "num_str_buf"); Value *FormatStr; @@ -33,7 +36,7 @@ Value *StringConversionHandler::emitNumToStr(Value *Num, bool IsReal) { FormatStr = Builder.CreateGlobalString("%lld"); } - Builder.CreateCall(SprintfFunc, {Buffer, FormatStr, Num}); + Builder.CreateCall(SnprintfFunc, {Buffer, AllocSize, FormatStr, Num}); return Buffer; } -- cgit v1.3.1-4-g156e