Marc via llvm-dev
2020-Aug-10  22:30 UTC
[llvm-dev] resolve the name of an ifunc resolver function
Hi,
I just spent 4 hours trying to find a way to get the name of the
resolver function of a ifunc definition ... :-(
and with all that time I didnt event get far:
for (GlobalIFunc &IF : M.ifuncs()) {
  StringRef ifunc_name = IF.getName();
  Constant *r = IF.getResolver();
But how do I get to the (Function*) or function name of the resolver
from there? I tried everything with the Constant which seems to be a
ConstantExpr type ... ....
Example test program below:
#include <stdio.h>
int foo(void) __attribute__((ifunc("foo_resolve")));
static int global = 1;
static int foo1(void) { return 0; }
static int foo2(void) { return 1; }
void *foo_resolve(void) { return global == 1 ? foo1 : foo2; }
int main() { printf("%d\n", foo()); }
Thank you!
Regards,
Marc
David Blaikie via llvm-dev
2020-Aug-10  22:56 UTC
[llvm-dev] resolve the name of an ifunc resolver function
You could call "getValueID" on that Constant to figure out what kind it is. Also printing it (or calling "dump()") in a debugger might be helpful. On Mon, Aug 10, 2020 at 3:30 PM Marc via llvm-dev <llvm-dev at lists.llvm.org> wrote:> > Hi, > > I just spent 4 hours trying to find a way to get the name of the > resolver function of a ifunc definition ... :-( > > and with all that time I didnt event get far: > > for (GlobalIFunc &IF : M.ifuncs()) { > StringRef ifunc_name = IF.getName(); > Constant *r = IF.getResolver(); > > But how do I get to the (Function*) or function name of the resolver > from there? I tried everything with the Constant which seems to be a > ConstantExpr type ... .... > > Example test program below: > > #include <stdio.h> > > int foo(void) __attribute__((ifunc("foo_resolve"))); > > static int global = 1; > > static int foo1(void) { return 0; } > > static int foo2(void) { return 1; } > > void *foo_resolve(void) { return global == 1 ? foo1 : foo2; } > > int main() { printf("%d\n", foo()); } > > Thank you! > > Regards, > Marc > _______________________________________________ > LLVM Developers mailing list > llvm-dev at lists.llvm.org > https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev
Johannes Doerfert via llvm-dev
2020-Aug-10  23:06 UTC
[llvm-dev] resolve the name of an ifunc resolver function
Hi Marc,
Take a look at the IR: https://clang.godbolt.org/z/cq99EE
Line 5, on the right, you see the definition of the `ifunc`:
   @foo = dso_local ifunc i32 (), bitcast (i8* ()* @foo_resolve to i32 ()*)
The resolver constant probably is the `bitcast (...)` (= I haven't
actually checked). That would match your ConstantExpr observation. You
should be able to just access the operand 0 of the resolver constant
which is the llvm::Function (as llvm::Constant) you are looking for.
`getName()` on that one should work, eventually with a prior cast, thus:
   cast<Function>(r->getOperand(0))->getName()
You can also cast the resolver into a `UnaryConstantExpr` first if you
want, but that should not be necessary to access the operand, just if
you want to verify you have a bitcast in front of you.
Hope this helps.
~ Johannes
On 8/10/20 5:30 PM, Marc via llvm-dev wrote:
 > Hi,
 >
 > I just spent 4 hours trying to find a way to get the name of the
 > resolver function of a ifunc definition ... :-(
 >
 > and with all that time I didnt event get far:
 >
 > for (GlobalIFunc &IF : M.ifuncs()) {
 >   StringRef ifunc_name = IF.getName();
 >   Constant *r = IF.getResolver();
 >
 > But how do I get to the (Function*) or function name of the resolver
 > from there? I tried everything with the Constant which seems to be a
 > ConstantExpr type ... ....
 >
 > Example test program below:
 >
 > #include <stdio.h>
 >
 > int foo(void) __attribute__((ifunc("foo_resolve")));
 >
 > static int global = 1;
 >
 > static int foo1(void) { return 0; }
 >
 > static int foo2(void) { return 1; }
 >
 > void *foo_resolve(void) { return global == 1 ? foo1 : foo2; }
 >
 > int main() { printf("%d\n", foo()); }
 >
 > Thank you!
 >
 > Regards,
 > Marc
 > _______________________________________________
 > LLVM Developers mailing list
 > llvm-dev at lists.llvm.org
 > https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev
Marc via llvm-dev
2020-Aug-10  23:14 UTC
[llvm-dev] resolve the name of an ifunc resolver function
genius, this works! I would never have found that out myself :) thank you! On 11.08.20 01:06, Johannes Doerfert wrote:> Hi Marc, > > Take a look at the IR: https://clang.godbolt.org/z/cq99EE > > Line 5, on the right, you see the definition of the `ifunc`: > @foo = dso_local ifunc i32 (), bitcast (i8* ()* @foo_resolve to i32 ()*) > > The resolver constant probably is the `bitcast (...)` (= I haven't > actually checked). That would match your ConstantExpr observation. You > should be able to just access the operand 0 of the resolver constant > which is the llvm::Function (as llvm::Constant) you are looking for. > `getName()` on that one should work, eventually with a prior cast, thus: > cast<Function>(r->getOperand(0))->getName() > You can also cast the resolver into a `UnaryConstantExpr` first if you > want, but that should not be necessary to access the operand, just if > you want to verify you have a bitcast in front of you. > > Hope this helps. > > ~ Johannes > > > On 8/10/20 5:30 PM, Marc via llvm-dev wrote: >> Hi, >> >> I just spent 4 hours trying to find a way to get the name of the >> resolver function of a ifunc definition ... :-( >> >> and with all that time I didnt event get far: >> >> for (GlobalIFunc &IF : M.ifuncs()) { >> StringRef ifunc_name = IF.getName(); >> Constant *r = IF.getResolver(); >> >> But how do I get to the (Function*) or function name of the resolver >> from there? I tried everything with the Constant which seems to be a >> ConstantExpr type ... .... >> >> Example test program below: >> >> #include <stdio.h> >> >> int foo(void) __attribute__((ifunc("foo_resolve"))); >> >> static int global = 1; >> >> static int foo1(void) { return 0; } >> >> static int foo2(void) { return 1; } >> >> void *foo_resolve(void) { return global == 1 ? foo1 : foo2; } >> >> int main() { printf("%d\n", foo()); } >> >> Thank you! >> >> Regards, >> Marc >> _______________________________________________ >> LLVM Developers mailing list >> llvm-dev at lists.llvm.org >> https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev-- Marc Heuse Mobil: +49 177 9611560 Fax: +49 30 37309726 www.mh-sec.de Marc Heuse - IT-Security Consulting Winsstr. 68 10405 Berlin Ust.-Ident.-Nr.: DE244222388 PGP: AF3D 1D4C D810 F0BB 977D 3807 C7EE D0A0 6BE9 F573