diff --git a/src/main/scala/spinal/lib/misc/Elf.scala b/src/main/scala/spinal/lib/misc/Elf.scala index ec45f8a..8144e4d 100644 --- a/src/main/scala/spinal/lib/misc/Elf.scala +++ b/src/main/scala/spinal/lib/misc/Elf.scala @@ -2,6 +2,7 @@ package spinal.lib.misc import net.fornwall.jelf.{ElfFile, ElfSection, ElfSectionHeader, ElfSymbol, ElfSymbolTableSection} import spinal.lib.sim.SparseMemory +import spinal.core._ import java.io.File import java.nio.file.Files @@ -41,6 +42,41 @@ class Elf(val f : File, addressWidth : Int){ } } + + def getMemInit[T <: Data](ram: Mem[T],offset: BigInt, allowOverflow: Boolean = false) = { + val wordSize = ram.wordType.getBitsWidth / 8 + val initContent = Array.fill[BigInt](ram.wordCount)(0) + foreachSection { section => + if ((section.header.sh_flags & ElfSectionHeader.FLAG_ALLOC) != 0) { + val data = getData(section) + val memoryAddress = (section.header.sh_addr - offset) & ((BigInt(1) << addressWidth) - 1).toLong + for((byte, i) <- data.zipWithIndex){ + val addressWithoutOffset = memoryAddress+i + val addressWord = addressWithoutOffset / wordSize + if (addressWord < 0 || addressWord >= initContent.size) { + assert(allowOverflow) + } else { + initContent(addressWord.toInt) |= BigInt(byte.toInt & 0xFF) << ((addressWithoutOffset.toInt % wordSize) * 8) + } + } + } + } + initContent + } + + def init[T <: Data](ram: Mem[T], offset: BigInt, allowOverflow: Boolean = false): Unit = { + val initContent = getMemInit(ram, offset, allowOverflow) + ram.initBigInt(initContent) + } + + def load[T <: Data](ram: Mem[T], offset: BigInt, allowOverflow: Boolean = false): Unit = { + val initContent = getMemInit(ram, offset, allowOverflow) + import spinal.core.sim._ + for((e, i) <- initContent.zipWithIndex){ + ram.setBigInt(i, e) + } + } + def getSymbolAddress(name : String): Long ={ val s = getELFSymbol(name) s.st_value