Fix FxPick code emission

- Fixed: Integer constants passed to pick() need to manually generate load
  instructions, since FxConstant::Emit() will just return a constant
  register with its value.
- Fixed: VMFunctionBuilder::RegAvailability::Reuse() didn't actually
  calculate a proper mask. Also added another assert to this function.
This commit is contained in:
Randy Heit 2014-12-21 21:57:30 -06:00
parent 1ea03ffbec
commit b14f768b68
2 changed files with 20 additions and 11 deletions

View file

@ -2203,6 +2203,13 @@ ExpEmit FxPick::Emit(VMFunctionBuilder *build)
for (unsigned i = 0; i < choices.Size(); ++i)
{
build->BackpatchToHere(jumptable + i);
if (choices[i]->isConstant())
{
int val = static_cast<FxConstant *>(choices[i])->GetValue().GetInt();
build->EmitLoadInt(resultreg.RegNum, val);
}
else
{
ExpEmit casereg = choices[i]->Emit(build);
if (casereg.RegNum != resultreg.RegNum)
{ // The result of the case is in a different register from what
@ -2214,6 +2221,7 @@ ExpEmit FxPick::Emit(VMFunctionBuilder *build)
}
// Free this register so the remaining cases can use it.
casereg.Free(build);
}
// All but the final case needs a jump to the end of the expression's code.
if (i + 1 < choices.Size())
{

View file

@ -423,8 +423,9 @@ void VMFunctionBuilder::RegAvailability::Return(int reg, int count)
bool VMFunctionBuilder::RegAvailability::Reuse(int reg)
{
assert(reg >= 0 && reg <= 255);
assert(reg < MostUsed && "Attempt to reuse a register that was never used");
VM_UWORD mask = reg & 31;
VM_UWORD mask = 1 << (reg & 31);
int word = reg / 32;
if (Used[word] & mask)