Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Forcefully access private member [duplicate]

Say I am using an open source library of someone who does not know what they're doing well. (no encapsulation for important members) Really it's a coworker who's code I'm not allowed to modify, nor is he willing to modify it for me.

How can I forcefully access a private member without doing something like rewriting a fake class or modifying the original class?

I've tried things like #define private public, but the class file includes some standard namespace files and this will give a compilation error.

I've tried memory manipulation, but this requires member identification which isn't going to work. (See the following)

#define PX_ACCESS_PRIVATE( pObject, _Member ) ( static_cast< std::size_t >( pObject ) + static_cast< std::size_t >( &( ( decltype( pObject )( nullptr ) )->_Member ) ) )

Any ideas?

like image 300
man of asdf Avatar asked May 21 '19 07:05

man of asdf


1 Answers

Oh, you can break encapsulation gloriously. The type system has a loophole that can be leveraged to that effect. Explicit instantiations of templates don't do access checks on their arguments. You can pass anything there. So with a bit of plumbing...

template<typename Tag>
struct contraband_ {
    using type = typename Tag::type;
    inline static type ptr;
};

template<typename Tag>
inline auto const contraband = contraband_<Tag>::ptr;

template<typename Tag, typename Tag::type ptr_>
class steal : contraband_<Tag> {
    static inline const char filler = [] {
        steal::contraband_::ptr = ptr_;
        return '\0';
    }();
};

... you can have yourself indirect access to any private member via a pointer to it...

class foo {
    int x = 3;
};

struct x_tag { using type = int foo::*; };

template class steal<x_tag, &foo::x>;

int main()
{
    foo f;
    // return f.x; ill-formed! Private!
    return f.*contraband<x_tag>; // Okay!
}

See it live.

A fun exercise, but you really should work things out with your colleague instead of resorting to this. Use at your own peril.

like image 58
StoryTeller - Unslander Monica Avatar answered Sep 28 '22 12:09

StoryTeller - Unslander Monica