redef class ScopeVisitor
- redef init(toolcontext)
+ redef init
do
super
if toolcontext.dbg != null then
redef fun check_errors
do
if dbg == null then
- super
+ return super
else
if messages.length > 0 then
message_sorter.sort(messages)
messages.clear
end
+ return not had_error
end
# -d
- var opt_debugger_mode: OptionBool = new OptionBool("Launches the target program with the debugger attached to it", "-d")
+ var opt_debugger_mode = new OptionBool("Launches the target program with the debugger attached to it", "-d")
# -c
- var opt_debugger_autorun: OptionBool = new OptionBool("Launches the target program with the interpreter, such as when the program fails, the debugging prompt is summoned", "-c")
+ var opt_debugger_autorun = new OptionBool("Launches the target program with the interpreter, such as when the program fails, the debugging prompt is summoned", "-c")
redef init
do
# Auto continues the execution until the end or until an error is encountered
var autocontinue = false
+ redef type FRAME: InterpreterFrame
+
#######################################################################
## Execution of statement function ##
#######################################################################
end
# Same as a regular call but for a runtime injected module
- #
fun rt_call(mpropdef: MMethodDef, args: Array[Instance]): nullable Instance
do
- args = call_commons(mpropdef, args)
- return rt_call_without_varargs(mpropdef, args)
- end
-
- # Common code to call and this function
- #
- # Call only executes the variadic part, this avoids
- # double encapsulation of variadic parameters into an Array
- fun rt_call_without_varargs(mpropdef: MMethodDef, args: Array[Instance]): nullable Instance
- do
if self.modelbuilder.toolcontext.opt_discover_call_trace.value and not self.discover_call_trace.has(mpropdef) then
self.discover_call_trace.add mpropdef
self.debug("Discovered {mpropdef}")
assert args.length == mpropdef.msignature.arity + 1 else debug("Invalid arity for {mpropdef}. {args.length} arguments given.")
# Look for the AST node that implements the property
- var mproperty = mpropdef.mproperty
- if self.modelbuilder.mpropdef2npropdef.has_key(mpropdef) then
- var npropdef = self.modelbuilder.mpropdef2npropdef[mpropdef]
- self.parameter_check(npropdef, mpropdef, args)
- if npropdef isa AMethPropdef then
- return npropdef.rt_call(self, mpropdef, args)
- else
- print "Error, invalid propdef to call at runtime !"
- return null
- end
- else if mproperty.name == "init" then
- var nclassdef = self.modelbuilder.mclassdef2nclassdef[mpropdef.mclassdef]
- self.parameter_check(nclassdef, mpropdef, args)
- return nclassdef.call(self, mpropdef, args)
+ var node = modelbuilder.mpropdef2node(mpropdef)
+ if node isa AMethPropdef then
+ self.parameter_check(node, mpropdef, args)
+ return node.rt_call(self, mpropdef, args)
+ else if node isa AClassdef then
+ self.parameter_check(node, mpropdef, args)
+ return node.call(self, mpropdef, args)
else
fatal("Fatal Error: method {mpropdef} not found in the AST")
abort
var mmod = e.mmodule
if mmod != null then
self.mainmodule = mmod
- var local_classdefs = mmod.mclassdefs
var sys_type = mmod.sys_type
if sys_type == null then
print "Fatal error, cannot find Class Sys !\nAborting"
var identifiers_in_instruction = get_identifiers_in_current_instruction(n.location.text)
for i in identifiers_in_instruction do
- var variable = seek_variable(i, frame)
for j in self.traces do
if j.is_variable_traced_in_frame(i, frame) then
n.debug("Traced variable {i} used")
if parts[1] == "*" then
var map_of_instances = frame.map
- var keys = map_of_instances.iterator
-
var self_var = seek_variable("self", frame)
print "self: {self_var.to_s}"
# If the variable *variable_name* is an argument of the function being executed in the frame *frame*
# The function returns its position in the arguments
# Else, it returns -1
- private fun get_position_of_variable_in_arguments(frame: Frame, variable_name: String): Int
+ private fun get_position_of_variable_in_arguments(frame: FRAME, variable_name: String): Int
do
var identifiers = get_identifiers_in_current_instruction(get_function_arguments(frame.mpropdef.location.text))
for i in [0 .. identifiers.length-1] do
var trigger_char_escape = false
var trigger_string_escape = false
- var trigger_concat_in_string = false
for i in instruction.chars do
if trigger_char_escape then
if i == '\'' then trigger_char_escape = false
else if trigger_string_escape then
if i == '{' then
- trigger_concat_in_string = true
trigger_string_escape = false
else if i == '\"' then trigger_string_escape = false
else
else if i == '\"' then
trigger_string_escape = true
else if i == '}' then
- trigger_concat_in_string = false
trigger_string_escape = true
else
if instruction_buffer.length > 0 and not instruction_buffer.is_numeric and not (instruction_buffer.chars[0] >= 'A' and instruction_buffer.chars[0] <= 'Z') then result_array.push(instruction_buffer.to_s)
#######################################################################
# Seeks a variable from the current frame called 'variable_path', can introspect complex objects using function get_variable_in_mutable_instance
- private fun seek_variable(variable_path: String, frame: Frame): nullable Instance
+ private fun seek_variable(variable_path: String, frame: FRAME): nullable Instance
do
var full_variable = variable_path.split_with(".")
end
# Gets a variable 'variable_name' contained in the frame 'frame'
- private fun get_variable_in_frame(variable_name: String, frame: Frame): nullable Instance
+ private fun get_variable_in_frame(variable_name: String, frame: FRAME): nullable Instance
do
if variable_name == "self" then
if frame.arguments.length >= 1 then return frame.arguments.first
do
var collection_length_attribute = get_attribute_in_mutable_instance(collection, "length")
- var real_collection_length: nullable Int = null
-
if collection_length_attribute != null then
var primitive_length_instance = collection.attributes[collection_length_attribute]
if primitive_length_instance isa PrimitiveInstance[Int] then
# Not supposed to be used by anyone else than the Debugger.
private fun rt_call(v: Debugger, mpropdef: MMethodDef, args: Array[Instance]): nullable Instance
do
- var f = new Frame(self, self.mpropdef.as(not null), args)
+ var f = new InterpreterFrame(self, self.mpropdef.as(not null), args)
var curr_instances = v.frame.map
for i in curr_instances.keys do
f.map[i] = curr_instances[i]
private class TraceObject
# Map of the local names bound to a frame
- var trace_map: HashMap[Frame, String]
+ var trace_map = new HashMap[Frame, String]
+
# Decides if breaking or printing statement when the variable is encountered
var break_on_encounter: Bool
- init(break_on_encounter: Bool)
- do
- trace_map = new HashMap[Frame, String]
- self.break_on_encounter = break_on_encounter
- end
-
# Adds the local alias for a variable and the frame bound to it
fun add_frame_variable(frame: Frame, variable_name: String)
do