views:

492

answers:

3

I would like to use reflection in .NET to get access to the object that invoked my method. I assume it is somehow possible to view up the stacktrace. I know it's not safe for a variety of reasons, but I just need to grab and catalog some property values.

How do I do this?

Update: I'm an idiot, I forgot to say this was in C#

+1  A: 

What if a static method calls you?

Wouldn't it be a better (simpler) contract with the caller if they passed themself to you?

David B
Of course, but I don't have control of the calling library. I'm looking into writing a command-history Launchy plugin and their plugin model is somewhat lacking in flexibility. I know who will be doing the calling, I just need some way of accessing it
George Mauer
+1  A: 

You may use the StackTrace & StackFrame classes

here is an example from MSDN

http://msdn.microsoft.com/en-us/library/system.diagnostics.stackframe.aspx

This is an example, which should print "Main"

class Program
{
    static void Main(string[] args){
        Func();
    }
    static void Func(){
        StackFrame frame = new StackFrame(1);
        StackTrace trace = new StackTrace(frame);
        var method = frame.GetMethod();
        Console.WriteLine(method.Name);
    }
}
bashmohandes
Great info, didn't know that. But I really need information on the instance that invoked my method.
George Mauer
You need to use the StackFrame object constructor and pass it an integer of how many levels you wanna be in the call stack. for example new StackFrame(1) means the caller StackFrame(2) the caller of caller
bashmohandes
+2  A: 
var methodInfo = new StackFrame(1).GetMethod();

Returns the method that called the current method.

Note that the compiler may inline or otherwise optimize calls to methods (although that sounds like it might not be the case for you), which thwarts expected behavior. To be safe, decorate your method with:

[MethodImpl(MethodImplOptions.NoInlining | MethodImplOptions.NoOptimization)]

Note that this goes contrary to allowing the compiler to do its job. Caveat emptor.

EDITED Oops, I see that you want the instance that invoked your method. There's no way to get that information.

Ben M
Thanks for the response. Shouldn't all the information that is accessible to the VS debugger in theory also be accessible to me? The debugger can look up the stack frames at the instance that called a method...
George Mauer
You'd probably have to attach to the process as a debugger to get this level of detail. See http://stackoverflow.com/questions/420541/is-there-any-way-to-get-a-reference-to-the-calling-object-in-c
Ben M