Passing classes and structs by value

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Passing classes and structs by value

2,391 Views
Jarrod
Contributor I
Say I have a struct or class that is register sized.

Code:
struct ByValuePlease{    int val;}

Most compilers won't pass this by value in a register. Is there a pragma or something (apart from casting) that will force Codewarrior to pass-by-value in a register?



Message Edited by Jarrod on 2008-11-07 06:00 AM

Message Edited by Jarrod on 2008-11-07 06:03 AM
Labels (1)
0 Kudos
3 Replies

328 Views
Lundin
Senior Contributor IV
That's because there is never a reason to pass a struct by value. If you need a copy of the struct, copy it manually with memcpy() etc and then pass the copy by ref to the function.

It doesn't matter how small the struct is, you can never beat a pointer's memory efficiency on the stack. As stated in the C/C++ standards, structs may also contain padding bytes at any location, which would mean additional overhead when passing them by value.
0 Kudos

328 Views
CompilerGuru
NXP Employee
NXP Employee
For C++ (different to C) often the address of the struct is required, for example as this for calling any member function. Some members like constructors are event created automatically, so for C++ some compilers may special case POD's (plain old data types), but most do for consistency pass all structs via stack.
For C things are a little bit easier for compilers to pass in registers. But having a different calling behavior to C++ is not nice.
In the end, the OP did not mention the architecture, so this is all really guessing around.
So questions back:
- Which architecture?
- Which compiler, which version?
- Which calling convention(if there are multiple)?
- Why do you think it matters?
- Is inlining an option (no arguments at all)?

Also I think it is not likely that there is a pragma to modify this detail of the calling convention behavior of the compiler, it's just very dangerous that only the call or the callee side is aware of the pragma, so such a pragma would be dangerous to use.

Daniel
0 Kudos

328 Views
Jarrod
Contributor I
- Which architecture?
Nintendo Wii (Broadway CPU)

- Which compiler, which version?
Freescale C/C++ Compiler for Embedded PowerPC
Version 4.2 build 142
Runtime Built: Aug 26 2008 02:32:39

- Which calling convention(if there are multiple)?

The default I think.

- Why do you think it matters?
Just the obvious performance boost by eliminating the reference load. They are register sized or less, so it would be nice to at least have the option. We checked the assembly and as expected pass-by-value currently causes a copy to be made on the stack, and a behind the scenes a pointer is passed.

In practice will probably turn out not to be too much of an issue, especially on Wii which has a higher cache : cpu speed ratio, so L1 vs. register isn't as bad as on PS3 etc., but we would at least like to be able to do some profiling and find out.

- Is inlining an option (no arguments at all)?
This would help in some cases. The struct would almost always be in L1 but it would be better to chuck it in a register if possible and leave L1 alone for other stuff. Plus even L1 is slow compared to a register and we know it is going to be a guaranteed lookup.

I suppose we could just cast to unsigned int, pass that, and then cast back, but this is pretty nasty from a readability perspective obviously, and I'm not sure if it would result in an extra local on the stack - hopefully that would get optimised away.

0 Kudos