From f35176efad8f6c16067cc444c06ef7bc30764c0d Mon Sep 17 00:00:00 2001 From: David Nadlinger Date: Sat, 21 Sep 2013 18:24:34 +0200 Subject: [PATCH] Fix SymOffExp::toConstElem. I am surprised and horrified at the same time that the test suite (on platforms other than Windows, where the code path is triggered in core.stdc.stdio) did not catch this at all. The elemSize-dependent path probably doesn't make too much sense for global variables, as it always refers to the total size of the global. Should add a special case for arrays for clearer codegen in those cases. GitHub: Fixes #477. --- gen/toir.cpp | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/gen/toir.cpp b/gen/toir.cpp index 792f8784..243e52b7 100644 --- a/gen/toir.cpp +++ b/gen/toir.cpp @@ -1262,7 +1262,7 @@ DValue* SymOffExp::toElem(IRState* p) llvm::Constant* SymOffExp::toConstElem(IRState* p) { - Logger::print("SymOffExp::toConstElem: %s @ %s\n", toChars(), type->toChars()); + IF_LOG Logger::println("SymOffExp::toConstElem: %s @ %s", toChars(), type->toChars()); LOG_SCOPE; // We might get null here due to the hackish implementation of @@ -1277,8 +1277,11 @@ llvm::Constant* SymOffExp::toConstElem(IRState* p) } else { - uint64_t elemSize = gDataLayout->getTypeStoreSize( + const unsigned elemSize = gDataLayout->getTypeStoreSize( base->getType()->getContainedType(0)); + + Logger::println("adding offset: %u (elem size: %u)", offset, elemSize); + if (offset % elemSize == 0) { // We can turn this into a "nice" GEP. @@ -1291,7 +1294,7 @@ llvm::Constant* SymOffExp::toConstElem(IRState* p) // apply the byte offset. result = llvm::ConstantExpr::getGetElementPtr( DtoBitCast(base, getVoidPtrType()), - DtoConstSize_t(offset / elemSize)); + DtoConstSize_t(offset)); } }