> What would be the best way to set the value of a ivar?
>
> Is there a reason that properties, a setter method, or KVC won't work? If
> you absolutely need direct access, can you make the ivar public?
>

Originally I found that code in some tests where the testing class does not
expose some properties. (Probably the original developer didn't want to
expose a getter/setter just for testing purposes(?)
KVO is the first thing that came to my mind, but I wanted to make 100% sure
I understand why/how it is bad.


>  > It is still unclear to me, how is that object_getInstanceVariable only
> > works for pointer-size things.
>
> You can see the implementation of this if you download the runtime from
> opensource.apple.com and look in objc-class.m.
> object_{get,set}InstanceVariable() simply call object_{get,set}Ivar(),
> which take 'id's. They don't pay attention to the type of the ivar; they
> compute its offset and then assume there's an id there. So, in effect,
> they're doing this:
>
> struct Foo {
>    Class isa;
>    ...blah;
>    BOOL _somevar;
>    ...blah;
> }
>
> id *varptr = (id *)&(someFoo->_somevar);
> *varptr = (void *)YES;
>
>
> In many cases this won't cause a problem because structure member
> alignment restrictions mean that the class's instance variables are all
> padded out to pointer-size boundaries. On a little-endian machine,
> retrieving the value and the padding, then casting to a narrower type, will
> (usually) actually do the right thing, as will the reverse operation ...
> but this only works through sheer chance. And if you change the types or
> ordering of your instance variables so that there isn't enough padding
> there (for example, if you have two BOOL instance variables, or perhaps if
> Apple changes the way the compiler lays out instance structures), then
> you'll start clobbering other ivars.
>
> However, you can if you want use ivar_getOffset() to get the offset of an
> instance variable within an instance. I assume that something like this
> would work:
>
>    id foo;
>    Ivar ivar = class_getInstanceVariable(...);
>    *(some_random_type *)( ((void *)foo) + ivar_getOffset(ivar) ) =
> some_value;
>
> (or maybe:  memcpy(((void *)foo) + ivar_getOffset(ivar), &some_value,
> sizeof(some_value);  )
>
> although I've never been desperate enough to try it. If you find yourself
> doing this, I strongly suggest you consider the path that has brought you
> to this point and whether you could have done something differently. :)
>
> If you look at objc-class.m, you'll see that there's another thing the
> above example doesn't do, which is interact correctly with ARC (or GC).
> Presumably that's OK, as long as your ivar isn't some compound type
> containing pointers ...
>
>
>
:)

-- 
Ignacio
_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
https://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to