From 965543a8342bc53c740209eadeb943b6e033cc1b Mon Sep 17 00:00:00 2001 From: =?utf8?q?Julien=20Pag=C3=A8s?= Date: Mon, 17 Nov 2014 01:13:04 +0100 Subject: [PATCH] nitvm: Implementing attribute access with direct access MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Signed-off-by: Julien Pagès --- src/vm.nit | 50 +++++++++++++++++++++++++++++++++++++++----------- 1 file changed, 39 insertions(+), 11 deletions(-) diff --git a/src/vm.nit b/src/vm.nit index 067c962..d745909 100644 --- a/src/vm.nit +++ b/src/vm.nit @@ -226,11 +226,18 @@ class VirtualMachine super NaiveInterpreter do assert recv isa MutableInstance - # Read the attribute value with perfect hashing - var id = mproperty.intro_mclassdef.mclass.vtable.id + var i: Instance - var i = read_attribute_ph(recv.internal_attributes, recv.vtable.internal_vtable, + if mproperty.intro_mclassdef.mclass.positions_attributes[recv.mtype.as(MClassType).mclass] != -1 then + # if this attribute class has an unique position for this receiver, then use direct access + i = read_attribute_sst(recv.internal_attributes, mproperty.absolute_offset) + else + # Otherwise, read the attribute value with perfect hashing + var id = mproperty.intro_mclassdef.mclass.vtable.id + + i = read_attribute_ph(recv.internal_attributes, recv.vtable.internal_vtable, recv.vtable.mask, id, mproperty.offset) + end # If we get a `MInit` value, throw an error if i == initialization_value then @@ -260,6 +267,18 @@ class VirtualMachine super NaiveInterpreter return res; `} + # Return the attribute value in `instance` with a direct access (SST) + # `instance` is the attributes array of the receiver + # `offset` is the absolute offset of this attribute + private fun read_attribute_sst(instance: Pointer, offset: Int): Instance `{ + /* We can make a direct access to the attribute value + because this attribute is always at the same position + for the class of this receiver */ + Instance res = ((Instance *)instance)[offset]; + + return res; + `} + # Replace in `recv` the value of the attribute `mproperty` by `value` redef fun write_attribute(mproperty: MAttribute, recv: Instance, value: Instance) do @@ -341,6 +360,9 @@ redef class MClass # Absolute offset of method from the beginning of the methods table var offset_methods = 0 + # The previous element in `superclasses` + var previous_parent: nullable MClass = null + if superclasses.length > 0 then previous_parent = superclasses[0] for parent in superclasses do if not parent.loaded then parent.make_vt(v) @@ -357,8 +379,16 @@ redef class MClass nb_methods.push(methods) nb_attributes.push(attributes) - # Update `positions_attributes` and `positions_methods` in `parent` - update_positions(offset_attributes, offset_methods, parent) + # Update `positions_attributes` and `positions_methods` in `parent`. + # If the position is invariant for this parent, store this position + # else store a special value (-1) + var pos_attr = -1 + var pos_meth = -1 + + if previous_parent.as(not null).positions_attributes[parent] == offset_attributes then pos_attr = offset_attributes + if previous_parent.as(not null).positions_methods[parent] == offset_methods then pos_meth = offset_methods + + parent.update_positions(pos_attr, pos_meth, self) offset_attributes += attributes offset_methods += methods @@ -427,8 +457,6 @@ redef class MClass nb_attributes_total.push(nb_introduced_attributes) # Save the offsets of self class - offset_attributes += nb_introduced_attributes - offset_methods += self_methods update_positions(offset_attributes, offset_methods, self) # Since we have the number of attributes for each class, calculate the delta @@ -547,13 +575,13 @@ redef class MClass return res end - # Update positions of self class in `parent` + # Update positions of the class `cl` # `attributes_offset`: absolute offset of introduced attributes # `methods_offset`: absolute offset of introduced methods - private fun update_positions(attributes_offsets: Int, methods_offset:Int, parent: MClass) + private fun update_positions(attributes_offsets: Int, methods_offset:Int, cl: MClass) do - parent.positions_attributes[self] = attributes_offsets - parent.positions_methods[self] = methods_offset + positions_attributes[cl] = attributes_offsets + positions_methods[cl] = methods_offset end end -- 1.7.9.5