[Vm-dev] Problem understanding #cannotInterpret
Igor Stasenko
siguctua at gmail.com
Sun Jan 16 12:26:25 UTC 2011
AFAIK, #cannotInterpret: is sent to super
On 16 January 2011 11:50, Mariano Martinez Peck <marianopeck at gmail.com> wrote:
>
> Hi. There is something I don't understand about #cannotInterpret and maybe you can help me. Since I am not sure if this is more image side or vm, I did a cross post, sorry for that.
> Context: I am implementing proxies for classes. Since I want that a proxy loads back the original object when receiving the message #class, I have removed from the compiler the shortcut bytecode for class, with this:
>
> (ParseNode classVarNamed: 'StdSelectors') removeKey: #class ifAbsent: [].
>
> Now, my testcase is something like this:
>
> | inst proxy |
> "This is the simplest test that does the less assert as possible."
> inst := ClassWith1Var new.
> self assert: inst foo = 'foo'.
> proxy := ClassProxyInstVar new.
> proxy become: ClassWith1Var.
> "here I can send any message, it is just to load back the original class"
> inst basicIdentityHash.
> self assert: (inst class == ClassWith1Var).
> self assert: inst foo = 'foo'.
>
>
> ProtoObject subclass: #ClassProxyInstVar
> instanceVariableNames: 'superclass methodDict format actualClass'
> classVariableNames: ''
> poolDictionaries: ''
> category: 'Proxies'
>
>
> ClassProxyInstVar >> initialize
> super initialize.
> superclass := ProxySuperclass.
> methodDict := nil.
> actualClass := self
>
>
> So...with this i can use an instance of ClassProxyInstVar like a class. When an instance of the class receives a message, the methodDict will be in nil, and then the VM will send the #cannotInterpret. and there I want to put back the original class. Then I do:
>
> ProxySuperclass >> cannotInterpret: aMessage
> Transcript cr;
> show: 'cannotInterpret:';
> space;
> show: aMessage selector..
> self class restore.
> ^aMessage sendTo: self
>
> Now, this is working, but there is something I DO NOT UNSERSTAND. When I try to do the "inst basicIdentityHash" the VM will send the #cannotInterpret to ProxySuperclass because the methodDict was nil in ClassProxyInstVar. Ok, perfect. What I don't understand is how the method #cannotInterptet can be run perfeclty in this case, since I am doing a "self class restore" there. Remember I removed the shortcut bytecode, so #class is sent like any normal message. So, my question is, when sending "self class", why the VM doesn't call #cannotInterpter again like it did it when I did " inst basicIdentityHash." ? in other words...why the VM isn't entering in a loop ? There is something I am not seeing.
>
check the bytecode of method. A special sends, which shortcutted using
different bytecode.
To avoid self sends, which will lead to infinite loop, you can use the
message's lookupClass to send message to class side:
aMessage lookupClass restore.
> Thanks for any help in advance,
>
> Mariano
>
>
--
Best regards,
Igor Stasenko AKA sig.
More information about the Vm-dev
mailing list