Commit bb294cde authored by Kunshan Wang's avatar Kunshan Wang

MemoryOperations fix and refactor

Lifted xxxEntity outside match.

Fixed a bug in MemorySupport.cmpXchgEntity
parent 0bb90c20
......@@ -349,58 +349,58 @@ object MemoryOperations {
}
def load(ptr: Boolean, ty: Type, loc: Word, br: ValueBox)(implicit microVM: MicroVM, memorySupport: MemorySupport): Unit = {
def loadScalar(ty: Type, loc: Word, br: ValueBox): Unit = ty match {
case TypeInt(l) =>
val bi: BigInt = l match {
case 8 => memorySupport.loadByte(loc, !ptr)
case 16 => memorySupport.loadShort(loc, !ptr)
case 32 => memorySupport.loadInt(loc, !ptr)
case 64 => memorySupport.loadLong(loc, !ptr)
case 128 => {
val lowWord = memorySupport.loadLong(loc, !ptr)
val highWord = memorySupport.loadLong(loc + 8, !ptr)
(BigInt(highWord) << 64) + lowWord
}
case _ => throw new UvmUnimplementedOperationException("Loading int of length %d is not supported".format(l))
}
br.asInstanceOf[BoxInt].value = OpHelper.unprepare(bi, l)
case _: TypeFloat =>
val fv = memorySupport.loadFloat(loc, !ptr)
br.asInstanceOf[BoxFloat].value = fv
case _: TypeDouble =>
val dv = memorySupport.loadDouble(loc, !ptr)
br.asInstanceOf[BoxDouble].value = dv
case _: AbstractPointerType =>
val addr = memorySupport.loadLong(loc, !ptr)
br.asInstanceOf[BoxPointer].addr = addr
case _: TypeRef =>
noAccessViaPointer(ptr, ty)
val addr = memorySupport.loadLong(loc)
br.asInstanceOf[BoxRef].objRef = addr
case _: TypeIRef =>
noAccessViaPointer(ptr, ty)
val base = memorySupport.loadLong(loc)
val offset = memorySupport.loadLong(loc + WORD_SIZE_BYTES)
br.asInstanceOf[BoxIRef].oo = (base, offset)
case _: TypeTagRef64 =>
noAccessViaPointer(ptr, ty)
val raw = memorySupport.loadLong(loc)
br.asInstanceOf[BoxTagRef64].raw = raw
case _: AbstractOpaqueRefType => {
def loadEntity[T: CanBeIntegerized](): Unit = {
val obj = memorySupport.loadEntity[T](loc)
br.asInstanceOf[BoxOpaque[T]].obj = obj
}
def loadScalar(ty: Type, loc: Word, br: ValueBox): Unit = {
def loadEntity[T: CanBeIntegerized](): Unit = {
noAccessViaPointer(ptr, ty)
ty match {
case _: TypeFuncRef => loadEntity[Function]()
case _: TypeThreadRef => loadEntity[InterpreterThread]()
case _: TypeStackRef => loadEntity[InterpreterStack]()
case _: TypeFrameCursorRef => loadEntity[FrameCursor]()
case _: TypeIRBuilderRef => loadEntity[IRBuilder]()
}
val obj = memorySupport.loadEntity[T](loc)
br.asInstanceOf[BoxOpaque[T]].obj = obj
}
ty match {
case TypeInt(l) =>
val bi: BigInt = l match {
case 8 => memorySupport.loadByte(loc, !ptr)
case 16 => memorySupport.loadShort(loc, !ptr)
case 32 => memorySupport.loadInt(loc, !ptr)
case 64 => memorySupport.loadLong(loc, !ptr)
case 128 => {
val lowWord = memorySupport.loadLong(loc, !ptr)
val highWord = memorySupport.loadLong(loc + 8, !ptr)
(BigInt(highWord) << 64) + lowWord
}
case _ => throw new UvmUnimplementedOperationException(
"Loading int of length %d is not supported".format(l))
}
br.asInstanceOf[BoxInt].value = OpHelper.unprepare(bi, l)
case _: TypeFloat =>
val fv = memorySupport.loadFloat(loc, !ptr)
br.asInstanceOf[BoxFloat].value = fv
case _: TypeDouble =>
val dv = memorySupport.loadDouble(loc, !ptr)
br.asInstanceOf[BoxDouble].value = dv
case _: AbstractPointerType =>
val addr = memorySupport.loadLong(loc, !ptr)
br.asInstanceOf[BoxPointer].addr = addr
case _: TypeRef =>
noAccessViaPointer(ptr, ty)
val addr = memorySupport.loadLong(loc)
br.asInstanceOf[BoxRef].objRef = addr
case _: TypeIRef =>
noAccessViaPointer(ptr, ty)
val base = memorySupport.loadLong(loc)
val offset = memorySupport.loadLong(loc + WORD_SIZE_BYTES)
br.asInstanceOf[BoxIRef].oo = (base, offset)
case _: TypeTagRef64 =>
noAccessViaPointer(ptr, ty)
val raw = memorySupport.loadLong(loc)
br.asInstanceOf[BoxTagRef64].raw = raw
case _: TypeFuncRef => loadEntity[Function]()
case _: TypeThreadRef => loadEntity[InterpreterThread]()
case _: TypeStackRef => loadEntity[InterpreterStack]()
case _: TypeFrameCursorRef => loadEntity[FrameCursor]()
case _: TypeIRBuilderRef => loadEntity[IRBuilder]()
case _ => throw new UvmUnimplementedOperationException(
"Loading of type %s is not supported".format(ty.getClass.getName))
}
case _ => throw new UvmUnimplementedOperationException("Loading of type %s is not supporing".format(ty.getClass.getName))
}
ty match {
......@@ -415,57 +415,57 @@ object MemoryOperations {
}
def store(ptr: Boolean, ty: Type, loc: Word, nvb: ValueBox)(implicit microVM: MicroVM, memorySupport: MemorySupport): Unit = {
def storeScalar(ty: Type, loc: Word, nvb: ValueBox): Unit = ty match {
case TypeInt(l) =>
val bi = nvb.asInstanceOf[BoxInt].value
l match {
case 8 => memorySupport.storeByte(loc, bi.byteValue, !ptr)
case 16 => memorySupport.storeShort(loc, bi.shortValue, !ptr)
case 32 => memorySupport.storeInt(loc, bi.intValue, !ptr)
case 64 => memorySupport.storeLong(loc, bi.longValue, !ptr)
case 128 => {
memorySupport.storeLong(loc, (bi & 0xffffffffffffffffL).longValue, !ptr)
memorySupport.storeLong(loc + 8, (bi >> 64).longValue, !ptr)
}
case _ => throw new UvmUnimplementedOperationException("Storing int of length %d is not supported".format(l))
}
case _: TypeFloat =>
val fv = nvb.asInstanceOf[BoxFloat].value
memorySupport.storeFloat(loc, fv, !ptr)
case _: TypeDouble =>
val dv = nvb.asInstanceOf[BoxDouble].value
memorySupport.storeDouble(loc, dv, !ptr)
case _: AbstractPointerType =>
val addr = nvb.asInstanceOf[BoxPointer].addr
memorySupport.storeLong(loc, addr, !ptr)
case _: TypeRef =>
noAccessViaPointer(ptr, ty)
val addr = nvb.asInstanceOf[BoxRef].objRef
memorySupport.storeLong(loc, addr)
case _: TypeIRef =>
def storeScalar(ty: Type, loc: Word, nvb: ValueBox): Unit = {
def storeEntity[T: CanBeIntegerized](): Unit = {
noAccessViaPointer(ptr, ty)
val BoxIRef(base, offset) = nvb.asInstanceOf[BoxIRef]
memorySupport.storeLong(loc, base)
memorySupport.storeLong(loc + WORD_SIZE_BYTES, offset)
case _: TypeTagRef64 =>
noAccessViaPointer(ptr, ty)
val raw = nvb.asInstanceOf[BoxTagRef64].raw
memorySupport.storeLong(loc, raw)
case _: AbstractOpaqueRefType => {
def storeEntity[T: CanBeIntegerized](): Unit = {
val obj = nvb.asInstanceOf[BoxOpaque[T]].obj
memorySupport.storeEntity[T](loc, obj)
}
noAccessViaPointer(ptr, ty)
ty match {
case _: TypeFuncRef => storeEntity[Function]()
case _: TypeThreadRef => storeEntity[InterpreterThread]()
case _: TypeStackRef => storeEntity[InterpreterStack]()
case _: TypeFrameCursorRef => storeEntity[FrameCursor]()
case _: TypeIRBuilderRef => storeEntity[IRBuilder]()
}
val obj = nvb.asInstanceOf[BoxOpaque[T]].obj
memorySupport.storeEntity[T](loc, obj)
}
ty match {
case TypeInt(l) =>
val bi = nvb.asInstanceOf[BoxInt].value
l match {
case 8 => memorySupport.storeByte(loc, bi.byteValue, !ptr)
case 16 => memorySupport.storeShort(loc, bi.shortValue, !ptr)
case 32 => memorySupport.storeInt(loc, bi.intValue, !ptr)
case 64 => memorySupport.storeLong(loc, bi.longValue, !ptr)
case 128 => {
memorySupport.storeLong(loc, (bi & 0xffffffffffffffffL).longValue, !ptr)
memorySupport.storeLong(loc + 8, (bi >> 64).longValue, !ptr)
}
case _ => throw new UvmUnimplementedOperationException(
"Storing int of length %d is not supported".format(l))
}
case _: TypeFloat =>
val fv = nvb.asInstanceOf[BoxFloat].value
memorySupport.storeFloat(loc, fv, !ptr)
case _: TypeDouble =>
val dv = nvb.asInstanceOf[BoxDouble].value
memorySupport.storeDouble(loc, dv, !ptr)
case _: AbstractPointerType =>
val addr = nvb.asInstanceOf[BoxPointer].addr
memorySupport.storeLong(loc, addr, !ptr)
case _: TypeRef =>
noAccessViaPointer(ptr, ty)
val addr = nvb.asInstanceOf[BoxRef].objRef
memorySupport.storeLong(loc, addr)
case _: TypeIRef =>
noAccessViaPointer(ptr, ty)
val BoxIRef(base, offset) = nvb.asInstanceOf[BoxIRef]
memorySupport.storeLong(loc, base)
memorySupport.storeLong(loc + WORD_SIZE_BYTES, offset)
case _: TypeTagRef64 =>
noAccessViaPointer(ptr, ty)
val raw = nvb.asInstanceOf[BoxTagRef64].raw
memorySupport.storeLong(loc, raw)
case _: TypeFuncRef => storeEntity[Function]()
case _: TypeThreadRef => storeEntity[InterpreterThread]()
case _: TypeStackRef => storeEntity[InterpreterStack]()
case _: TypeFrameCursorRef => storeEntity[FrameCursor]()
case _: TypeIRBuilderRef => storeEntity[IRBuilder]()
case _ => throw new UvmUnimplementedOperationException(
"Storing of type %s is not supported".format(ty.getClass.getName))
}
case _ => throw new UvmUnimplementedOperationException("Storing of type %s is not supporing".format(ty.getClass.getName))
}
ty match {
......@@ -483,6 +483,14 @@ object MemoryOperations {
* Compare exchange. The result (the old value) is written into br. Return true if successful, false otherwise.
*/
def cmpXchg(ptr: Boolean, ty: Type, loc: Word, eb: ValueBox, db: ValueBox, br: ValueBox)(implicit microVM: MicroVM, memorySupport: MemorySupport): Boolean = {
def cmpXchgEntity[T: CanBeIntegerized](): Boolean = {
noAccessViaPointer(ptr, ty)
val eObj = eb.asInstanceOf[BoxOpaque[T]].obj
val dObj = db.asInstanceOf[BoxOpaque[T]].obj
val (succ, rObj) = memorySupport.cmpXchgEntity(loc, eObj, dObj)
br.asInstanceOf[BoxOpaque[T]].obj = rObj
succ
}
ty match {
case TypeInt(l) =>
val ebi = eb.asInstanceOf[BoxInt].value
......@@ -520,24 +528,13 @@ object MemoryOperations {
val (succ, (rl, rh)) = memorySupport.cmpXchgI128(loc, (el, eh), (dl, dh))
br.asInstanceOf[BoxIRef].oo = (rl, rh)
succ
case _: AbstractOpaqueRefType => {
def cmpXchgEntity[T: CanBeIntegerized](): Boolean = {
val eObj = eb.asInstanceOf[BoxOpaque[T]].obj
val dObj = db.asInstanceOf[BoxOpaque[T]].obj
val (succ, rObj) = memorySupport.cmpXchgEntity(loc, eObj, dObj)
br.asInstanceOf[BoxOpaque[T]].obj = rObj
succ
}
noAccessViaPointer(ptr, ty)
ty match {
case _: TypeFuncRef => cmpXchgEntity[Function]()
case _: TypeThreadRef => cmpXchgEntity[InterpreterThread]()
case _: TypeStackRef => cmpXchgEntity[InterpreterStack]()
case _: TypeFrameCursorRef => cmpXchgEntity[FrameCursor]()
case _: TypeIRBuilderRef => cmpXchgEntity[IRBuilder]()
}
}
case _ => throw new UvmUnimplementedOperationException("CmpXchg of type %s is not supporing".format(ty.getClass.getName))
case _: TypeFuncRef => cmpXchgEntity[Function]()
case _: TypeThreadRef => cmpXchgEntity[InterpreterThread]()
case _: TypeStackRef => cmpXchgEntity[InterpreterStack]()
case _: TypeFrameCursorRef => cmpXchgEntity[FrameCursor]()
case _: TypeIRBuilderRef => cmpXchgEntity[IRBuilder]()
case _ => throw new UvmUnimplementedOperationException(
"CmpXchg of type %s is not suppored".format(ty.getClass.getName))
}
}
......@@ -555,6 +552,12 @@ object MemoryOperations {
if (op != XCHG) {
throw new UvmUnimplementedOperationException("AtomicRMW operation other than XCHG only supports int. %s found.".format(ty.getClass.getName))
} else {
def xchgEntity[T: CanBeIntegerized](): Unit = {
noAccessViaPointer(ptr, ty)
val obj = ob.asInstanceOf[BoxOpaque[T]].obj
val oldObj = memorySupport.xchgEntity(loc, obj)
br.asInstanceOf[BoxOpaque[T]].obj = oldObj
}
ty match {
case _: AbstractPointerType =>
val ol = ob.asInstanceOf[BoxPointer].addr
......@@ -570,21 +573,11 @@ object MemoryOperations {
val BoxIRef(ol, oh) = ob.asInstanceOf[BoxIRef]
val (rl, rh) = memorySupport.xchgI128(loc, (ol, oh))
br.asInstanceOf[BoxIRef].oo = (rl, rh)
case _: AbstractOpaqueRefType => {
def xchgEntity[T: CanBeIntegerized](): Unit = {
val obj = ob.asInstanceOf[BoxOpaque[T]].obj
val oldObj = memorySupport.xchgEntity(loc, obj)
br.asInstanceOf[BoxOpaque[T]].obj = oldObj
}
noAccessViaPointer(ptr, ty)
ty match {
case _: TypeFuncRef => xchgEntity[Function]()
case _: TypeThreadRef => xchgEntity[InterpreterThread]()
case _: TypeStackRef => xchgEntity[InterpreterStack]()
case _: TypeFrameCursorRef => xchgEntity[FrameCursor]()
case _: TypeIRBuilderRef => xchgEntity[IRBuilder]()
}
}
case _: TypeFuncRef => xchgEntity[Function]()
case _: TypeThreadRef => xchgEntity[InterpreterThread]()
case _: TypeStackRef => xchgEntity[InterpreterStack]()
case _: TypeFrameCursorRef => xchgEntity[FrameCursor]()
case _: TypeIRBuilderRef => xchgEntity[IRBuilder]()
case _ =>
throw new UvmUnimplementedOperationException("AtomicRMW XCHG of type %s is not supporing".format(ty.getClass.getName))
}
......
......@@ -157,7 +157,7 @@ class MemorySupport(val muMemorySize: Word) {
def cmpXchgEntity[T: CanBeIntegerized](addr: Word, expected: Option[T], desired: Option[T])(
implicit microVM: MicroVM): (Boolean, Option[T]) = {
val numExpected = implicitly[CanBeIntegerized[T]].integerize(expected)
val numDesired = implicitly[CanBeIntegerized[T]].integerize(expected)
val numDesired = implicitly[CanBeIntegerized[T]].integerize(desired)
val (succ, oldNum) = cmpXchgLong(addr, numExpected, numDesired, inMu = true)
val oldObj = try {
implicitly[CanBeIntegerized[T]].deIntegerize(oldNum)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment