aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/StringConversionHandler.cc
diff options
context:
space:
mode:
author_ov4 <ov4@ov4.org>2026-10-20 11:57:16 +0000
committer_ov4 <ov4@ov4.org>2026-10-20 11:57:16 +0000
commit62b605c6c0ea13e9763c0a0115464007b13a8831 (patch)
tree53c27965f5a365682e0d79fd96e25b228ecb9dca /lib/CodeGen/StringConversionHandler.cc
parentbfe2e75d7e3b372e55369677028429990c49bc54 (diff)
refactor(strings): replace compiler builtins with the STRING library
Construct literals as STRING values and route string operations through ordinary library functions and operators. Preserve value ownership in records, arrays, constants and file I/O. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'lib/CodeGen/StringConversionHandler.cc')
-rw-r--r--lib/CodeGen/StringConversionHandler.cc74
1 files changed, 0 insertions, 74 deletions
diff --git a/lib/CodeGen/StringConversionHandler.cc b/lib/CodeGen/StringConversionHandler.cc
deleted file mode 100644
index 2263ef1..0000000
--- a/lib/CodeGen/StringConversionHandler.cc
+++ /dev/null
@@ -1,74 +0,0 @@
-#include "cps/StringConversionHandler.h"
-#include <limits>
-
-using namespace llvm;
-using namespace cps;
-
-StringConversionHandler::StringConversionHandler(LLVMContext &Ctx, IRBuilder<> &B, llvm::Module &M)
- : Context(Ctx), Builder(B), Module(M) {
- setupExternalFunctions();
-}
-
-void StringConversionHandler::setupExternalFunctions() {
- 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);
-
- FunctionType *StrtodType = FunctionType::get(Type::getDoubleTy(Context), {PointerType::getUnqual(Context), PointerType::getUnqual(Context)}, false);
- StrtodFunc = Module.getOrInsertFunction("strtod", StrtodType);
-
- FunctionType *MallocType = FunctionType::get(PointerType::getUnqual(Context), {Type::getInt64Ty(Context)}, false);
- MallocFunc = Module.getOrInsertFunction("malloc", MallocType);
-}
-
-Value *StringConversionHandler::emitNumToStr(Value *Num, bool IsReal) {
- // Allow an extra integer digit, sign, decimal point, six fractional digits and NUL.
- Value *AllocSize = ConstantInt::get(Type::getInt64Ty(Context),
- IsReal ? std::numeric_limits<double>::max_exponent10 + 10 : 64);
- Value *Buffer = Builder.CreateCall(MallocFunc, AllocSize, "num_str_buf");
-
- Value *FormatStr;
- if (IsReal) {
- FormatStr = Builder.CreateGlobalString("%f");
- } else {
- FormatStr = Builder.CreateGlobalString("%lld");
- }
-
- Builder.CreateCall(SnprintfFunc, {Buffer, AllocSize, FormatStr, Num});
- return Buffer;
-}
-
-Value *StringConversionHandler::emitStrToNum(Value *Str, bool AsReal) {
- Value *NullPtr = ConstantPointerNull::get(PointerType::getUnqual(Context));
- if (AsReal) {
- return Builder.CreateCall(StrtodFunc, {Str, NullPtr}, "str_to_real");
- } else {
- Value *Base = ConstantInt::get(Type::getInt32Ty(Context), 10);
- return Builder.CreateCall(StrtollFunc, {Str, NullPtr, Base}, "str_to_int");
- }
-}
-
-Value *StringConversionHandler::emitIsNum(Value *Str) {
- Function *TheFunction = Builder.GetInsertBlock()->getParent();
-
- IRBuilder<> TmpB(&TheFunction->getEntryBlock(), TheFunction->getEntryBlock().begin());
- AllocaInst *EndPtrAlloc = TmpB.CreateAlloca(PointerType::getUnqual(Context), nullptr, "endptr_alloc");
-
- Builder.CreateCall(StrtodFunc, {Str, EndPtrAlloc});
- Value *EndPtrVal = Builder.CreateLoad(PointerType::getUnqual(Context), EndPtrAlloc, "endptr_val");
-
- FunctionType *StrLenType = FunctionType::get(Type::getInt64Ty(Context), {PointerType::getUnqual(Context)}, false);
- FunctionCallee StrLenFunc = Module.getOrInsertFunction("strlen", StrLenType);
- Value *Len = Builder.CreateCall(StrLenFunc, Str, "str_len");
-
- Value *ExpectedEndPtr = Builder.CreateInBoundsGEP(Type::getInt8Ty(Context), Str, Len);
-
- Value *IsMatch = Builder.CreateICmpEQ(EndPtrVal, ExpectedEndPtr, "is_full_match");
-
- Value *Zero = ConstantInt::get(Type::getInt64Ty(Context), 0);
- Value *IsNotEmpty = Builder.CreateICmpSGT(Len, Zero, "is_not_empty");
-
- return Builder.CreateAnd(IsMatch, IsNotEmpty, "is_num_bool");
-}