From 68c3b241ceb093ef4ff02e2a3b3943dd18ae2525 Mon Sep 17 00:00:00 2001 From: Joel Dice Date: Mon, 22 Apr 2013 19:11:50 -0600 Subject: [PATCH] handle sign extension of constants of various lengths This is a generalization of 9918ea6 which handles 8-bit and 16-bit as well as 32-bit values. --- src/codegen/target/x86/encode.cpp | 32 +++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) diff --git a/src/codegen/target/x86/encode.cpp b/src/codegen/target/x86/encode.cpp index 7f8782b105..31852f4269 100644 --- a/src/codegen/target/x86/encode.cpp +++ b/src/codegen/target/x86/encode.cpp @@ -24,6 +24,24 @@ using namespace avian::util; +namespace { + +int64_t +signExtend(unsigned size, int64_t v) +{ + if (size == 4) { + return static_cast(v); + } else if (size == 2) { + return static_cast(v); + } else if (size == 1) { + return static_cast(v); + } else { + return v; + } +} + +} // namespace + namespace avian { namespace codegen { namespace x86 { @@ -328,11 +346,7 @@ void moveCR2(Context* c, UNUSED unsigned aSize, lir::Constant* a, UNUSED unsigned bSize, lir::Register* b, unsigned promiseOffset) { if (vm::TargetBytesPerWord == 4 and bSize == 8) { - int64_t v = a->value->value(); - - if (aSize == 4) { - v = static_cast(v); - } + int64_t v = signExtend(aSize, a->value->value()); ResolvedPromise high((v >> 32) & 0xFFFFFFFF); lir::Constant ah(&high); @@ -348,13 +362,7 @@ void moveCR2(Context* c, UNUSED unsigned aSize, lir::Constant* a, maybeRex(c, vm::TargetBytesPerWord, b); opcode(c, 0xb8 + regCode(b)); if (a->value->resolved()) { - int64_t v = a->value->value(); - - if (aSize == 4 and bSize == 8) { - v = static_cast(v); - } - - c->code.appendTargetAddress(v); + c->code.appendTargetAddress(signExtend(aSize, a->value->value())); } else { expect(c, aSize == vm::TargetBytesPerWord);