This is the mail archive of the gcc-help@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: __declspec(naked) and function body size


Ilyes Gouta wrote:

> Is it possible to get the size of a function, i.e the number of bytes generated by the compiler between the prologue and
> the final routine's ret instruction, so that it would be available through a 'sizeof' like operator for the other code?

You can do this at the assembler level:

int foo()
{
  int a = 0, b = 1;
  int c = a + b;

  return (c);
}

asm(".set foo_size, .-foo");
extern unsigned foo_size;                

int main()
{
  unsigned char buf[512];

  memcpy (buf, foo, foo_size);
}

There are two problems with this:

1. In unit-at-a-time mode (which is enabled by default when optimizing)
the compiler does not guarantee that functions and top-level asm
statements are emitted in the same order as specified in the input
source.  Since this technique requires that the asm() come immediately
after the function it refers to, this will break.  So you have to use
-fno-unit-at-a-time (for gcc < 4.2.0) or preferably
-fno-toplevel-reorder (for gcc >= 4.2.0) unless you use -O0.

2. The asm has to be adjusted if you want it to work on
leading-underscore targets.  For example on win32 you'd need to use
something like asm(".set _foo_size, .-_foo") instead.  I suppose you
could abstract this away with some macro junk:

#define ASMNAME(cname)          ASMNAME2 (__USER_LABEL_PREFIX__, cname)
#define ASMNAME2(prefix, cname) STRING (prefix) cname
#define STRING(x)               #x

// ...

asm(".set " ASMNAME("foo_size") ", .-" ASMNAME("foo"));
extern unsigned foo_size;

Brian


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]