Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
M
mu-impl-ref2
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
5
Issues
5
List
Boards
Labels
Milestones
Merge Requests
2
Merge Requests
2
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
mu
mu-impl-ref2
Commits
f6d369d9
Commit
f6d369d9
authored
Jun 29, 2016
by
Kunshan Wang
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Implemented IR builder CommInsts.
parent
d502900b
Changes
11
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
11 changed files
with
1114 additions
and
147 deletions
+1114
-147
cbinding/muapi.h
cbinding/muapi.h
+1
-1
migrate_scripts/muapitoirbuildercomminstsimpl.py
migrate_scripts/muapitoirbuildercomminstsimpl.py
+172
-6
src/main/scala/uvm/refimpl/MicroVM.scala
src/main/scala/uvm/refimpl/MicroVM.scala
+2
-0
src/main/scala/uvm/refimpl/exceptions.scala
src/main/scala/uvm/refimpl/exceptions.scala
+3
-0
src/main/scala/uvm/refimpl/itpr/CommInstExecutor.scala
src/main/scala/uvm/refimpl/itpr/CommInstExecutor.scala
+3
-3
src/main/scala/uvm/refimpl/itpr/IRBuilderCommInstExecutor.scala
...in/scala/uvm/refimpl/itpr/IRBuilderCommInstExecutor.scala
+787
-90
src/main/scala/uvm/refimpl/itpr/InstructionExecutor.scala
src/main/scala/uvm/refimpl/itpr/InstructionExecutor.scala
+5
-5
src/main/scala/uvm/refimpl/itpr/InterpreterThread.scala
src/main/scala/uvm/refimpl/itpr/InterpreterThread.scala
+12
-11
src/main/scala/uvm/refimpl/itpr/operationHelpers.scala
src/main/scala/uvm/refimpl/itpr/operationHelpers.scala
+84
-23
src/main/scala/uvm/refimpl/mem/SequentialObjectKeeper.scala
src/main/scala/uvm/refimpl/mem/SequentialObjectKeeper.scala
+37
-0
src/main/scala/uvm/types/types.scala
src/main/scala/uvm/types/types.scala
+8
-8
No files found.
cbinding/muapi.h
View file @
f6d369d9
...
...
@@ -609,7 +609,7 @@ struct MuCtx {
MuInstNode
(
*
new_ccall
)(
MuCtx
*
ctx
,
MuBBNode
bb
,
MuCallConv
callconv
,
MuTypeNode
callee_ty
,
MuFuncSigNode
sig
,
MuVarNode
callee
,
MuVarNode
*
args
,
MuArraySize
nargs
);
/// MUAPIPARSER args:array:nargs
MuInstNode
(
*
new_newthread
)(
MuCtx
*
ctx
,
MuBBNode
bb
,
MuVarNode
stack
,
MuVarNode
threadlocal
);
MuInstNode
(
*
new_newthread
)(
MuCtx
*
ctx
,
MuBBNode
bb
,
MuVarNode
stack
,
MuVarNode
threadlocal
);
/// MUAPIPARSER threadlocal:optional
MuInstNode
(
*
new_swapstack_ret
)(
MuCtx
*
ctx
,
MuBBNode
bb
,
MuVarNode
swappee
,
MuTypeNode
*
ret_tys
,
MuArraySize
nret_tys
);
/// MUAPIPARSER ret_tys:array:nret_tys
MuInstNode
(
*
new_swapstack_kill
)(
MuCtx
*
ctx
,
MuBBNode
bb
,
MuVarNode
swappee
);
...
...
migrate_scripts/muapitoirbuildercomminstsimpl.py
View file @
f6d369d9
...
...
@@ -25,7 +25,7 @@ CommInstDesc = namedtuple("CommInstDesc", """
pragmas
arrays
sizes
boo
ls
optiona
ls
"""
.
split
())
_type_map
=
{
...
...
@@ -90,7 +90,7 @@ def get_comminsts(ast):
pragmas
=
meth
[
"pragmas"
]
arrays
=
{}
sizes
=
set
()
boo
ls
=
set
()
optiona
ls
=
set
()
paramnames
=
[]
cparamtys
=
[]
...
...
@@ -111,8 +111,8 @@ def get_comminsts(ast):
sz
=
pragma
[
2
]
arrays
[
pn
]
=
sz
sizes
.
add
(
sz
)
elif
pragma
[
1
]
==
"
boo
l"
:
boo
ls
.
add
(
pn
)
elif
pragma
[
1
]
==
"
optiona
l"
:
optiona
ls
.
add
(
pn
)
muretty
=
to_mu_ty
(
cretty
)
...
...
@@ -128,7 +128,7 @@ def get_comminsts(ast):
muretty
=
muretty
,
arrays
=
arrays
,
sizes
=
sizes
,
bools
=
boo
ls
,
optionals
=
optiona
ls
,
)
comminsts
.
append
(
comminst
)
...
...
@@ -171,11 +171,177 @@ def gen_comminsts_retvals(comminsts):
return
"
\n
"
.
join
(
lines
)
_get_arg_meths
=
{
"int<64>"
:
"asInt64.toLong"
,
"int<32>"
:
"asInt32.toInt"
,
"float"
:
"asFloat"
,
"double"
:
"asDouble"
,
}
def
get_arg_meth
(
mty
,
cty
,
cname
):
if
mty
in
_get_arg_meths
:
return
_get_arg_meths
[
mty
]
elif
mty
.
startswith
(
"iref<"
):
return
"asIRef"
raise
Exception
(
"I don't know how to get arg: {}, {}, {}"
.
format
(
mty
,
cty
,
cname
))
def
get_arg
(
ind
,
mty
,
cty
,
cname
,
is_optional
):
if
cty
==
"MuBundleNode"
:
meth
=
'asIRNode.getOrElse(throw new UvmNullGenRefException("CommInst arg %{} must not be null")).asInstanceOf[BundleNode]'
.
format
(
cname
)
elif
mty
==
"irnoderef"
:
if
is_optional
:
meth
=
'asIRNode'
else
:
meth
=
'asIRNode.getOrElse(throw new UvmNullGenRefException("CommInst arg %{} must not be null"))'
.
format
(
cname
)
else
:
meth
=
get_arg_meth
(
mty
,
cty
,
cname
)
return
" val {} = argList({}).{}"
.
format
(
cname
,
ind
,
meth
)
_set_arg_meths
=
{
"int<32>"
:
"asInt32"
,
}
def
set_arg_meth
(
mty
,
cty
):
if
mty
in
_set_arg_meths
:
return
_set_arg_meths
[
mty
]
elif
mty
.
startswith
(
"iref<"
):
return
"asIRef"
raise
Exception
(
"I don't know how to set return value: {}, {}"
.
format
(
mty
,
cty
))
def
set_ret
(
ind
,
mty
,
cty
,
value
):
if
mty
==
"irnoderef"
:
meth
=
'asIRNode'
return
" results({}).{} = Some({})"
.
format
(
ind
,
meth
,
value
)
else
:
meth
=
set_arg_meth
(
mty
,
cty
)
return
" results({}).{} = {}"
.
format
(
ind
,
meth
,
value
)
_special_cases
=
{
"id"
:
"ID"
,
"sint8"
:
"SInt8"
,
"uint8"
:
"UInt8"
,
"sint16"
:
"SInt16"
,
"uint16"
:
"UInt16"
,
"sint32"
:
"SInt32"
,
"uint32"
:
"UInt32"
,
"sint64"
:
"SInt64"
,
"uint64"
:
"UInt64"
,
"uint64s"
:
"UInt64s"
,
"fp"
:
"FP"
,
"uptr"
:
"UPtr"
,
"ufuncptr"
:
"UFuncPtr"
,
"iref"
:
"IRef"
,
"weakref"
:
"WeakRef"
,
"funcref"
:
"FuncRef"
,
"tagref64"
:
"TagRef64"
,
"threadref"
:
"ThreadRef"
,
"stackref"
:
"StackRef"
,
"framecursorref"
:
"FrameCursorRef"
,
"irnoderef"
:
"IRNodeRef"
,
"funcsig"
:
"FuncSig"
,
"bb"
:
"BB"
,
"binop"
:
"BinOp"
,
"tailcall"
:
"TailCall"
,
"extractvalue"
:
"ExtractValue"
,
"insertvalue"
:
"InsertValue"
,
"extractelement"
:
"ExtractElement"
,
"insertelement"
:
"InsertElement"
,
"shufflevector"
:
"ShuffleVector"
,
"newhybrid"
:
"NewHybrid"
,
"allocahybrid"
:
"AllocaHybrid"
,
"getiref"
:
"GetIRef"
,
"getfieldiref"
:
"GetFieldIRef"
,
"getelemiref"
:
"GetElemIRef"
,
"shiftiref"
:
"ShiftIRef"
,
"getvarpartiref"
:
"GetVarPartIRef"
,
"cmpxchg"
:
"CmpXchg"
,
"atomicrmw"
:
"AtomicRMW"
,
"watchpoint"
:
"WatchPoint"
,
"wpbranch"
:
"WPBranch"
,
"ccall"
:
"CCall"
,
"newthread"
:
"NewThread"
,
"newstack"
:
"NewStack"
,
"swapstack"
:
"SwapStack"
,
"comminst"
:
"CommInst"
,
}
def
toCamelCase
(
name
):
ins
=
name
.
split
(
"_"
)
outs
=
[
ins
[
0
]]
for
inn
in
ins
[
1
:]:
if
inn
in
_special_cases
:
outs
.
append
(
_special_cases
[
inn
])
else
:
outs
.
append
(
inn
[
0
].
upper
()
+
inn
[
1
:])
return
""
.
join
(
outs
)
def
gen_comminst_impl
(
comminst
):
lines
=
[]
lines
.
append
(
' case "{}" => {{'
.
format
(
comminst
.
muname
))
for
ind
,
(
cty
,
mty
,
cname
)
in
enumerate
(
zip
(
comminst
.
cparamtys
,
comminst
.
muparamtys
,
comminst
.
paramnames
)):
lines
.
append
(
get_arg
(
ind
,
mty
,
cty
,
cname
,
is_optional
=
(
cname
in
comminst
.
optionals
)))
ir_builder_args
=
[]
for
cty
,
mty
,
cname
in
zip
(
comminst
.
cparamtys
,
comminst
.
muparamtys
,
comminst
.
paramnames
):
if
cname
in
comminst
.
arrays
:
sz
=
comminst
.
arrays
[
cname
]
loaded_array_name
=
"_ary_"
+
cname
if
mty
==
"iref<irnoderef>"
:
loader_func
=
"loadIRNodeArray"
elif
mty
==
"iref<int<64>>"
:
loader_func
=
"loadInt64Array"
elif
cty
==
"MuFlag*"
:
loader_func
=
"loadFlagArray"
else
:
raise
Exception
(
"I don't know how to load array: {}, {}, {}"
.
format
(
cty
,
mty
,
cname
))
lines
.
append
(
' val {} = {}({}, {})'
.
format
(
loaded_array_name
,
loader_func
,
cname
,
sz
))
ir_builder_args
.
append
(
loaded_array_name
)
elif
cname
in
comminst
.
sizes
:
pass
# skip array sizes
elif
cty
==
"MuBool"
:
bool_name
=
"_bool_"
+
cname
lines
.
append
(
' val {} = {} != 0'
.
format
(
bool_name
,
cname
))
ir_builder_args
.
append
(
bool_name
)
else
:
ir_builder_args
.
append
(
cname
)
ir_builder_meth_name
=
toCamelCase
(
comminst
.
funcname
)
lines
.
append
(
' val _rv = irBuilder.{}({})'
.
format
(
ir_builder_meth_name
,
", "
.
join
(
ir_builder_args
)))
if
comminst
.
cretty
!=
"void"
:
lines
.
append
(
set_ret
(
0
,
comminst
.
muretty
,
comminst
.
cretty
,
"_rv"
))
lines
.
append
(
" continueNormally()"
)
lines
.
append
(
" }"
)
return
"
\n
"
.
join
(
lines
)
# These functions are too speical. Implemented manually in Scala.
_blacklist
=
[
"load_bundle_from_node"
,
"abort_bundle_node"
,
"set_name"
,
"new_const_int_ex"
,
]
def
gen_comminsts_impls
(
comminsts
):
lines
=
[]
for
comminst
in
comminsts
:
lines
.
append
(
' case "{}" => ???'
.
format
(
comminst
.
muname
))
if
comminst
.
funcname
not
in
_blacklist
:
lines
.
append
(
gen_comminst_impl
(
comminst
))
return
"
\n
"
.
join
(
lines
)
...
...
src/main/scala/uvm/refimpl/MicroVM.scala
View file @
f6d369d9
...
...
@@ -13,6 +13,7 @@ import uvm.refimpl.nat.NativeCallHelper
import
uvm.staticanalysis.StaticAnalyzer
import
uvm.utils.IDFactory
import
uvm.ir.irbuilder.IRBuilder
import
uvm.ir.irbuilder.IRNode
object
MicroVM
{
val
DEFAULT_SOS_SIZE
:
Word
=
2L
*
1024L
*
1024L
;
// 2MiB
...
...
@@ -52,6 +53,7 @@ class MicroVM(vmConf: VMConf) {
val
idFactory
=
new
IDFactory
(
MicroVM
.
FIRST_CLIENT_USABLE_ID
)
val
irBuilder
=
new
IRBuilder
(
globalBundle
,
idFactory
)
val
irNodeRegistry
=
new
SequentialObjectKeeper
[
IRNode
]()
val
irReader
=
new
UIRTextReader
(
idFactory
,
recordSourceInfo
=
vmConf
.
sourceInfo
)
val
hailScriptLoader
=
new
HailScriptLoader
(
recordSourceInfo
=
vmConf
.
sourceInfo
)
val
staticAnalyzer
=
new
StaticAnalyzer
()
...
...
src/main/scala/uvm/refimpl/exceptions.scala
View file @
f6d369d9
...
...
@@ -27,6 +27,9 @@ class UvmUndefinedBehaviorException(message: String = null, cause: Throwable = n
/** Thrown when a division by zero is executed and the exception clause is not present. */
class
UvmDivisionByZeroException
(
message
:
String
=
null
,
cause
:
Throwable
=
null
)
extends
UvmUndefinedBehaviorException
(
message
,
cause
)
/** Thrown when a general reference value is null when it must not be. */
class
UvmNullGenRefException
(
message
:
String
=
null
,
cause
:
Throwable
=
null
)
extends
UvmUndefinedBehaviorException
(
message
,
cause
)
/** Thrown when accessing Mu memory but the address is outside the allocated region. */
class
UvmIllegalMemoryAccessException
(
message
:
String
=
null
,
cause
:
Throwable
=
null
)
extends
UvmRuntimeException
(
message
,
cause
)
...
...
src/main/scala/uvm/refimpl/itpr/CommInstExecutor.scala
View file @
f6d369d9
...
...
@@ -34,7 +34,7 @@ trait CommInstExecutor extends InterpreterActions with ObjectPinner with IRBuild
val
Seq
(
sig
)
=
sigList
val
Seq
(
func
)
=
argList
val
funcVal
=
func
.
asFunc
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
ctx
+
"Attempt to create new thread for NULL Mu function."
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Attempt to create new thread for NULL Mu function."
)
}
val
sta
=
microVM
.
threadStackManager
.
newStack
(
funcVal
,
mutator
)
...
...
@@ -45,7 +45,7 @@ trait CommInstExecutor extends InterpreterActions with ObjectPinner with IRBuild
case
"@uvm.kill_stack"
=>
{
val
Seq
(
s
)
=
argList
val
sta
=
s
.
asStack
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
ctx
+
"Attempt to kill NULL stack."
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Attempt to kill NULL stack."
)
}
sta
.
kill
()
continueNormally
()
...
...
@@ -281,7 +281,7 @@ trait CommInstExecutor extends InterpreterActions with ObjectPinner with IRBuild
val
Seq
(
func
,
cookie
)
=
argList
val
f
=
func
.
asFunc
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
ctx
+
"Attempt to expose NULL Mu function"
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Attempt to expose NULL Mu function"
)
}
val
c
=
boxOf
(
cookie
).
asSInt64
.
longValue
...
...
src/main/scala/uvm/refimpl/itpr/IRBuilderCommInstExecutor.scala
View file @
f6d369d9
This diff is collapsed.
Click to expand it.
src/main/scala/uvm/refimpl/itpr/InstructionExecutor.scala
View file @
f6d369d9
...
...
@@ -242,7 +242,7 @@ trait InstructionExecutor extends InterpreterActions with CommInstExecutor {
case
i
@
InstCall
(
sig
,
callee
,
argList
,
excClause
,
keepalives
)
=>
{
val
calleeFunc
=
callee
.
asFunc
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
ctx
+
"Callee must not be NULL"
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Callee must not be NULL"
)
}
val
argBoxes
=
argList
.
map
(
boxOf
)
...
...
@@ -255,7 +255,7 @@ trait InstructionExecutor extends InterpreterActions with CommInstExecutor {
case
i
@
InstTailCall
(
sig
,
callee
,
argList
)
=>
{
val
calleeFunc
=
callee
.
asFunc
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
ctx
+
"Callee must not be NULL"
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Callee must not be NULL"
)
}
val
argBoxes
=
argList
.
map
(
boxOf
)
...
...
@@ -386,7 +386,7 @@ trait InstructionExecutor extends InterpreterActions with CommInstExecutor {
case
i
@
InstGetIRef
(
referentTy
,
opnd
)
=>
{
val
baseAddr
=
opnd
.
asRef
if
(
baseAddr
==
0L
)
{
throw
new
Uvm
UndefinedBehavior
Exception
(
ctx
+
"Attempted to use GETIREF on a NULL reference"
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Attempted to use GETIREF on a NULL reference"
)
}
results
(
0
).
asIRef
=
(
baseAddr
,
0L
)
continueNormally
()
...
...
@@ -524,7 +524,7 @@ trait InstructionExecutor extends InterpreterActions with CommInstExecutor {
case
i
@
InstNewThread
(
stack
,
threadLocal
,
newStackAction
,
excClause
)
=>
{
val
newStack
=
stack
.
asStack
.
getOrElse
{
throw
new
Uvm
UndefinedBehavior
Exception
(
ctx
+
"Attempt to bind a new thread to a NULL stack."
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Attempt to bind a new thread to a NULL stack."
)
}
val
threadLocalAddr
=
threadLocal
.
map
(
tl
=>
tl
.
asRef
).
getOrElse
(
0L
)
...
...
@@ -547,7 +547,7 @@ trait InstructionExecutor extends InterpreterActions with CommInstExecutor {
case
i
@
InstSwapStack
(
swappee
,
curStackAction
,
newStackAction
,
excClause
,
keepalives
)
=>
{
val
oldStack
=
curStack
val
newStack
=
swappee
.
asStack
.
getOrElse
{
throw
new
Uvm
UndefinedBehavior
Exception
(
ctx
+
"Swappee must not be NULL."
)
throw
new
Uvm
NullGenRef
Exception
(
ctx
+
"Swappee must not be NULL."
)
}
def
handleOldStack
()
=
curStackAction
match
{
...
...
src/main/scala/uvm/refimpl/itpr/InterpreterThread.scala
View file @
f6d369d9
...
...
@@ -13,6 +13,7 @@ import uvm.refimpl.mem.TypeSizes.Word
import
uvm.ssavariables._
import
uvm.types._
import
uvm.refimpl.nat.NativeCallResult
import
uvm.ir.irbuilder.IRNode
object
InterpreterThread
{
val
logger
=
Logger
(
LoggerFactory
.
getLogger
(
getClass
.
getName
))
...
...
@@ -421,7 +422,7 @@ trait InterpreterActions extends InterpreterThreadState {
}
case
TrapHandlerResult
.
Rebind
(
newStack
,
htr
)
=>
{
val
ns
=
newStack
.
vb
.
stack
.
getOrElse
{
throw
new
Uvm
Runtime
Exception
(
curCtx
+
"Attempt to rebind to NULL stack when returning from trap."
)
throw
new
Uvm
NullGenRef
Exception
(
curCtx
+
"Attempt to rebind to NULL stack when returning from trap."
)
}
htr
match
{
...
...
@@ -510,14 +511,16 @@ object MagicalBox {
def
asBoolean
:
Boolean
=
OpHelper
.
prepareUnsigned
(
box
.
asIntRaw
,
1
)
==
1
def
asFloat
:
Float
=
box
.
asInstanceOf
[
BoxFloat
].
value
def
asDouble
:
Double
=
box
.
asInstanceOf
[
BoxDouble
].
value
def
asPtr
:
Word
=
box
.
asInstanceOf
[
BoxPointer
].
addr
def
asSeq
:
Seq
[
ValueBox
]
=
box
.
asInstanceOf
[
BoxSeq
].
values
def
asRef
:
Word
=
box
.
asInstanceOf
[
BoxRef
].
objRef
def
asIRef
:
(
Word
,
Word
)
=
box
.
asInstanceOf
[
BoxIRef
].
oo
def
asTR64Raw
:
Long
=
box
.
asInstanceOf
[
BoxTagRef64
].
raw
def
asFunc
:
Option
[
Function
]
=
box
.
asInstanceOf
[
BoxFunc
].
func
def
asThread
:
Option
[
InterpreterThread
]
=
box
.
asInstanceOf
[
BoxThread
].
thread
def
asStack
:
Option
[
InterpreterStack
]
=
box
.
asInstanceOf
[
BoxStack
].
stack
def
asTR64Raw
:
Long
=
box
.
asInstanceOf
[
BoxTagRef64
].
raw
def
asPtr
:
Word
=
box
.
asInstanceOf
[
BoxPointer
].
addr
def
asSeq
:
Seq
[
ValueBox
]
=
box
.
asInstanceOf
[
BoxSeq
].
values
def
asFrameCursor
:
Option
[
FrameCursor
]
=
box
.
asInstanceOf
[
BoxFrameCursor
].
cursor
def
asIRNode
:
Option
[
IRNode
]
=
box
.
asInstanceOf
[
BoxIRNode
].
node
def
asIntRaw_=
(
v
:
BigInt
)
:
Unit
=
box
.
asInstanceOf
[
BoxInt
].
value
=
v
def
asInt1_=
(
v
:
BigInt
)
:
Unit
=
box
.
setInt
(
v
,
1
)
...
...
@@ -530,18 +533,16 @@ object MagicalBox {
def
asBoolean_=
(
v
:
Boolean
)
:
Unit
=
box
.
setInt
(
if
(
v
)
1
else
0
,
1
)
def
asFloat_=
(
v
:
Float
)
:
Unit
=
box
.
asInstanceOf
[
BoxFloat
].
value
=
v
def
asDouble_=
(
v
:
Double
)
:
Unit
=
box
.
asInstanceOf
[
BoxDouble
].
value
=
v
def
asPtr_=
(
v
:
Word
)
:
Unit
=
box
.
asInstanceOf
[
BoxPointer
].
addr
=
v
def
asSeq_=
(
vs
:
Seq
[
ValueBox
])
:
Unit
=
{
for
((
dst
,
src
)
<-
box
.
asSeq
zip
vs
)
{
dst
copyFrom
src
}
}
def
asRef_=
(
v
:
Word
)
:
Unit
=
box
.
asInstanceOf
[
BoxRef
].
objRef
=
v
def
asIRef_=
(
oo
:
(
Word
,
Word
))
:
Unit
=
box
.
asInstanceOf
[
BoxIRef
].
oo
=
oo
def
asTR64Raw_=
(
v
:
Long
)
:
Unit
=
box
.
asInstanceOf
[
BoxTagRef64
].
raw
=
v
def
asFunc_=
(
v
:
Option
[
Function
])
:
Unit
=
box
.
asInstanceOf
[
BoxFunc
].
func
=
v
def
asThread_=
(
v
:
Option
[
InterpreterThread
])
:
Unit
=
box
.
asInstanceOf
[
BoxThread
].
thread
=
v
def
asStack_=
(
v
:
Option
[
InterpreterStack
])
:
Unit
=
box
.
asInstanceOf
[
BoxStack
].
stack
=
v
def
asTR64Raw_=
(
v
:
Long
)
:
Unit
=
box
.
asInstanceOf
[
BoxTagRef64
].
raw
=
v
def
asPtr_=
(
v
:
Word
)
:
Unit
=
box
.
asInstanceOf
[
BoxPointer
].
addr
=
v
def
asSeq_=
(
vs
:
Seq
[
ValueBox
])
:
Unit
=
{
for
((
dst
,
src
)
<-
box
.
asSeq
zip
vs
)
{
dst
copyFrom
src
}
}
def
asFrameCursor_=
(
v
:
Option
[
FrameCursor
])
:
Unit
=
box
.
asInstanceOf
[
BoxFrameCursor
].
cursor
=
v
def
asIRNode_=
(
v
:
Option
[
IRNode
])
:
Unit
=
box
.
asInstanceOf
[
BoxIRNode
].
node
=
v
def
getSInt
(
len
:
Int
)
:
BigInt
=
OpHelper
.
prepareSigned
(
box
.
asIntRaw
,
len
)
def
getUInt
(
len
:
Int
)
:
BigInt
=
OpHelper
.
prepareUnsigned
(
box
.
asIntRaw
,
len
)
...
...
src/main/scala/uvm/refimpl/itpr/operationHelpers.scala
View file @
f6d369d9
...
...
@@ -10,6 +10,7 @@ import uvm.refimpl.mem.TypeSizes
import
uvm.ssavariables._
import
uvm.ssavariables.AtomicRMWOptr._
import
uvm.types._
import
uvm.ir.irbuilder.IRNode
object
OpHelper
{
...
...
@@ -365,6 +366,9 @@ object MemoryOperations {
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
)
...
...
@@ -374,6 +378,10 @@ object MemoryOperations {
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
=>
noAccessViaPointer
(
ptr
,
ty
)
val
fid
=
memorySupport
.
loadLong
(
loc
).
toInt
...
...
@@ -389,13 +397,10 @@ object MemoryOperations {
val
sid
=
memorySupport
.
loadLong
(
loc
).
toInt
val
sta
=
microVM
.
threadStackManager
.
stackRegistry
.
get
(
sid
)
br
.
asInstanceOf
[
BoxStack
].
stack
=
sta
case
_:
Type
TagRef64
=>
case
_:
Type
IRNodeRef
=>
noAccessViaPointer
(
ptr
,
ty
)
val
raw
=
memorySupport
.
loadLong
(
loc
)
br
.
asInstanceOf
[
BoxTagRef64
].
raw
=
raw
case
_:
TypeUPtr
|
_
:
TypeUFuncPtr
=>
val
addr
=
memorySupport
.
loadLong
(
loc
,
!
ptr
)
br
.
asInstanceOf
[
BoxPointer
].
addr
=
addr
val
maybeIRNode
=
loadIRNode
(
loc
)
br
.
asInstanceOf
[
BoxIRNode
].
node
=
maybeIRNode
case
_
=>
throw
new
UvmUnimplementedOperationException
(
"Loading of type %s is not supporing"
.
format
(
ty
.
getClass
.
getName
))
}
...
...
@@ -410,7 +415,7 @@ object MemoryOperations {
}
}
def
store
(
ptr
:
Boolean
,
ty
:
Type
,
loc
:
Word
,
nvb
:
ValueBox
)(
implicit
memorySupport
:
MemorySupport
)
:
Unit
=
{
def
store
(
ptr
:
Boolean
,
ty
:
Type
,
loc
:
Word
,
nvb
:
ValueBox
)(
implicit
m
icroVM
:
MicroVM
,
m
emorySupport
:
MemorySupport
)
:
Unit
=
{
def
storeScalar
(
ty
:
Type
,
loc
:
Word
,
nvb
:
ValueBox
)
:
Unit
=
ty
match
{
case
TypeInt
(
l
)
=>
val
bi
=
nvb
.
asInstanceOf
[
BoxInt
].
value
...
...
@@ -431,6 +436,9 @@ object MemoryOperations {
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
...
...
@@ -440,6 +448,10 @@ object MemoryOperations {
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
=>
noAccessViaPointer
(
ptr
,
ty
)
val
fid
=
nvb
.
asInstanceOf
[
BoxFunc
].
func
.
map
(
_
.
id
).
getOrElse
(
0
)
...
...
@@ -452,13 +464,10 @@ object MemoryOperations {
noAccessViaPointer
(
ptr
,
ty
)
val
sid
=
nvb
.
asInstanceOf
[
BoxStack
].
stack
.
map
(
_
.
id
).
getOrElse
(
0
)
memorySupport
.
storeLong
(
loc
,
sid
.
toLong
&
0xFFFFFFFF
L
)
case
_:
Type
TagRef64
=>
case
_:
Type
IRNodeRef
=>
noAccessViaPointer
(
ptr
,
ty
)
val
raw
=
nvb
.
asInstanceOf
[
BoxTagRef64
].
raw
memorySupport
.
storeLong
(
loc
,
raw
)
case
_:
TypeUPtr
|
_
:
TypeUFuncPtr
=>
val
addr
=
nvb
.
asInstanceOf
[
BoxPointer
].
addr
memorySupport
.
storeLong
(
loc
,
addr
,
!
ptr
)
val
maybeIRNode
=
nvb
.
asInstanceOf
[
BoxIRNode
].
node
storeIRNode
(
loc
,
maybeIRNode
)
case
_
=>
throw
new
UvmUnimplementedOperationException
(
"Storing of type %s is not supporing"
.
format
(
ty
.
getClass
.
getName
))
}
...
...
@@ -494,6 +503,12 @@ object MemoryOperations {
}
br
.
asInstanceOf
[
BoxInt
].
value
=
OpHelper
.
unprepare
(
rbi
,
l
)
succ
case
_:
AbstractPointerType
=>
val
el
=
eb
.
asInstanceOf
[
BoxPointer
].
addr
val
dl
=
db
.
asInstanceOf
[
BoxPointer
].
addr
val
(
succ
,
rl
)
=
memorySupport
.
cmpXchgLong
(
loc
,
el
,
dl
,
!
ptr
)
br
.
asInstanceOf
[
BoxPointer
].
addr
=
rl
succ
case
_:
TypeRef
=>
noAccessViaPointer
(
ptr
,
ty
)
val
el
=
eb
.
asInstanceOf
[
BoxRef
].
objRef
...
...
@@ -532,12 +547,6 @@ object MemoryOperations {
val
rs
=
microVM
.
threadStackManager
.
stackRegistry
.
get
(
rl
.
toInt
)
br
.
asInstanceOf
[
BoxStack
].
stack
=
rs
succ
case
_:
TypeUPtr
|
_
:
TypeUFuncPtr
=>
val
el
=
eb
.
asInstanceOf
[
BoxPointer
].
addr
val
dl
=
db
.
asInstanceOf
[
BoxPointer
].
addr
val
(
succ
,
rl
)
=
memorySupport
.
cmpXchgLong
(
loc
,
el
,
dl
,
!
ptr
)
br
.
asInstanceOf
[
BoxPointer
].
addr
=
rl
succ
case
_
=>
throw
new
UvmUnimplementedOperationException
(
"CmpXchg of type %s is not supporing"
.
format
(
ty
.
getClass
.
getName
))
}
}
...
...
@@ -557,6 +566,10 @@ object MemoryOperations {
throw
new
UvmUnimplementedOperationException
(
"AtomicRMW operation other than XCHG only supports int. %s found."
.
format
(
ty
.
getClass
.
getName
))
}
else
{
ty
match
{
case
_:
AbstractPointerType
=>
val
ol
=
ob
.
asInstanceOf
[
BoxPointer
].
addr
val
rl
=
memorySupport
.
atomicRMWLong
(
op
,
loc
,
ol
,
!
ptr
)
br
.
asInstanceOf
[
BoxPointer
].
addr
=
rl
case
_:
TypeRef
=>
noAccessViaPointer
(
ptr
,
ty
)
val
ol
=
ob
.
asInstanceOf
[
BoxRef
].
objRef
...
...
@@ -590,10 +603,6 @@ object MemoryOperations {
val
ol
=
ob
.
asInstanceOf
[
BoxTagRef64
].
raw
val
rl
=
memorySupport
.
atomicRMWLong
(
op
,
loc
,
ol
)
br
.
asInstanceOf
[
BoxTagRef64
].
raw
=
rl
case
_:
TypeUPtr
|
_
:
TypeUFuncPtr
=>
val
ol
=
ob
.
asInstanceOf
[
BoxPointer
].
addr
val
rl
=
memorySupport
.
atomicRMWLong
(
op
,
loc
,
ol
,
!
ptr
)
br
.
asInstanceOf
[
BoxPointer
].
addr
=
rl
case
_
=>
throw
new
UvmUnimplementedOperationException
(
"AtomicRMW XCHG of type %s is not supporing"
.
format
(
ty
.
getClass
.
getName
))
}
...
...
@@ -651,5 +660,57 @@ object MemoryOperations {
loc
}
/**
* Load irnoderef value from the memory. Use fake value from microVM.irNodeRegistry
*/
def
loadIRNode
(
loc
:
Word
)(
implicit
microVM
:
MicroVM
,
memorySupport
:
MemorySupport
)
:
Option
[
IRNode
]
=
{
val
irNodeLong
=
memorySupport
.
loadLong
(
loc
).
toInt
val
maybeIRNode
=
microVM
.
irNodeRegistry
.
longToObj
(
irNodeLong
)
maybeIRNode
}
/**
* Store irnoderef value into the memory. Use fake value from microVM.irNodeRegistry
*/
def
storeIRNode
(
loc
:
Word
,
maybeIRNode
:
Option
[
IRNode
])(
implicit
microVM
:
MicroVM
,
memorySupport
:
MemorySupport
)
:
Unit
=
{
val
irNodeLong
=
microVM
.
irNodeRegistry
.
objGetLong
(
maybeIRNode
)
memorySupport
.
storeLong
(
loc
,
irNodeLong
)
}
def
loadInt32Array
(
base
:
Word
,
len
:
Word
)(
implicit
memorySupport
:
MemorySupport
)
:
IndexedSeq
[
Int
]
=
{
if
(
base
==
0L
)
{
IndexedSeq
[
Int
]()
}
else
{
for
(
i
<-
0L
until
len
)
yield
{
val
addr
=
base
+
i
*
4L
val
v
=
memorySupport
.
loadInt
(
addr
)
v
}
}
}
def
loadInt64Array
(
base
:
Word
,
len
:
Word
)(
implicit
memorySupport
:
MemorySupport
)
:
IndexedSeq
[
Long
]
=
{
if
(
base
==
0L
)
{
IndexedSeq
[
Long
]()
}
else
{
for
(
i
<-
0L
until
len
)
yield
{
val
addr
=
base
+
i
*
WORD_SIZE_BYTES
val
v
=
memorySupport
.
loadLong
(
addr
)
v
}
}
}
def
loadIRNodeArray
(
base
:
Word
,
sz
:
Word
)(
implicit
microVM
:
MicroVM
,
memorySupport
:
MemorySupport
)
:
IndexedSeq
[
IRNode
]
=
{
if
(
base
==
0L
)
{
IndexedSeq
[
IRNode
]()
}
else
{
for
(
i
<-
0L
until
sz
)
yield
{
val
loc
=
base
+
i
*
WORD_SIZE_BYTES
loadIRNode
(
loc
).
get
}
}
}
}
src/main/scala/uvm/refimpl/mem/SequentialObjectKeeper.scala
0 → 100644
View file @
f6d369d9
package
uvm.refimpl.mem
import
scala.collection.mutable.HashMap
/**
* This class keeps a map between Long and arbitrary Scala objects. In this way,
* references to arbitrary Scala objects can be stored in the Mu memory.
* <p>
* Similar to JFFI's object exposer.
*/
class
SequentialObjectKeeper
[
T
]
{
private
val
longToObj
=
new
HashMap
[
Long
,
T
]()
private
val
objToLong
=
new
HashMap
[
T
,
Long
]()
var
nextLong
=
1L
def
objGetLong
(
maybeObj
:
Option
[
T
])
:
Long
=
{
maybeObj
match
{
case
None
=>
0L
case
Some
(
obj
)
=>
objToLong
.
getOrElseUpdate
(
obj
,
{
val
myLong
=
nextLong
nextLong
+=
1
longToObj
(
myLong
)
=
obj
myLong
})
}
}
def
longToObj
(
l
:
Long
)
:
Option
[
T
]
=
longToObj
.
get
(
l
)
def
maybeRemoveObj
(
obj
:
T
)
:
Unit
=
{
objToLong
.
remove
(
obj
).
foreach
{
l
=>
longToObj
.
remove
(
l
)
}
}
}
\ No newline at end of file
src/main/scala/uvm/types/types.scala
View file @
f6d369d9
...
...
@@ -32,20 +32,20 @@ abstract class AbstractPointerType extends Type
case
class
TypeInt
(
var
length
:
Int
)
extends
Type
case
class
TypeFloat
()
extends
FPType
case
class
TypeDouble
()
extends
FPType
case
class
TypeRef
(
var
ty
:
Type
)
extends
AbstractObjRefType
case
class
TypeIRef
(
var
ty
:
Type
)
extends
AbstractRefType
case
class
TypeWeakRef
(
var
ty
:
Type
)
extends
AbstractObjRefType
case
class
TypeUPtr
(
var
ty
:
Type
)
extends
AbstractPointerType
case
class
TypeUFuncPtr
(
var
sig
:
FuncSig
)
extends
AbstractPointerType
case
class
TypeStruct
(
var
fieldTys
:
Seq
[
Type
])
extends
AbstractStructType
case
class
TypeArray
(
var
elemTy
:
Type
,
var
len
:
Long
)
extends
AbstractSeqType
case
class
TypeHybrid
(
var
fieldTys
:
Seq
[
Type
],
var
varTy
:
Type
)
extends
AbstractStructType
case
class
TypeArray
(
var
elemTy
:
Type
,
var
len
:
Long
)
extends
AbstractSeqType
case
class
TypeVector
(
var
elemTy
:
Type
,
var
len
:
Long
)
extends
AbstractSeqType
case
class
TypeVoid
()
extends
Type
case
class
TypeRef
(
var
ty
:
Type
)
extends
AbstractObjRefType
case
class
TypeIRef
(
var
ty
:
Type
)
extends
AbstractRefType
case
class
TypeWeakRef
(
var
ty
:
Type
)
extends
AbstractObjRefType
case
class
TypeTagRef64
()
extends
Type
case
class
TypeFuncRef
(
var
sig
:
FuncSig
)
extends
AbstractGenRefType
case
class
TypeThreadRef
()
extends
AbstractGenRefType
case
class
TypeStackRef
()
extends
AbstractGenRefType
case
class
TypeTagRef64
()
extends
Type
case
class
TypeVector
(
var
elemTy
:
Type
,
var
len
:
Long
)
extends
AbstractSeqType
case
class
TypeUPtr
(
var
ty
:
Type
)
extends
AbstractPointerType
case
class
TypeUFuncPtr
(
var
sig
:
FuncSig
)
extends
AbstractPointerType
case
class
TypeFrameCursorRef
()
extends
AbstractGenRefType
case
class
TypeIRNodeRef
()
extends
AbstractGenRefType
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment