Skip to content

Commit

Permalink
[Assembler] Add %pcrel_hi16 and %pcrel_lo16 MIPS relocations
Browse files Browse the repository at this point in the history
Return the 16 MSB and 16 LSB
  • Loading branch information
SteliosKaragiorgis committed Sep 30, 2023
1 parent 6082d75 commit 8c56c93
Showing 1 changed file with 70 additions and 0 deletions.
70 changes: 70 additions & 0 deletions src/assembler/mipsrelocations.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
#pragma once

#include "QDebug"
#include "VSRTL/interface/vsrtl_binutils.h"
#include "relocation.h"

namespace Ripes {
namespace Assembler {

// pcrel_lo/hi are restricted to 32-bit absolute addresses, so keep computations
// in this base.
inline uint32_t pcrel_hi16(const uint32_t val, const uint32_t reloc_addr) {
return ((val - (reloc_addr % 0xFFFFF000) + 0x800) >> 16);
}

template <typename Reg_T>
Relocation<Reg_T> mips_pcrel_hi() {
return Relocation<Reg_T>("%pcrel_hi16",
[](const Reg_T val, const Reg_T reloc_addr)
-> HandleRelocationRes<Reg_T> {
const uint32_t _hi16 = pcrel_hi16(val, reloc_addr);
return {_hi16};
});
}

template <typename Reg_T>
Relocation<Reg_T> mips_pcrel_lo() {
return Relocation<Reg_T>(
"%pcrel_lo16",
[](const Reg_T val,
const Reg_T reloc_addr) -> HandleRelocationRes<Reg_T> {
using Reg_T_S = typename std::make_signed<Reg_T>::type;
const uint32_t _hi16 = pcrel_hi16(val, reloc_addr);
const uint32_t lo16 = val & 0x0000FFF;
return {static_cast<Reg_T>(
static_cast<Reg_T_S>(vsrtl::signextend(lo16, 16)))};
});
}

template <typename Reg_T>
Relocation<Reg_T> mips_hi() {
return Relocation<Reg_T>(
"%hi",
[](const Reg_T val, const Reg_T /*reloc_addr*/)
-> HandleRelocationRes<Reg_T> { return {val >> 16 & 0xFFFFFF}; });
}

template <typename Reg_T>
Relocation<Reg_T> mips_lo() {
return Relocation<Reg_T>(
"%lo",
[](const Reg_T val, const Reg_T /*reloc_addr*/)
-> HandleRelocationRes<Reg_T> { return {val & 0xFFF}; });
}

template <typename Reg_T>
RelocationsVec<Reg_T> mipsRelocations() {
RelocationsVec<Reg_T> relocations;

relocations.push_back(
std::make_shared<Relocation<Reg_T>>(mips_pcrel_hi<Reg_T>()));
relocations.push_back(
std::make_shared<Relocation<Reg_T>>(mips_pcrel_lo<Reg_T>()));
relocations.push_back(std::make_shared<Relocation<Reg_T>>(mips_hi<Reg_T>()));
relocations.push_back(std::make_shared<Relocation<Reg_T>>(mips_lo<Reg_T>()));

return relocations;
}
} // namespace Assembler
} // namespace Ripes

0 comments on commit 8c56c93

Please sign in to comment.