diff options
| author | _ov4 <ov4@ov4.org> | 2026-10-20 11:57:16 +0000 |
|---|---|---|
| committer | _ov4 <ov4@ov4.org> | 2026-10-20 11:57:16 +0000 |
| commit | 62b605c6c0ea13e9763c0a0115464007b13a8831 (patch) | |
| tree | 53c27965f5a365682e0d79fd96e25b228ecb9dca /lib/CodeGen/FileHandler.cc | |
| parent | bfe2e75d7e3b372e55369677028429990c49bc54 (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/FileHandler.cc')
| -rw-r--r-- | lib/CodeGen/FileHandler.cc | 18 |
1 files changed, 16 insertions, 2 deletions
diff --git a/lib/CodeGen/FileHandler.cc b/lib/CodeGen/FileHandler.cc index a7879e0..a2c3492 100644 --- a/lib/CodeGen/FileHandler.cc +++ b/lib/CodeGen/FileHandler.cc @@ -39,6 +39,9 @@ void FileHandler::setupExternalFunctions() { "realloc", FunctionType::get(PtrTy, {PtrTy, I64}, false)); StrcmpFunc = Module.getOrInsertFunction( "strcmp", FunctionType::get(I32, {PtrTy, PtrTy}, false)); + StrlenFunc = Module.getOrInsertFunction("strlen", FunctionType::get(I64, {PtrTy}, false)); + MemcpyFunc = Module.getOrInsertFunction("memcpy", FunctionType::get(PtrTy, {PtrTy, PtrTy, I64}, false)); + FreeFunc = Module.getOrInsertFunction("free", FunctionType::get(Type::getVoidTy(Context), {PtrTy}, false)); } void FileHandler::setupGlobals() { @@ -231,11 +234,22 @@ void FileHandler::buildOpenFn() { Value *IsRead = Builder.CreateICmpEQ(Mode, ConstantInt::get(I8, uint8_t(FileMode::Read))); Value *ModeStr = Builder.CreateSelect(IsRead, ModeReadStr, WriteOrAppend, "mode_str"); + Value *Size = Builder.CreateAdd(Builder.CreateCall(StrlenFunc, {Name}), Builder.getInt64(1)); + Value *NameCopy = Builder.CreateCall(MallocFunc, {Size}, "owned_filename"); + Value *AllocationError = Builder.CreateGlobalString("[Fatal] line %d: File name allocation failed\n"); + Checker.emitCheck(Builder.CreateICmpEQ(NameCopy, ConstantPointerNull::get(PtrTy)), AllocationError, {Line}); + Builder.CreateCall(MemcpyFunc, {NameCopy, Name, Size}); Value *Handle = Builder.CreateCall(FopenFunc, {Name, ModeStr}, "handle"); Value *OpenFailed = Builder.CreateICmpEQ(Handle, ConstantPointerNull::get(PtrTy), "open_failed"); + auto *Failed = BasicBlock::Create(Context, "open_failed", OpenFn); + auto *Opened = BasicBlock::Create(Context, "opened", OpenFn); + Builder.CreateCondBr(OpenFailed, Failed, Opened); + Builder.SetInsertPoint(Failed); + Builder.CreateCall(FreeFunc, {NameCopy}); Checker.emitCheck(OpenFailed, ErrOpenFail, {Line, Name}); - - Builder.CreateStore(Name, emitSlotGEP(FileNames, PtrTy, Slot)); + Builder.CreateBr(Opened); + Builder.SetInsertPoint(Opened); + Builder.CreateStore(NameCopy, emitSlotGEP(FileNames, PtrTy, Slot)); Builder.CreateStore(Handle, emitSlotGEP(FileHandles, PtrTy, Slot)); Builder.CreateStore(Mode, emitSlotGEP(FileModes, I8, Slot)); Builder.CreateRetVoid(); |
