开发者

How can I check a function was called by another function?

开发者 https://www.devze.com 2023-03-16 21:03 出处:网络
I am currently trying to make sure that a member function of one class is only called by a member function of another class.

I am currently trying to make sure that a member function of one class is only called by a member function of another class.

The architecture is imposed and cannot be changed, the port means that some logic has to be done in a.call() before calling b.call(). a.call() therefore calls b.call() to simplify things and make sure the order is respected.

I found this answer to my question. Only, the problem is that I am using classes, and the two cla开发者_如何学Pythonsses have the same member function name and so the #define tries to replace all the occurrences which have different prototypes.


I recommend the passkey pattern. It's very good for giving fine grained control on who can do what with your function.


Off the top of my head, options would be:

  • Make b.call private and make b add a or a.call as a friend
  • Turn b.call into a class and put the body into a a private constructor with a or a.call as a friend
  • grep the source code for b.call, make sure the only call is in a.call, and add a comment at the declaration saying "if you call this function you will be fired"
  • Change b.call to take at least one of the values it needs as a parameter (even if it ignores it and uses the value from somewhere else)


Can you change b.call to take a reference to a? This way, b.call can call a.call itself:

struct A {
    void call() {
        // do stuff
    }
};

struct B {
    void call(A & a) {
        a.call();
        // do stuff
    }
};

This makes sure that a.call is always called before the rest of b.call is executed.


How about using a flag?

a.call()
{
    // ...
    flag = 1;
    b.call();
    flag = 0;
}

b.call()
{
    if (flag == 0)
        return;

    // ...
}


If you program for certain platform (say x86 or x64), and you know the calling convention (e.g. cdecl), then you can get this info from the stack

Say you want to check the object that called the function, so use the this pointer that is pushed to the stack prior to calling the member function: get the this pointer and compare it with the object that you want (this_pointer == a)

If you want to check certain function, get the caller address from the stack and check against that function: caller_address == A::call. If it's a virtual function, use the this pointer to get the vtable.

Depending on the calling-convention and the order of pushing variables on the stack, you may have to check first the input variables sizes, in order to get to the information you need.

0

精彩评论

暂无评论...
验证码 换一张
取 消