C
C#ā€¢3y ago
Glatrix

ā” Importing functions by RVA instead of Name

right now, I have a function imported from a cpp library which I pass in a function name and params, and it gives me back a pointer to that function. And currently, I just cast it to a unmanaged function pointer and it works fine. Does anyone here know if there is a way to simplify this process by using a custom attribute? example: instead of
delegate* unmanaged[Cdecl]<int,int,void> DoThing = (delegate* unmanaged[Cdecl]<int,int,void>)ResolveFunc("DoThing(int, int)");
delegate* unmanaged[Cdecl]<int,int,void> DoThing = (delegate* unmanaged[Cdecl]<int,int,void>)ResolveFunc("DoThing(int, int)");
just
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
or similar. How can I go about making ResolvableAttribute?
16 Replies
Kouhai
Kouhaiā€¢3y ago
Get the attribute and call ResolveFunc with the value of ResolvableAttribute
Glatrix
GlatrixOPā€¢3y ago
right, but where? is there a way to override invoke in the attribute class?
Kouhai
Kouhaiā€¢3y ago
I'm not sure what do you mean override invoke, you can do it with reflection.
Glatrix
GlatrixOPā€¢3y ago
what will reflection even do for me in this case? I'm working with function pointers, and I need to make an attribute which shortens the process thats all if I have
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
and I call it, it should make sure it has the pointer by calling ResolveFunc with the value ive passed in, and then call it with the args pA and pB instead of
var DoThing = (delegate* unmanaged[Cdecl]<int,int,void>)ResolveFunc("DoThing(int, int)");
var DoThing = (delegate* unmanaged[Cdecl]<int,int,void>)ResolveFunc("DoThing(int, int)");
I want to put the
ResolveFunc("DoThing(int, int)");
ResolveFunc("DoThing(int, int)");
functionality inside the attribute somehow, and get rid of the annoyingly long cast if possible
Kouhai
Kouhaiā€¢3y ago
What's the return type of ResolveFunc?
Glatrix
GlatrixOPā€¢3y ago
IntPtr which is the address of the function in memory when I cast it as a func pointer it works, im just looking to simplify the process
Kouhai
Kouhaiā€¢3y ago
A very simple example
class Test
{
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
public static void Init()
{
foreach (var field in typeof(Test).GetFields(BindingFlags.Public | BindingFlags.Static))
{
var resolvable = field.GetCustomAttribute<ResolvableAttribute>();
if(resolvable != null)
{
var methodPtr = ResolveFunc(resolvable.Name);
try
{
if (methodPtr != IntPtr.Zero)
field.SetValue(null, Marshal.GetDelegateForFunctionPointer(methodPtr, field.FieldType));
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
}
}
}
class Test
{
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
public static void Init()
{
foreach (var field in typeof(Test).GetFields(BindingFlags.Public | BindingFlags.Static))
{
var resolvable = field.GetCustomAttribute<ResolvableAttribute>();
if(resolvable != null)
{
var methodPtr = ResolveFunc(resolvable.Name);
try
{
if (methodPtr != IntPtr.Zero)
field.SetValue(null, Marshal.GetDelegateForFunctionPointer(methodPtr, field.FieldType));
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
}
}
}
}
Init would initialize all fields that has the attribute Resolvable
internal class ResolvableAttribute : Attribute
{
public string Name { get; }

public ResolvableAttribute(string name)
{
this.Name = name;
}
}
internal class ResolvableAttribute : Attribute
{
public string Name { get; }

public ResolvableAttribute(string name)
{
this.Name = name;
}
}
Glatrix
GlatrixOPā€¢3y ago
would public static extern void DoThing(int pA, int pB); be considered a field?
Kouhai
Kouhaiā€¢3y ago
Yup, it's a field
Glatrix
GlatrixOPā€¢3y ago
oh I didnt know that interesting and it can be set to a delegate?
Kouhai
Kouhaiā€¢3y ago
oops sorry, I messed u, you need to define the delegate
Glatrix
GlatrixOPā€¢3y ago
is the delegate not already defined here somehow?
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
[Resolvable("DoThing(int, int)")]
public static extern void DoThing(int pA, int pB);
like void DoThing(int pA, int pB);
Kouhai
Kouhaiā€¢3y ago
or field with an action I messed up, that won't work with GetField Lemme send the correct code This
public delegate void DoThingDelegate(int pA, int pB);
[Resolvable("DoThing(int, int)")]
public static DoThingDelegate? DoThing;
public delegate void DoThingDelegate(int pA, int pB);
[Resolvable("DoThing(int, int)")]
public static DoThingDelegate? DoThing;
Or
[Resolvable("DoThing(int, int)")]
public static Action<int,int>? DoThing;
[Resolvable("DoThing(int, int)")]
public static Action<int,int>? DoThing;
Glatrix
GlatrixOPā€¢3y ago
okay then thanks!! šŸ™‚
Kouhai
Kouhaiā€¢3y ago
np šŸ‘
Accord
Accordā€¢3y ago
Was this issue resolved? If so, run /close - otherwise I will mark this as stale and this post will be archived until there is new activity.

Did you find this page helpful?