Pointer to a member's member - c++

C++ allows one to define pointers to members of a class like:
struct A
{
int i;
};
void a()
{
int A::*p = &A::i;
}
but what if I want a pointer to a member that's on a deeper "level" like this?
struct A
{
int i;
struct B{int j;};
B b;
};
void a()
{
int A::*p = &A::b::j;
}
Theoretically it seems that if pointer to members are compiled to offets from the start of the object this could have been easily supported by the language although things like virtual/diamond inheritance would probably make this far too complicated
What's the easiest way to achieve that without performance penalties or undefined behaviour?
My first idea was to just use an offset and work with raw pointers on the object but that seems like it might not be defined behaviour and would also make it impossible for the compiler to detect if I'm pointing to actual fields with the correct type

You can only define a pointer to data member for a given class for actual data members of that class.
That you have a nested class type declared is no special case here: you can extract a pointer a data member of A::B and apply the pointer to data member onto the b member (of type A::B) of an A object:
#include <iostream>
struct A {
int i;
struct B{ int j; };
B b;
};
int main() {
A a{1, {42}}; // a.b.j is 42
// Declare a pointer-to-data-member of B (which
// is a nested class in A).
int A::B::*p = &A::B::j;
// Apply to an actual 'B' object to retrieve
// the data member value pointed to.
std::cout << a.b.*p; // 42
}
However if you want to apply a pointer to data member on an A object, the best you can get is a pointer to the data member b.
You could always use nested pointer to data member pointers for a nested class objects:
int main() {
A a{1, {42}}; // a.b.j is 42
A::B A::*pb = &A::b;
int A::B::*pj = &A::B::j;
std::cout << (a.*pb).*pj; // 42
}

Just for the sake of showing that what I want isn't impossible in C++ I'll provide following solution:
// Example program
#include <iostream>
#include <string>
#include <memory>
template<typename T, typename P>
class MemberPointer
{
public:
virtual P& access(T& obj) = 0;
};
template<typename T, typename P>
class SimpleMemberPointer : public MemberPointer<T, P>
{
P T::*ptr;
public:
SimpleMemberPointer(P T::*ptr): ptr(ptr){}
P& access(T& obj) override
{
return obj.*ptr;
}
using object = T;
using property = P;
};
template<typename Ptr, typename P>
class NestedMemberPointer : public MemberPointer<typename Ptr::object, P>
{
public:
using object = typename Ptr::object;
using property = P;
private:
using intermediate = typename Ptr::property;
Ptr parent;
P intermediate::*ptr;
public:
NestedMemberPointer(Ptr parent, P intermediate::*ptr): parent(parent), ptr(ptr){}
P& access(object& obj) override
{
return parent.access(obj).*ptr;
}
};
Sample usage code:
class Person
{
public:
std::string name;
struct Address{
std::string street;
}address;
};
void test(Person &p, MemberPointer<Person, std::string> &ptr)
{
std::cout << ptr.access(p) << std::endl;
}
int main()
{
Person p{"Jim", {"Street"}};
std::unique_ptr<MemberPointer<Person, std::string>> ptr = std::make_unique<SimpleMemberPointer<Person, std::string>>(&Person::name);
std::unique_ptr<MemberPointer<Person, std::string>> ptr2 = std::make_unique<NestedMemberPointer<SimpleMemberPointer<Person, Person::Address>, std::string>>(SimpleMemberPointer<Person, Person::Address>{&Person::address}, &Person::Address::street);
test(p, *ptr);
test(p, *ptr2);
}
ptr and ptr2 are variables of the same type despite refering to members in different depth, just as I want.
If executed the program prints
Jim
Street
Now the only problem with this solution is that it's not really simple and also not very performant given that it requires rather complicated variable definitions and needs polymorphism to differentiate on different paths

Related

Why would I want a .* operator in C++?

I recently found out that the .* operator (and the closely related ->* operator) exists in C++. (See this question.)
Seems neat at first, but why would I ever need such a thing? The two answers in the linked question provided contrived examples which would benefit from a direct function call.
Where a direct function call is inconvenient, a function object could be used instead, like the lambda functions that may be used in std::sort. This removes a level of indirection and hence would be more performant than using .*.
The linked question also mentioned a simplified version of this example:
struct A {
int a;
int b;
};
void set_member(A& obj, int A::* ptr, int val){
obj.*ptr = val;
}
int main()
{
A obj;
set_member(obj, &A::b, 5);
set_member(obj, &A::a, 7);
// Both members of obj are now assigned
}
But it's pretty trivial (perhaps even better practice because it's cleaner and isn't unnecessarily constrained to members of A) to do this instead:
struct A {
int a;
int b;
};
void set_me(int& out, int val){
out = val;
}
int main()
{
A obj;
set_me(obj.b, 5);
set_me(obj.a, 7);
// Both members of obj are now assigned
}
In conclusion, a pointer-to-member-function might be replaced by a function object, and a pointer-to-member-variable might be replaced by a direct reference of said variable or a function object. Doing so might also increase the efficiency of the code due to one less indirection.
This question only provides examples where my conclusion stands, so it does not answer my question.
Apart from interfacing legacy code which uses .* (in which there would be no choice at all), when, really, would I want to use .*?
Your example is too trivial to be illustrative. Consider a bit more complicated one
struct A {
int a;
int b;
};
void set_n_members(A objs[], unsigned n, int A::* ptr, int val)
{
for (unsigned i = 0; i < n; ++i)
objs[i].*ptr = val;
}
int main()
{
A objs[100];
set_n_members(objs, 100, &A::b, 5);
set_n_members(objs, 100, &A::a, 7);
}
How would you rewrite this without int A::* ptr and without inducing code bloat?
You could create collections of pointers to members and iterate over them. E.g.:
struct UserStrings
{
std::string first_name;
std::string surname;
std::string preferred_name;
std::string address;
};
...
std::array<std::string UserStrings::*, 4> str_cols = { &UserStrings::first_name, &UserStrings::surname, &UserStrings::preferred_name, &UserStrings::address };
std::vector<UserStrings> users = GetUserStrings();
for (auto& user : users)
{
for (auto& column : str_cols)
{
SanitizeForSQLQuery(user.*column);
}
}
It is used to implement std::mem_fn, which is used to implement std::function.
The following code shows how the ->* operator works in a naive Function class implemention.
Similarly, you can implement a member invoker class using the .* operator and a class reference.
#include <iostream>
class A
{
public:
void greet()
{
std::cout << "Hello world"<<std::endl;
}
};
template<typename R, typename ...TArgs>
class Invoker
{
public:
virtual R apply(TArgs&& ...args) = 0;
};
template<typename C, typename R, typename ...TArgs>
class MemberInvoker :public Invoker<R, TArgs...>
{
protected:
C* sender;
R(C::*function)(TArgs ...args);
public:
MemberInvoker(C* _sender, R(C::*_function)(TArgs ...args))
:sender(_sender)
, function(_function)
{
}
virtual R apply(TArgs&& ...args) override
{
return (sender->*function)(std::forward<TArgs>(args)...);
}
};
template<typename T>
class Func
{
};
template<typename R, typename ...TArgs>
class Func<R(TArgs...)>
{
public:
Invoker<R,TArgs...>* invoker=nullptr;
template<typename C>
Func(C* sender, R(C::*function)(TArgs...))
{
invoker =new MemberInvoker<C, R, TArgs...>(sender, function);
}
R operator()(TArgs&& ...args)
{
return invoker->apply(std::forward<TArgs>(args)...);
}
~Func()
{
if (invoker)
{
delete invoker;
invoker = nullptr;
}
}
};
int main()
{
A a;
Func<void()> greetFunc(&a, &A::greet);
greetFunc();
system("PAUSE");
}
Let's say you wanted to write a LINQ style library for C++ that could be used something like this:
struct Person
{
std::string first_name;
std::string last_name;
std::string occupation;
int age;
int children;
};
std::vector<Person> people = loadPeople();
std::vector<std::string> result = from(people)
.where(&Person::last_name == "Smith")
.where(&Person::age > 30)
.select("%s %s",&Person::first_name,&Person::last_name);
for(std::string person : result) { ... };
Under the covers, the where function accepts an expression tree containing a pointer to member (among other stuff) and is applied to each vector item looking for one that matches. The select statement accepts a format string and some pointer to members and does an sprintf style formatting of whichever vector items get through the where statements.
I have written something like this, and there are several others out there that do it slightly differently (Is there a LINQ library for C++?). Pointer-to-member allows the library user to specify whichever members of their struct that they want and the library doesn't need to know anything about what they might do.

C++: can you force the access to a private member of a class? [duplicate]

Disclaimer
Yes, I am fully aware that what I am asking about is totally stupid and that anyone who would wish to try such a thing in production code should be fired and/or shot. I'm mainly looking to see if can be done.
Now that that's out of the way, is there any way to access private class members in C++ from outside the class? For example, is there any way to do this with pointer offsets?
(Naive and otherwise non-production-ready techniques welcome)
Update
As noted in the comments, I asked this question because I wanted to write a blog post on over-encapsulation (and how it affects TDD). I wanted to see if there was a way to say "using private variables isn't a 100% reliable way to enforce encapsulation, even in C++." At the end, I decided to focus more on how to solve the problem rather than why it's a problem, so I didn't feature some of the stuff brought up here as prominently as I had planned, but I still left a link.
At any rate, if anyone's interested in how it came out, here it is: Enemies of Test Driven Development part I: encapsulation (I suggest reading it before you decide that I'm crazy).
If the class contains any template member functions you can specialize that member function to suit your needs. Even if the original developer didn't think of it.
safe.h
class safe
{
int money;
public:
safe()
: money(1000000)
{
}
template <typename T>
void backdoor()
{
// Do some stuff.
}
};
main.cpp:
#include <safe.h>
#include <iostream>
class key;
template <>
void safe::backdoor<key>()
{
// My specialization.
money -= 100000;
std::cout << money << "\n";
}
int main()
{
safe s;
s.backdoor<key>();
s.backdoor<key>();
}
Output:
900000
800000
I've added an entry to my blog (see below) that shows how it can be done. Here is an example on how you use it for the following class
struct A {
private:
int member;
};
Just declare a struct for it where you describe it and instantiate the implementation class used for robbery
// tag used to access A::member
struct A_member {
typedef int A::*type;
friend type get(A_member);
};
template struct Rob<A_member, &A::member>;
int main() {
A a;
a.*get(A_member()) = 42; // write 42 to it
std::cout << "proof: " << a.*get(A_member()) << std::endl;
}
The Rob class template is defined like this, and needs only be defined once, regardless how many private members you plan to access
template<typename Tag, typename Tag::type M>
struct Rob {
friend typename Tag::type get(Tag) {
return M;
}
};
However, this doesn't show that c++'s access rules aren't reliable. The language rules are designed to protect against accidental mistakes - if you try to rob data of an object, the language by-design does not take long ways to prevent you.
The following is sneaky, illegal, compiler-dependent, and may not work depending on various implementation details.
#define private public
#define class struct
But it is an answer to your OP, in which you explicitly invite a technique which, and I quote, is "totally stupid and that anyone who would wish to try such a thing in production code should be fired and/or shot".
Another technique is to access private member data, by contructing pointers using hard-coded/hand-coded offsets from the beginning of the object.
Hmmm, don't know if this would work, but might be worth a try. Create another class with the same layout as the object with private members but with private changed to public. Create a variable of pointer to this class. Use a simple cast to point this to your object with private members and try calling a private function.
Expect sparks and maybe a crash ;)
class A
{
int a;
}
class B
{
public:
int b;
}
union
{
A a;
B b;
};
That should do it.
ETA: It will work for this sort of trivial class, but as a general thing it won't.
TC++PL Section C.8.3: "A class with a constructor, destructor, or copy operation cannot be the type of a union member ... because the compiler would not know which member to destroy."
So we're left with the best bet being to declare class B to match A's layout and hack to look at a class's privates.
If you can get a pointer to a member of a class you can use the pointer no matter what the access specifiers are (even methods).
class X;
typedef void (X::*METHOD)(int);
class X
{
private:
void test(int) {}
public:
METHOD getMethod() { return &X::test;}
};
int main()
{
X x;
METHOD m = x.getMethod();
X y;
(y.*m)(5);
}
Of course my favorite little hack is the friend template back door.
class Z
{
public:
template<typename X>
void backDoor(X const& p);
private:
int x;
int y;
};
Assuming the creator of the above has defined backDoor for his normal uses. But you want to access the object and look at the private member variables. Even if the above class has been compiled into a static library you can add your own template specialization for backDoor and thus access the members.
namespace
{
// Make this inside an anonymous namespace so
// that it does not clash with any real types.
class Y{};
}
// Now do a template specialization for the method.
template<>
void Z::backDoor<Y>(Y const& p)
{
// I now have access to the private members of Z
}
int main()
{
Z z; // Your object Z
// Use the Y object to carry the payload into the method.
z.backDoor(Y());
}
It's definately possible to access private members with a pointer offset in C++. Lets assume i had the following type definition that I wanted access to.
class Bar {
SomeOtherType _m1;
int _m2;
};
Assuming there are no virtual methods in Bar, The easy case is _m1. Members in C++ are stored as offsets of the memory location of the object. The first object is at offset 0, the second object at offset of sizeof(first member), etc ...
So here is a way to access _m1.
SomeOtherType& GetM1(Bar* pBar) {
return*(reinterpret_cast<SomeOtherType*>(pBar));
}
Now _m2 is a bit more difficult. We need to move the original pointer sizeof(SomeOtherType) bytes from the original. The cast to char is to ensure that I am incrementing in a byte offset
int& GetM2(Bar* pBar) {
char* p = reinterpret_cast<char*>(pBar);
p += sizeof(SomeOtherType);
return *(reinterpret_cast<int*>(p));
}
This answer is based on the exact concept demonstrated by #Johannes's answer/blog, as that seems to be the only "legitimate" way. I have converted that example code into a handy utility. It's easily compatible with C++03 (by implementing std::remove_reference & replacing nullptr).
Library
#define CONCATE_(X, Y) X##Y
#define CONCATE(X, Y) CONCATE_(X, Y)
#define ALLOW_ACCESS(CLASS, MEMBER, ...) \
template<typename Only, __VA_ARGS__ CLASS::*Member> \
struct CONCATE(MEMBER, __LINE__) { friend __VA_ARGS__ CLASS::*Access(Only*) { return Member; } }; \
template<typename> struct Only_##MEMBER; \
template<> struct Only_##MEMBER<CLASS> { friend __VA_ARGS__ CLASS::*Access(Only_##MEMBER<CLASS>*); }; \
template struct CONCATE(MEMBER, __LINE__)<Only_##MEMBER<CLASS>, &CLASS::MEMBER>
#define ACCESS(OBJECT, MEMBER) \
(OBJECT).*Access((Only_##MEMBER<std::remove_reference<decltype(OBJECT)>::type>*)nullptr)
API
ALLOW_ACCESS(<class>, <member>, <type>);
Usage
ACCESS(<object>, <member>) = <value>; // 1
auto& ref = ACCESS(<object>, <member>); // 2
Demo
struct X {
int get_member () const { return member; };
private:
int member = 0;
};
ALLOW_ACCESS(X, member, int);
int main() {
X x;
ACCESS(x, member) = 42;
std::cout << "proof: " << x.get_member() << std::endl;
}
If you know how your C++ compiler mangles names, yes.
Unless, I suppose, it's a virtual function. But then, if you know how your C++ compiler builds the VTABLE ...
Edit: looking at the other responses, I realize that I misread the question and thought it was about member functions, not member data. However, the point still stands: if you know how your compiler lays out data, then you can access that data.
cool question btw... here's my piece:
using namespace std;
class Test
{
private:
int accessInt;
string accessString;
public:
Test(int accessInt,string accessString)
{
Test::accessInt=accessInt;
Test::accessString=accessString;
}
};
int main(int argnum,char **args)
{
int x;
string xyz;
Test obj(1,"Shit... This works!");
x=((int *)(&obj))[0];
xyz=((string *)(&obj))[1];
cout<<x<<endl<<xyz<<endl;
return 0;
}
Hope this helps.
As an alternative to template backdoor method you can use template backdoor class. The difference is that you don't need to put this backdoor class into public area of the class your are going to test. I use the fact that many compilers allow nested classes to access private area of enclosing class (which is not exactly 1998 standard but considered to be "right" behaviour). And of course in C++11 this became legal behaviour.
See this example:
#include <vector>
#include <cassert>
#include <iostream>
using std::cout;
using std::endl;
///////// SystemUnderTest.hpp
class SystemUnderTest
{
//...put this 'Tested' declaration into private area of a class that you are going to test
template<typename T> class Tested;
public:
SystemUnderTest(int a): a_(a) {}
private:
friend std::ostream& operator<<(std::ostream& os, const SystemUnderTest& sut)
{
return os << sut.a_;
}
int a_;
};
/////////TestFramework.hpp
class BaseTest
{
public:
virtual void run() = 0;
const char* name() const { return name_; }
protected:
BaseTest(const char* name): name_(name) {}
virtual ~BaseTest() {}
private:
BaseTest(const BaseTest&);
BaseTest& operator=(const BaseTest&);
const char* name_;
};
class TestSuite
{
typedef std::vector<BaseTest*> Tests;
typedef Tests::iterator TIter;
public:
static TestSuite& instance()
{
static TestSuite TestSuite;
return TestSuite;
}
void run()
{
for(TIter iter = tests_.begin(); tests_.end() != iter; ++iter)
{
BaseTest* test = *iter;
cout << "Run test: " << test->name() << endl;
test->run();
}
}
void addTest(BaseTest* test)
{
assert(test);
cout << "Add test: " << test->name() << endl;
tests_.push_back(test);
}
private:
std::vector<BaseTest*> tests_;
};
#define TEST_CASE(SYSTEM_UNDER_TEST, TEST_NAME) \
class TEST_NAME {}; \
template<> \
class SYSTEM_UNDER_TEST::Tested<TEST_NAME>: public BaseTest \
{ \
Tested(): BaseTest(#SYSTEM_UNDER_TEST "::" #TEST_NAME) \
{ \
TestSuite::instance().addTest(this); \
} \
void run(); \
static Tested instance_; \
}; \
SYSTEM_UNDER_TEST::Tested<TEST_NAME> SYSTEM_UNDER_TEST::Tested<TEST_NAME>::instance_; \
void SYSTEM_UNDER_TEST::Tested<TEST_NAME>::run()
//...TestSuiteForSystemUnderTest.hpp
TEST_CASE(SystemUnderTest, AccessPrivateValueTest)
{
SystemUnderTest sut(23);
cout << "Changed private data member from " << sut << " to ";
sut.a_ = 12;
cout << sut << endl;
}
//...TestRunner.cpp
int main()
{
TestSuite::instance().run();
}
Beside #define private public you can also #define private protected and then define some foo class as descendant of wanted class to have access to it's (now protected) methods via type casting.
just create your own access member function to extend the class.
To all the people suggesting "#define private public":
This kind of thing is illegal. The standard forbids defining/undef-ing macros that are lexically equivalent to reserved language keywords. While your compiler probably won't complain (I've yet to see a compiler that does), it isn't something that's a "Good Thing" to do.
It's actually quite easy:
class jail {
int inmate;
public:
int& escape() { return inmate; }
};
"using private variables isn't a 100% reliable way to enforce encapsulation, even in C++."
Really? You can disassemble the library you need, find all the offsets needed and use them.
That will give you an ability to change any private member you like... BUT!
You can't access private members without some dirty hacking.
Let us say that writing const won't make your constant be really constant, 'cause you can
cast const away or just use it's address to invalidate it. If you're using MSVC++ and you specified "-merge:.rdata=.data" to a linker, the trick will work without any memory access faults.
We can even say that writing apps in C++ is not reliable way to write programs, 'cause resulting low level code may be patched from somewhere outside when your app is running.
Then what is reliable documented way to enforce encapsulation? Can we hide the data somewhere in RAM and prevent anything from accessing them except our code? The only idea I have is to encrypt private members and backup them, 'cause something may corrupt those members.
Sorry if my answer is too rude, I didn't mean to offend anybody, but I really don't think that statement is wise.
since you have an object of required class I am guessing that you have declaration of class.
Now what you can do is declare another class with same members but keep all of there access specifiers as public.
For example previous class is:
class Iamcompprivate
{
private:
Type1 privateelement1;
Typ2 privateelement2;
...
public:
somefunctions
}
you can declare a class as
class NowIampublic
{
**public:**
Type1 privateelement1;
Type2 privateelement2;
...
somefunctions
};
Now all you need to do is cast pointer of class Iamcompprivate into an pointer of class NowIampublic and use them as U wish.
Example:
NowIampublic * changetopublic(Iamcompprivate *A)
{
NowIampublic * B = (NowIampublic *)A;
return B;
}
By referencing to *this you enable a backdoor to all private data within an object.
class DumbClass
{
private:
int my_private_int;
public:
DumbClass& backdoor()
{
return *this;
}
}
Quite often a class provides mutator methods to private data (getters and setters).
If a class does provide a getter that returns a const reference (but no setter), then you can just const_cast the return value of the getter, and use that as an l-value:
class A {
private:
double _money;
public:
A(money) :
_money(money)
{}
const double &getMoney() const
{
return _money;
}
};
A a(1000.0);
const_cast<double &>(a.getMoney()) = 2000.0;
I've used another useful approach (and solution) to access a c++ private/protected member.
The only condition is that you are able to inherit from the class you want to access.
Then all credit goes to reinterpret_cast<>().
A possible problem is that it won't work if you insert a virtual function, which will modify virtual table, and so, object size/alignment.
class QObject
{
Q_OBJECT
Q_DECLARE_PRIVATE(QObject)
void dumpObjectInfo();
void dumpObjectTree();
...
protected:
QScopedPointer<QObjectData> d_ptr;
...
}
class QObjectWrapper : public QObject
{
public:
void dumpObjectInfo2();
void dumpObjectTree2();
};
Then you just need to use the class as follows:
QObject* origin;
QObjectWrapper * testAccesor = reinterpret_cast<QObjectWrapper *>(origin);
testAccesor->dumpObjectInfo2();
testAccesor->dumpObjectTree2();
My original problem was as follows: I needed a solution that won't imply recompiling QT libraries.
There are 2 methods in QObject, dumpObjectInfo() and dumpObjectTree(), that
just work if QT libs are compiled in debug mode, and they of course need access to d_ptr proteted member (among other internal structures).
What I did was to use the proposed solution to reimplement (with copy and paste) those methods in dumpObjectInfo2() and dumpObjectTree2() in my own class (QObjectWrapper) removing those debug preprocesor guards.
The following code accesses and modifies a private member of the class using a pointer to that class.
#include <iostream>
using namespace std;
class A
{
int private_var;
public:
A(){private_var = 0;}//initialized to zero.
void print(){cout<<private_var<<endl;}
};
int main()
{
A ob;
int *ptr = (int*)&ob; // the pointer to the class is typecast to a integer pointer.
(*ptr)++; //private variable now changed to 1.
ob.print();
return 0;
}
/*prints 1. subsequent members can also be accessed by incrementing the pointer (and
type casting if necessary).*/
study purpose only....
try this ....may be helpfull i guess.....
this program can access the private data just by knowing the values...
//GEEK MODE....;)
#include<iostream.h>
#include<conio.h>
class A
{
private :int iData,x;
public: void get() //enter the values
{cout<<"Enter iData : ";
cin>>iData;cout<<"Enter x : ";cin>>x;}
void put() //displaying values
{cout<<endl<<"sum = "<<iData+x;}
};
void hack(); //hacking function
void main()
{A obj;clrscr();
obj.get();obj.put();hack();obj.put();getch();
}
void hack() //hack begins
{int hck,*ptr=&hck;
cout<<endl<<"Enter value of private data (iData or x) : ";
cin>>hck; //enter the value assigned for iData or x
for(int i=0;i<5;i++)
{ptr++;
if(*ptr==hck)
{cout<<"Private data hacked...!!!\nChange the value : ";
cin>>*ptr;cout<<hck<<" Is chaged to : "<<*ptr;
return;}
}cout<<"Sorry value not found.....";
}
Inspired by #Johannes Schaub - litb, the following code may be a bit easier to digest.
struct A {
A(): member(10){}
private:
int get_member() { return member;}
int member;
};
typedef int (A::*A_fm_ptr)();
A_fm_ptr get_fm();
template< A_fm_ptr p>
struct Rob{
friend A_fm_ptr get_fm() {
return p;
}
};
template struct Rob< &A::get_member>;
int main() {
A a;
A_fm_ptr p = get_fm();
std::cout << (a.*p)() << std::endl;
}
Well, with pointer offsets, it's quite easy. The difficult part is finding the offset:
other.hpp
class Foo
{
public:
int pub = 35;
private:
int foo = 5;
const char * secret = "private :)";
};
main.cpp
#include <iostream>
#include <fstream>
#include <string>
#include <regex>
#include "other.hpp"
unsigned long long getPrivOffset(
const char * klass,
const char * priv,
const char * srcfile
){
std::ifstream read(srcfile);
std::ofstream write("fork.hpp");
std::regex r ("private:");
std::string line;
while(getline(read, line))
// make all of the members public
write << std::regex_replace(line, r, "public:") << '\n';
write.close();
read.close();
// find the offset, using the clone object
std::ofstream phony("phony.cpp");
phony <<
"#include <iostream>\n"
"#include <fstream>\n"
"#include \"fork.hpp\"\n"
"int main() {\n";
phony << klass << " obj;\n";
// subtract to find the offset, the write it to a file
phony <<
"std::ofstream out(\"out.txt\");\n out << (((unsigned char *) &(obj."
<< priv << ")) -((unsigned char *) &obj)) << '\\n';\nout.close();";
phony << "return 0;\n}";
phony.close();
system(
"clang++-7 -o phony phony.cpp\n"
"./phony\n"
"rm phony phony.cpp fork.hpp");
std::ifstream out("out.txt");
// read the file containing the offset
getline(out, line);
out.close();
system("rm out.txt");
unsigned long long offset = strtoull(line.c_str(), NULL, 10);
return offset;
}
template <typename OutputType, typename Object>
OutputType hack(
Object obj,
const char * objectname,
const char * priv_method_name,
const char * srcfile
) {
unsigned long long o = getPrivOffset(
objectname,
priv_method_name,
srcfile
);
return *(OutputType *)(((unsigned char *) (&obj)+o));
}
#define HACK($output, $object, $inst, $priv, $src)\
hack <$output, $object> (\
$inst,\
#$object,\
$priv,\
$src)
int main() {
Foo bar;
std::cout << HACK(
// output type
const char *,
// type of the object to be "hacked"
Foo,
// the object being hacked
bar,
// the desired private member name
"secret",
// the source file of the object's type's definition
"other.hpp"
) << '\n';
return 0;
}
clang++ -o main main.cpp
./main
output:
private :)
You could also use reinterpret_cast.
Maybe some pointer arithmetics can do it
#pragma pack(1)
class A
{
int x{0};
char c{0};
char s[8]{0};
public:
void display()
{
print(x);
print(c);
print(s);
};
};
int main(void)
{
A a;
int *ptr2x = (int *)&a;
*ptr2x = 10;
char *ptr2c = (char *)ptr2x+4;
*ptr2c = 'A';
char *ptr2s = (char *)ptr2c+1;
strcpy(ptr2s ,"Foo");
a.display();
}
class Test{
int a;
alignas(16) int b;
int c;
};
Test t;
method A : intrusive mood.
since we can access source code and recomplie it, we can use
many other way like friend class to access private member, they are all legal backdoor.
method B : brute mood.
int* ptr_of_member_c = reinterpret_cast<int*>(reinterpret_cast<char*>(&t) + 20);
we use a magic number (20) , and It's not always right. When the layout of class Test changed, the magic number is a big bug source.
method C : super hacker mood.
is there any non-intrusive and non-brute mood ?
since the class Test's layout infomation is hide by the complier,
we can not get offset information from the complie's mouth.
ex.
offsetof(Test,c); //complie error. they said can not access private member.
we also can not get member pointer from class Test.
ex.
&Test::c ; //complie error. they said can not access private member.
#Johannes Schaub - litb has a blog, he found a way to rob private member pointer.
but i thought this should be complier's bug or language pitfall.
i can complie it on gcc4.8, but not on vc8 complier.
so the conclusion may be :
the landlord build all backdoor.
the thief always has brute and bad way to break into.
the hacker accidental has elegant and automated way to break into.
I made Johannes answer more generic. You can get the source here: https://github.com/lackhole/Lupin
All you have to know is just the name of the class and the member.
You can use like,
#include <iostream>
#include "access/access.hpp"
struct foo {
private:
std::string name = "hello";
int age = 27;
void print() {}
};
using tag_foo_name = access::Tag<class foo_name>;
template struct access::Accessor<tag_foo_name, foo, decltype(&foo::name), &foo::name>;
int main() {
foo f;
// peek hidden data
std::cout << access::get<tag_foo_name>(f) << '\n'; // "hello"
// steal hidden data
access::get<tag_foo_name>(f) = "lupin";
std::cout << access::get<tag_foo_name>(f) << '\n'; // "lupin"
}
Call private functions, get the type of private members is also possible with only using the tag.

Get Value of Void* C++

I have a void pointer and I would like to get the content of what the pointer refers to.
void class :: method(void * pointer)
{
cout<<pointer; // The address which the pointer refers to.
cout<<?; //The content of where the pointer refers to.
}
The original type of pointer is unknown.
EDIT: The goal is to allow create a "generic method" which gets any type of argument, and do the same actions for each.
The limitation is that the method is virtual and therefore I cannot use template method.
You need to cast the void* back to its original type (ie. before it was cast to void*). Then you can dereference the pointer and use what it's pointing to.
Eg. :
void fun(void* ptr) {
int* iptr = (int*) ptr;
std::cout << *iptr;
}
int* iptr = new int(42);
fun(iptr);
One way to do this in a way that fits your specific use case, is to pass on the type information with the object using a generic type like boost::any :
#include <iostream>
#include <string>
#include <boost/any.hpp>
class Foo {
public :
virtual void fun(const boost::any& obj) {
if (typeid(int) == obj.type()) {
std::cout << boost::any_cast<int>(obj) << std::endl;
}
else if (typeid(std::string) == obj.type()) {
std::cout << boost::any_cast<std::string>(obj) << std::endl;
}
else {
std::cout << "unsupported type" << std::endl;
}
}
};
int main(void) {
Foo foo;
int i = 42;
std::string s = "str";
float f = 1.1f;
foo.fun(i);
foo.fun(s);
foo.fun(f);
return 0;
}
But that can get very verbose, depending on how many types you want to support.
This is impossible. The types in C++ are (mostly) a compile-time property. At runtime, types are unknown (they are erased).
However, RTTI exist, notably for instances of some class containing virtual methods.
There is no possible trick in general. You could redesign your program by having some kind of variant type, or by having a common root class from which all your objects inherit, etc etc, or by using union types (better have your own discriminated unions).
Put it another way: when the compiler see a void* pointer, it does not even know the size of the data pointed by that pointer.
Future C++ standards might propose some std::any container.
Maybe you could have something like a cheap discriminated union class like
class Int_or_String {
const bool isint;
union {
int n;
std::string s;
};
Int_or_String(const int i) : isint(true), n(i) {};
Int_or_String(const std::string &st): isint(false), s(st) {};
~Int_or_String() { if (isint) n=0; else
/*not sure*/ s.std::string::~std::string(); };
// much more is missing
};
I'm not even sure of the syntax to explicitly destroy a union member.
See e.g. this question on calling destructors explicitly
Perhaps the Qt object model might inspire you. Look also into its QVariant
The usual way is to define a root class in your program and adopt the convention that all your objects are inheriting this root class (or even that all your meaningful data are in objects derived from that root class). This requires a redesign of the whole thing.
So you would decide that your root class is e.g
class Root {
public:
virtual void out(std::ostream&s) =0;
virtual ~Root() =0;
/// other common methods
};
static inline std::ostream& operator << (std::ostream&o, const Root &r)
{ r.out(o); return o; }
class Integer : public Root {
const int num;
public:
Integer(int n) : Root(), num(n) {};
void out (std::ostream &o) { o << num ; };
/// etc...
}; // end class Num
class String : public Root {
const std::string str;
public:
String(const std::string& s) : Root(), str(s) {};
void out (std::ostream &o) { o << str ; };
/// etc...
}; // end class String

C++ Push Multiple Types onto Vector

Note: I know similar questions to this have been asked on SO before, but I did not find them helpful or very clear.
Second note: For the scope of this project/assignment, I'm trying to avoid third party libraries, such as Boost.
I am trying to see if there is a way I can have a single vector hold multiple types, in each of its indices. For example, say I have the following code sample:
vector<something magical to hold various types> vec;
int x = 3;
string hi = "Hello World";
MyStruct s = {3, "Hi", 4.01};
vec.push_back(x);
vec.push_back(hi);
vec.push_back(s);
I've heard vector<void*> could work, but then it gets tricky with memory allocation and then there is always the possibility that certain portions in nearby memory could be unintentionally overridden if a value inserted into a certain index is larger than expected.
In my actual application, I know what possible types may be inserted into a vector, but these types do not all derive from the same super class, and there is no guarantee that all of these types will be pushed onto the vector or in what order.
Is there a way that I can safely accomplish the objective I demonstrated in my code sample?
Thank you for your time.
The objects hold by the std::vector<T> need to be of a homogenous type. If you need to put objects of different type into one vector you need somehow erase their type and make them all look similar. You could use the moral equivalent of boost::any or boost::variant<...>. The idea of boost::any is to encapsulate a type hierarchy, storing a pointer to the base but pointing to a templatized derived. A very rough and incomplete outline looks something like this:
#include <algorithm>
#include <iostream>
class any
{
private:
struct base {
virtual ~base() {}
virtual base* clone() const = 0;
};
template <typename T>
struct data: base {
data(T const& value): value_(value) {}
base* clone() const { return new data<T>(*this); }
T value_;
};
base* ptr_;
public:
template <typename T> any(T const& value): ptr_(new data<T>(value)) {}
any(any const& other): ptr_(other.ptr_->clone()) {}
any& operator= (any const& other) {
any(other).swap(*this);
return *this;
}
~any() { delete this->ptr_; }
void swap(any& other) { std::swap(this->ptr_, other.ptr_); }
template <typename T>
T& get() {
return dynamic_cast<data<T>&>(*this->ptr_).value_;
}
};
int main()
{
any a0(17);
any a1(3.14);
try { a0.get<double>(); } catch (...) {}
a0 = a1;
std::cout << a0.get<double>() << "\n";
}
As suggested you can use various forms of unions, variants, etc. Depending on what you want to do with your stored objects, external polymorphism could do exactly what you want, if you can define all necessary operations in a base class interface.
Here's an example if all we want to do is print the objects to the console:
#include <iostream>
#include <string>
#include <vector>
#include <memory>
class any_type
{
public:
virtual ~any_type() {}
virtual void print() = 0;
};
template <class T>
class concrete_type : public any_type
{
public:
concrete_type(const T& value) : value_(value)
{}
virtual void print()
{
std::cout << value_ << '\n';
}
private:
T value_;
};
int main()
{
std::vector<std::unique_ptr<any_type>> v(2);
v[0].reset(new concrete_type<int>(99));
v[1].reset(new concrete_type<std::string>("Bottles of Beer"));
for(size_t x = 0; x < 2; ++x)
{
v[x]->print();
}
return 0;
}
In order to do that, you'll definitely need a wrapper class to somehow conceal the type information of your objects from the vector.
It's probably also good to have this class throw an exception when you try to get Type-A back when you have previously stored a Type-B into it.
Here is part of the Holder class from one of my projects. You can probably start from here.
Note: due to the use of unrestricted unions, this only works in C++11. More information about this can be found here: What are Unrestricted Unions proposed in C++11?
class Holder {
public:
enum Type {
BOOL,
INT,
STRING,
// Other types you want to store into vector.
};
template<typename T>
Holder (Type type, T val);
~Holder () {
// You want to properly destroy
// union members below that have non-trivial constructors
}
operator bool () const {
if (type_ != BOOL) {
throw SomeException();
}
return impl_.bool_;
}
// Do the same for other operators
// Or maybe use templates?
private:
union Impl {
bool bool_;
int int_;
string string_;
Impl() { new(&string_) string; }
} impl_;
Type type_;
// Other stuff.
};

Can I access private members from outside the class without using friends?

Disclaimer
Yes, I am fully aware that what I am asking about is totally stupid and that anyone who would wish to try such a thing in production code should be fired and/or shot. I'm mainly looking to see if can be done.
Now that that's out of the way, is there any way to access private class members in C++ from outside the class? For example, is there any way to do this with pointer offsets?
(Naive and otherwise non-production-ready techniques welcome)
Update
As noted in the comments, I asked this question because I wanted to write a blog post on over-encapsulation (and how it affects TDD). I wanted to see if there was a way to say "using private variables isn't a 100% reliable way to enforce encapsulation, even in C++." At the end, I decided to focus more on how to solve the problem rather than why it's a problem, so I didn't feature some of the stuff brought up here as prominently as I had planned, but I still left a link.
At any rate, if anyone's interested in how it came out, here it is: Enemies of Test Driven Development part I: encapsulation (I suggest reading it before you decide that I'm crazy).
If the class contains any template member functions you can specialize that member function to suit your needs. Even if the original developer didn't think of it.
safe.h
class safe
{
int money;
public:
safe()
: money(1000000)
{
}
template <typename T>
void backdoor()
{
// Do some stuff.
}
};
main.cpp:
#include <safe.h>
#include <iostream>
class key;
template <>
void safe::backdoor<key>()
{
// My specialization.
money -= 100000;
std::cout << money << "\n";
}
int main()
{
safe s;
s.backdoor<key>();
s.backdoor<key>();
}
Output:
900000
800000
I've added an entry to my blog (see below) that shows how it can be done. Here is an example on how you use it for the following class
struct A {
private:
int member;
};
Just declare a struct for it where you describe it and instantiate the implementation class used for robbery
// tag used to access A::member
struct A_member {
typedef int A::*type;
friend type get(A_member);
};
template struct Rob<A_member, &A::member>;
int main() {
A a;
a.*get(A_member()) = 42; // write 42 to it
std::cout << "proof: " << a.*get(A_member()) << std::endl;
}
The Rob class template is defined like this, and needs only be defined once, regardless how many private members you plan to access
template<typename Tag, typename Tag::type M>
struct Rob {
friend typename Tag::type get(Tag) {
return M;
}
};
However, this doesn't show that c++'s access rules aren't reliable. The language rules are designed to protect against accidental mistakes - if you try to rob data of an object, the language by-design does not take long ways to prevent you.
The following is sneaky, illegal, compiler-dependent, and may not work depending on various implementation details.
#define private public
#define class struct
But it is an answer to your OP, in which you explicitly invite a technique which, and I quote, is "totally stupid and that anyone who would wish to try such a thing in production code should be fired and/or shot".
Another technique is to access private member data, by contructing pointers using hard-coded/hand-coded offsets from the beginning of the object.
Hmmm, don't know if this would work, but might be worth a try. Create another class with the same layout as the object with private members but with private changed to public. Create a variable of pointer to this class. Use a simple cast to point this to your object with private members and try calling a private function.
Expect sparks and maybe a crash ;)
class A
{
int a;
}
class B
{
public:
int b;
}
union
{
A a;
B b;
};
That should do it.
ETA: It will work for this sort of trivial class, but as a general thing it won't.
TC++PL Section C.8.3: "A class with a constructor, destructor, or copy operation cannot be the type of a union member ... because the compiler would not know which member to destroy."
So we're left with the best bet being to declare class B to match A's layout and hack to look at a class's privates.
If you can get a pointer to a member of a class you can use the pointer no matter what the access specifiers are (even methods).
class X;
typedef void (X::*METHOD)(int);
class X
{
private:
void test(int) {}
public:
METHOD getMethod() { return &X::test;}
};
int main()
{
X x;
METHOD m = x.getMethod();
X y;
(y.*m)(5);
}
Of course my favorite little hack is the friend template back door.
class Z
{
public:
template<typename X>
void backDoor(X const& p);
private:
int x;
int y;
};
Assuming the creator of the above has defined backDoor for his normal uses. But you want to access the object and look at the private member variables. Even if the above class has been compiled into a static library you can add your own template specialization for backDoor and thus access the members.
namespace
{
// Make this inside an anonymous namespace so
// that it does not clash with any real types.
class Y{};
}
// Now do a template specialization for the method.
template<>
void Z::backDoor<Y>(Y const& p)
{
// I now have access to the private members of Z
}
int main()
{
Z z; // Your object Z
// Use the Y object to carry the payload into the method.
z.backDoor(Y());
}
It's definately possible to access private members with a pointer offset in C++. Lets assume i had the following type definition that I wanted access to.
class Bar {
SomeOtherType _m1;
int _m2;
};
Assuming there are no virtual methods in Bar, The easy case is _m1. Members in C++ are stored as offsets of the memory location of the object. The first object is at offset 0, the second object at offset of sizeof(first member), etc ...
So here is a way to access _m1.
SomeOtherType& GetM1(Bar* pBar) {
return*(reinterpret_cast<SomeOtherType*>(pBar));
}
Now _m2 is a bit more difficult. We need to move the original pointer sizeof(SomeOtherType) bytes from the original. The cast to char is to ensure that I am incrementing in a byte offset
int& GetM2(Bar* pBar) {
char* p = reinterpret_cast<char*>(pBar);
p += sizeof(SomeOtherType);
return *(reinterpret_cast<int*>(p));
}
This answer is based on the exact concept demonstrated by #Johannes's answer/blog, as that seems to be the only "legitimate" way. I have converted that example code into a handy utility. It's easily compatible with C++03 (by implementing std::remove_reference & replacing nullptr).
Library
#define CONCATE_(X, Y) X##Y
#define CONCATE(X, Y) CONCATE_(X, Y)
#define ALLOW_ACCESS(CLASS, MEMBER, ...) \
template<typename Only, __VA_ARGS__ CLASS::*Member> \
struct CONCATE(MEMBER, __LINE__) { friend __VA_ARGS__ CLASS::*Access(Only*) { return Member; } }; \
template<typename> struct Only_##MEMBER; \
template<> struct Only_##MEMBER<CLASS> { friend __VA_ARGS__ CLASS::*Access(Only_##MEMBER<CLASS>*); }; \
template struct CONCATE(MEMBER, __LINE__)<Only_##MEMBER<CLASS>, &CLASS::MEMBER>
#define ACCESS(OBJECT, MEMBER) \
(OBJECT).*Access((Only_##MEMBER<std::remove_reference<decltype(OBJECT)>::type>*)nullptr)
API
ALLOW_ACCESS(<class>, <member>, <type>);
Usage
ACCESS(<object>, <member>) = <value>; // 1
auto& ref = ACCESS(<object>, <member>); // 2
Demo
struct X {
int get_member () const { return member; };
private:
int member = 0;
};
ALLOW_ACCESS(X, member, int);
int main() {
X x;
ACCESS(x, member) = 42;
std::cout << "proof: " << x.get_member() << std::endl;
}
If you know how your C++ compiler mangles names, yes.
Unless, I suppose, it's a virtual function. But then, if you know how your C++ compiler builds the VTABLE ...
Edit: looking at the other responses, I realize that I misread the question and thought it was about member functions, not member data. However, the point still stands: if you know how your compiler lays out data, then you can access that data.
cool question btw... here's my piece:
using namespace std;
class Test
{
private:
int accessInt;
string accessString;
public:
Test(int accessInt,string accessString)
{
Test::accessInt=accessInt;
Test::accessString=accessString;
}
};
int main(int argnum,char **args)
{
int x;
string xyz;
Test obj(1,"Shit... This works!");
x=((int *)(&obj))[0];
xyz=((string *)(&obj))[1];
cout<<x<<endl<<xyz<<endl;
return 0;
}
Hope this helps.
As an alternative to template backdoor method you can use template backdoor class. The difference is that you don't need to put this backdoor class into public area of the class your are going to test. I use the fact that many compilers allow nested classes to access private area of enclosing class (which is not exactly 1998 standard but considered to be "right" behaviour). And of course in C++11 this became legal behaviour.
See this example:
#include <vector>
#include <cassert>
#include <iostream>
using std::cout;
using std::endl;
///////// SystemUnderTest.hpp
class SystemUnderTest
{
//...put this 'Tested' declaration into private area of a class that you are going to test
template<typename T> class Tested;
public:
SystemUnderTest(int a): a_(a) {}
private:
friend std::ostream& operator<<(std::ostream& os, const SystemUnderTest& sut)
{
return os << sut.a_;
}
int a_;
};
/////////TestFramework.hpp
class BaseTest
{
public:
virtual void run() = 0;
const char* name() const { return name_; }
protected:
BaseTest(const char* name): name_(name) {}
virtual ~BaseTest() {}
private:
BaseTest(const BaseTest&);
BaseTest& operator=(const BaseTest&);
const char* name_;
};
class TestSuite
{
typedef std::vector<BaseTest*> Tests;
typedef Tests::iterator TIter;
public:
static TestSuite& instance()
{
static TestSuite TestSuite;
return TestSuite;
}
void run()
{
for(TIter iter = tests_.begin(); tests_.end() != iter; ++iter)
{
BaseTest* test = *iter;
cout << "Run test: " << test->name() << endl;
test->run();
}
}
void addTest(BaseTest* test)
{
assert(test);
cout << "Add test: " << test->name() << endl;
tests_.push_back(test);
}
private:
std::vector<BaseTest*> tests_;
};
#define TEST_CASE(SYSTEM_UNDER_TEST, TEST_NAME) \
class TEST_NAME {}; \
template<> \
class SYSTEM_UNDER_TEST::Tested<TEST_NAME>: public BaseTest \
{ \
Tested(): BaseTest(#SYSTEM_UNDER_TEST "::" #TEST_NAME) \
{ \
TestSuite::instance().addTest(this); \
} \
void run(); \
static Tested instance_; \
}; \
SYSTEM_UNDER_TEST::Tested<TEST_NAME> SYSTEM_UNDER_TEST::Tested<TEST_NAME>::instance_; \
void SYSTEM_UNDER_TEST::Tested<TEST_NAME>::run()
//...TestSuiteForSystemUnderTest.hpp
TEST_CASE(SystemUnderTest, AccessPrivateValueTest)
{
SystemUnderTest sut(23);
cout << "Changed private data member from " << sut << " to ";
sut.a_ = 12;
cout << sut << endl;
}
//...TestRunner.cpp
int main()
{
TestSuite::instance().run();
}
Beside #define private public you can also #define private protected and then define some foo class as descendant of wanted class to have access to it's (now protected) methods via type casting.
just create your own access member function to extend the class.
To all the people suggesting "#define private public":
This kind of thing is illegal. The standard forbids defining/undef-ing macros that are lexically equivalent to reserved language keywords. While your compiler probably won't complain (I've yet to see a compiler that does), it isn't something that's a "Good Thing" to do.
It's actually quite easy:
class jail {
int inmate;
public:
int& escape() { return inmate; }
};
"using private variables isn't a 100% reliable way to enforce encapsulation, even in C++."
Really? You can disassemble the library you need, find all the offsets needed and use them.
That will give you an ability to change any private member you like... BUT!
You can't access private members without some dirty hacking.
Let us say that writing const won't make your constant be really constant, 'cause you can
cast const away or just use it's address to invalidate it. If you're using MSVC++ and you specified "-merge:.rdata=.data" to a linker, the trick will work without any memory access faults.
We can even say that writing apps in C++ is not reliable way to write programs, 'cause resulting low level code may be patched from somewhere outside when your app is running.
Then what is reliable documented way to enforce encapsulation? Can we hide the data somewhere in RAM and prevent anything from accessing them except our code? The only idea I have is to encrypt private members and backup them, 'cause something may corrupt those members.
Sorry if my answer is too rude, I didn't mean to offend anybody, but I really don't think that statement is wise.
since you have an object of required class I am guessing that you have declaration of class.
Now what you can do is declare another class with same members but keep all of there access specifiers as public.
For example previous class is:
class Iamcompprivate
{
private:
Type1 privateelement1;
Typ2 privateelement2;
...
public:
somefunctions
}
you can declare a class as
class NowIampublic
{
**public:**
Type1 privateelement1;
Type2 privateelement2;
...
somefunctions
};
Now all you need to do is cast pointer of class Iamcompprivate into an pointer of class NowIampublic and use them as U wish.
Example:
NowIampublic * changetopublic(Iamcompprivate *A)
{
NowIampublic * B = (NowIampublic *)A;
return B;
}
By referencing to *this you enable a backdoor to all private data within an object.
class DumbClass
{
private:
int my_private_int;
public:
DumbClass& backdoor()
{
return *this;
}
}
Quite often a class provides mutator methods to private data (getters and setters).
If a class does provide a getter that returns a const reference (but no setter), then you can just const_cast the return value of the getter, and use that as an l-value:
class A {
private:
double _money;
public:
A(money) :
_money(money)
{}
const double &getMoney() const
{
return _money;
}
};
A a(1000.0);
const_cast<double &>(a.getMoney()) = 2000.0;
I've used another useful approach (and solution) to access a c++ private/protected member.
The only condition is that you are able to inherit from the class you want to access.
Then all credit goes to reinterpret_cast<>().
A possible problem is that it won't work if you insert a virtual function, which will modify virtual table, and so, object size/alignment.
class QObject
{
Q_OBJECT
Q_DECLARE_PRIVATE(QObject)
void dumpObjectInfo();
void dumpObjectTree();
...
protected:
QScopedPointer<QObjectData> d_ptr;
...
}
class QObjectWrapper : public QObject
{
public:
void dumpObjectInfo2();
void dumpObjectTree2();
};
Then you just need to use the class as follows:
QObject* origin;
QObjectWrapper * testAccesor = reinterpret_cast<QObjectWrapper *>(origin);
testAccesor->dumpObjectInfo2();
testAccesor->dumpObjectTree2();
My original problem was as follows: I needed a solution that won't imply recompiling QT libraries.
There are 2 methods in QObject, dumpObjectInfo() and dumpObjectTree(), that
just work if QT libs are compiled in debug mode, and they of course need access to d_ptr proteted member (among other internal structures).
What I did was to use the proposed solution to reimplement (with copy and paste) those methods in dumpObjectInfo2() and dumpObjectTree2() in my own class (QObjectWrapper) removing those debug preprocesor guards.
The following code accesses and modifies a private member of the class using a pointer to that class.
#include <iostream>
using namespace std;
class A
{
int private_var;
public:
A(){private_var = 0;}//initialized to zero.
void print(){cout<<private_var<<endl;}
};
int main()
{
A ob;
int *ptr = (int*)&ob; // the pointer to the class is typecast to a integer pointer.
(*ptr)++; //private variable now changed to 1.
ob.print();
return 0;
}
/*prints 1. subsequent members can also be accessed by incrementing the pointer (and
type casting if necessary).*/
study purpose only....
try this ....may be helpfull i guess.....
this program can access the private data just by knowing the values...
//GEEK MODE....;)
#include<iostream.h>
#include<conio.h>
class A
{
private :int iData,x;
public: void get() //enter the values
{cout<<"Enter iData : ";
cin>>iData;cout<<"Enter x : ";cin>>x;}
void put() //displaying values
{cout<<endl<<"sum = "<<iData+x;}
};
void hack(); //hacking function
void main()
{A obj;clrscr();
obj.get();obj.put();hack();obj.put();getch();
}
void hack() //hack begins
{int hck,*ptr=&hck;
cout<<endl<<"Enter value of private data (iData or x) : ";
cin>>hck; //enter the value assigned for iData or x
for(int i=0;i<5;i++)
{ptr++;
if(*ptr==hck)
{cout<<"Private data hacked...!!!\nChange the value : ";
cin>>*ptr;cout<<hck<<" Is chaged to : "<<*ptr;
return;}
}cout<<"Sorry value not found.....";
}
Inspired by #Johannes Schaub - litb, the following code may be a bit easier to digest.
struct A {
A(): member(10){}
private:
int get_member() { return member;}
int member;
};
typedef int (A::*A_fm_ptr)();
A_fm_ptr get_fm();
template< A_fm_ptr p>
struct Rob{
friend A_fm_ptr get_fm() {
return p;
}
};
template struct Rob< &A::get_member>;
int main() {
A a;
A_fm_ptr p = get_fm();
std::cout << (a.*p)() << std::endl;
}
Well, with pointer offsets, it's quite easy. The difficult part is finding the offset:
other.hpp
class Foo
{
public:
int pub = 35;
private:
int foo = 5;
const char * secret = "private :)";
};
main.cpp
#include <iostream>
#include <fstream>
#include <string>
#include <regex>
#include "other.hpp"
unsigned long long getPrivOffset(
const char * klass,
const char * priv,
const char * srcfile
){
std::ifstream read(srcfile);
std::ofstream write("fork.hpp");
std::regex r ("private:");
std::string line;
while(getline(read, line))
// make all of the members public
write << std::regex_replace(line, r, "public:") << '\n';
write.close();
read.close();
// find the offset, using the clone object
std::ofstream phony("phony.cpp");
phony <<
"#include <iostream>\n"
"#include <fstream>\n"
"#include \"fork.hpp\"\n"
"int main() {\n";
phony << klass << " obj;\n";
// subtract to find the offset, the write it to a file
phony <<
"std::ofstream out(\"out.txt\");\n out << (((unsigned char *) &(obj."
<< priv << ")) -((unsigned char *) &obj)) << '\\n';\nout.close();";
phony << "return 0;\n}";
phony.close();
system(
"clang++-7 -o phony phony.cpp\n"
"./phony\n"
"rm phony phony.cpp fork.hpp");
std::ifstream out("out.txt");
// read the file containing the offset
getline(out, line);
out.close();
system("rm out.txt");
unsigned long long offset = strtoull(line.c_str(), NULL, 10);
return offset;
}
template <typename OutputType, typename Object>
OutputType hack(
Object obj,
const char * objectname,
const char * priv_method_name,
const char * srcfile
) {
unsigned long long o = getPrivOffset(
objectname,
priv_method_name,
srcfile
);
return *(OutputType *)(((unsigned char *) (&obj)+o));
}
#define HACK($output, $object, $inst, $priv, $src)\
hack <$output, $object> (\
$inst,\
#$object,\
$priv,\
$src)
int main() {
Foo bar;
std::cout << HACK(
// output type
const char *,
// type of the object to be "hacked"
Foo,
// the object being hacked
bar,
// the desired private member name
"secret",
// the source file of the object's type's definition
"other.hpp"
) << '\n';
return 0;
}
clang++ -o main main.cpp
./main
output:
private :)
You could also use reinterpret_cast.
Maybe some pointer arithmetics can do it
#pragma pack(1)
class A
{
int x{0};
char c{0};
char s[8]{0};
public:
void display()
{
print(x);
print(c);
print(s);
};
};
int main(void)
{
A a;
int *ptr2x = (int *)&a;
*ptr2x = 10;
char *ptr2c = (char *)ptr2x+4;
*ptr2c = 'A';
char *ptr2s = (char *)ptr2c+1;
strcpy(ptr2s ,"Foo");
a.display();
}
class Test{
int a;
alignas(16) int b;
int c;
};
Test t;
method A : intrusive mood.
since we can access source code and recomplie it, we can use
many other way like friend class to access private member, they are all legal backdoor.
method B : brute mood.
int* ptr_of_member_c = reinterpret_cast<int*>(reinterpret_cast<char*>(&t) + 20);
we use a magic number (20) , and It's not always right. When the layout of class Test changed, the magic number is a big bug source.
method C : super hacker mood.
is there any non-intrusive and non-brute mood ?
since the class Test's layout infomation is hide by the complier,
we can not get offset information from the complie's mouth.
ex.
offsetof(Test,c); //complie error. they said can not access private member.
we also can not get member pointer from class Test.
ex.
&Test::c ; //complie error. they said can not access private member.
#Johannes Schaub - litb has a blog, he found a way to rob private member pointer.
but i thought this should be complier's bug or language pitfall.
i can complie it on gcc4.8, but not on vc8 complier.
so the conclusion may be :
the landlord build all backdoor.
the thief always has brute and bad way to break into.
the hacker accidental has elegant and automated way to break into.
I made Johannes answer more generic. You can get the source here: https://github.com/lackhole/Lupin
All you have to know is just the name of the class and the member.
You can use like,
#include <iostream>
#include "access/access.hpp"
struct foo {
private:
std::string name = "hello";
int age = 27;
void print() {}
};
using tag_foo_name = access::Tag<class foo_name>;
template struct access::Accessor<tag_foo_name, foo, decltype(&foo::name), &foo::name>;
int main() {
foo f;
// peek hidden data
std::cout << access::get<tag_foo_name>(f) << '\n'; // "hello"
// steal hidden data
access::get<tag_foo_name>(f) = "lupin";
std::cout << access::get<tag_foo_name>(f) << '\n'; // "lupin"
}
Call private functions, get the type of private members is also possible with only using the tag.