fix (re)positioning when link exceptions are thrown
slow design, but sort of works
This commit is contained in:
parent
1c52ab6b67
commit
6be28e7f55
@ -11,26 +11,9 @@ module Risc
|
||||
@code = code
|
||||
end
|
||||
|
||||
# write into the given BinaryCode instance
|
||||
# LinkException may be thrown, possibly several times
|
||||
# So repeat until it works
|
||||
def assemble( instruction )
|
||||
not_ok = 1
|
||||
while(not_ok)
|
||||
begin
|
||||
#puts "Not ok #{not_ok}"
|
||||
#FIXME really need to reposition here, so jumps go right
|
||||
assemble_all(instruction)
|
||||
not_ok = false
|
||||
rescue LinkException
|
||||
not_ok += 1
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# Go through and assemble all instructions.
|
||||
# Assembly may cause LinkException, which is caught by caller
|
||||
def assemble_all( instruction )
|
||||
def assemble( instruction )
|
||||
@index = 1
|
||||
while(instruction)
|
||||
instruction.assemble(self)
|
||||
|
@ -79,14 +79,15 @@ module Risc
|
||||
cpu_init.set_position( 0 )
|
||||
#Positioned.set_position(cpu_init.first , 0)
|
||||
Positioned.set_position(binary_init,0)
|
||||
at = position_objects( binary_init.padded_length )
|
||||
@code_start = position_objects( binary_init.padded_length )
|
||||
# and then everything code
|
||||
position_code_from( at )
|
||||
position_code
|
||||
end
|
||||
|
||||
# go through everything that is not code (BinaryCode) and set position
|
||||
# padded_length is what determines an objects (byte) length
|
||||
def position_objects( at )
|
||||
# return final position that is stored in code_start
|
||||
def position_objects(at)
|
||||
# want to have the objects first in the executable
|
||||
objects.each do | id , objekt|
|
||||
next if objekt.is_a?( Parfait::BinaryCode) or objekt.is_a?( Risc::Label )
|
||||
@ -98,9 +99,13 @@ module Risc
|
||||
|
||||
# Position all BinaryCode.
|
||||
#
|
||||
# So that all code from one method is layed out linearly (for debuggin)
|
||||
# So that all code from one method is layed out linearly (for debugging)
|
||||
# we go through methods, and then through all codes from the method
|
||||
def position_code_from( at )
|
||||
#
|
||||
# start at @code_start. The method is called until
|
||||
# assembly stops throwing errors
|
||||
def position_code
|
||||
at = @code_start
|
||||
objects.each do |id , method|
|
||||
next unless method.is_a? Parfait::TypedMethod
|
||||
log.debug "POS1 #{method.name}:#{at.to_s(16)}"
|
||||
@ -119,16 +124,32 @@ module Risc
|
||||
|
||||
# Create Binary code for all methods and the initial jump
|
||||
# BinaryWriter handles the writing from instructions into BinaryCode objects
|
||||
#
|
||||
# current (poor) design throws an exception when the assembly can't fit
|
||||
# constant loads into one instruction.
|
||||
#
|
||||
def create_binary
|
||||
not_ok = 1
|
||||
while(not_ok)
|
||||
begin
|
||||
return do_create_binary
|
||||
rescue LinkException
|
||||
not_ok += 1
|
||||
puts "relink no #{not_ok}"
|
||||
position_code
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# have to retry until it works. Unfortunately (FIXME) jumps can go be both
|
||||
# directions, and so already assembled codes get wrong by moving/ inserting
|
||||
# instructions. And we end up assmebling all code again :-(
|
||||
def do_create_binary
|
||||
objects.each do |id , method|
|
||||
next unless method.is_a? Parfait::TypedMethod
|
||||
writer = BinaryWriter.new(method.binary)
|
||||
writer.assemble(method.cpu_instructions)
|
||||
end
|
||||
puts "CPU init"
|
||||
puts cpu_init.first.inspect[0...130]
|
||||
puts Parfait.object_space.get_init.risc_instructions.inspect[0...130]
|
||||
puts Parfait.object_space.get_init.cpu_instructions.inspect[0...130]
|
||||
BinaryWriter.new(binary_init).assemble(cpu_init)
|
||||
end
|
||||
|
||||
|
@ -9,7 +9,7 @@ module Risc
|
||||
|
||||
class TextWriter
|
||||
include Logging
|
||||
log_level :debug
|
||||
log_level :info
|
||||
|
||||
MARKER = 0xBAD4C0DE
|
||||
|
||||
@ -109,7 +109,7 @@ module Risc
|
||||
def write_object_check(object)
|
||||
log.debug "Write object #{object.class} #{object.inspect[0..100]}"
|
||||
#Only initially created codes are collected. Binary_init and method "tails" not
|
||||
if !@objects.has_key?(object.object_id) and !object.is_a?(Parfait::BinaryCode)
|
||||
if !@machine.objects.has_key?(object.object_id) and !object.is_a?(Parfait::BinaryCode)
|
||||
log.debug "Object at 0x#{Positioned.position(object).to_s(16)}:#{object.get_type()}"
|
||||
raise "Object(0x#{object.object_id.to_s(16)}) not linked #{object.inspect}"
|
||||
end
|
||||
|
Loading…
Reference in New Issue
Block a user