1.1 --- a/encoders.py Thu Jul 12 18:53:58 2018 +0200
1.2 +++ b/encoders.py Sun Jul 22 12:14:48 2018 +0200
1.3 @@ -259,6 +259,14 @@
1.4 "__load_static_ignore", "__load_static_replace", "__load_static_test", "<test_context_static>",
1.5 )
1.6
1.7 +accessor_values = (
1.8 + "<accessor>",
1.9 + )
1.10 +
1.11 +accessor_ops = (
1.12 + "<accessor>", "<set_accessor>",
1.13 + )
1.14 +
1.15 context_values = (
1.16 "<context>",
1.17 )
1.18 @@ -278,7 +286,7 @@
1.19 "<accessor>", "<context>", "<name>", "<private_context>", "<target_accessor>"
1.20 )
1.21
1.22 -def encode_access_instruction(instruction, subs, context_index):
1.23 +def encode_access_instruction(instruction, subs, accessor_index, context_index):
1.24
1.25 """
1.26 Encode the 'instruction' - a sequence starting with an operation and
1.27 @@ -288,6 +296,9 @@
1.28 The 'subs' parameter defines a mapping of substitutions for special values
1.29 used in instructions.
1.30
1.31 + The 'accessor_index' parameter defines the position in local accessor
1.32 + storage for the referenced accessor or affected by an accessor operation.
1.33 +
1.34 The 'context_index' parameter defines the position in local context storage
1.35 for the referenced context or affected by a context operation.
1.36
1.37 @@ -304,7 +315,7 @@
1.38 if args:
1.39 converting_op = op
1.40 for arg in args:
1.41 - s, _substituted = encode_access_instruction_arg(arg, subs, converting_op, context_index)
1.42 + s, _substituted = encode_access_instruction_arg(arg, subs, converting_op, accessor_index, context_index)
1.43 substituted.update(_substituted)
1.44 a.append(s)
1.45 converting_op = None
1.46 @@ -326,6 +337,11 @@
1.47 elif op in static_ops:
1.48 a[-1] = "&%s" % a[-1]
1.49
1.50 + # Add accessor storage information to certain operations.
1.51 +
1.52 + if op in accessor_ops:
1.53 + a.insert(0, accessor_index)
1.54 +
1.55 # Add context storage information to certain operations.
1.56
1.57 if op in context_ops:
1.58 @@ -365,19 +381,19 @@
1.59
1.60 return "%s%s" % (op, argstr), substituted
1.61
1.62 -def encode_access_instruction_arg(arg, subs, op, context_index):
1.63 +def encode_access_instruction_arg(arg, subs, op, accessor_index, context_index):
1.64
1.65 """
1.66 Encode 'arg' using 'subs' to define substitutions, 'op' to indicate the
1.67 - operation to which the argument belongs, and 'context_index' to indicate any
1.68 - affected context storage.
1.69 + operation to which the argument belongs, and with 'accessor_index' and
1.70 + 'context_index' indicating any affected accessor and context storage.
1.71
1.72 Return a tuple containing the encoded form of 'arg' along with a collection
1.73 of any substituted values.
1.74 """
1.75
1.76 if isinstance(arg, tuple):
1.77 - encoded, substituted = encode_access_instruction(arg, subs, context_index)
1.78 + encoded, substituted = encode_access_instruction(arg, subs, accessor_index, context_index)
1.79 return attribute_to_reference(op, arg[0], encoded, substituted)
1.80
1.81 # Special values only need replacing, not encoding.
1.82 @@ -386,7 +402,7 @@
1.83
1.84 # Handle values modified by storage details.
1.85
1.86 - if arg in context_values:
1.87 + if arg in accessor_values or arg in context_values:
1.88 encoded = "%s(%s)" % (subs.get(arg), context_index)
1.89 else:
1.90 encoded = subs.get(arg)