Angelscript on Raspberry Pi

Started by
130 comments, last by WitchLord 11 years, 2 months ago
Hi. I´ve been trying to build Angelscript on a Raspberry Pi computer (ARM processor). I made some modifications to the makefile and I´ve got mixed results.

First, after the


...
else ifeq($(TARGERPLATFORM), android)
OBJ += $(OBJDIR)/as_callfunc_arm_gcc.o


I added:


else
OBJ += $(OBJDIR)/as_callfunc_arm_gcc.o



Since the RPi is ARM based, and since I´m using gcc, this looked like the right thing to do.
I also had to add -DAS_NO_THREADS to avoid getting some "unreferences".

The Tutorial and Game examples build fine with this setup, but in the tutorial project I´ve found some problems. When running it, the program outputs this:

[color=#0000ff]---
[color=#0000ff]Received: 1000, 1000
[color=#0000ff]System has been running for 1000 seconds.
[color=#0000ff]---
[color=#0000ff]The script function returned: 8.53973

So as you can see, the received values are wrong. (Interestingly enough, the value returned at the end is correct).

I have the same problem with an application I made. Everything seems to be working fine as long as I use ints or string within my scripts, but as soon as I use floats or doubles the values get corrupted. (I haven´t tested the game project enough, BTW).

If I build the library with -DAS_MAX_PORTABILITY then the tutorial project build ok and works as expected:

[color=#0000ff]---
Received: 3.14159, 2.71828
System has been running for 3.89004e+06 seconds.
---
The script function returned: 8.53973


Any ideas on what could be the problem or what to look for in order to find a solution?

Thanks!
Advertisement
I'd wager this is the same problem that has been reported for Linux with armel. It's quite possible that RPi uses the same ABI as armel Linux.

The thing is that the ABI is slightly different from that used by iOS, Android, and Windows Phone. It would be necessary to make changes to the as_callfunc_arm_gcc code to support this too.

Do you have any documentation that describes the ABI used by RPi? Or else try to disassemble a function that returns a float value and another that returns an int value so we can examine the difference.

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

The RPi is using the armhf ABI. I haven´t found the docs yet but I found some posts in soe other forum stating that when passing values around, ints are passed using int registers and floats are passed using float registers.Does it make any sense?

I´ll check if I can get the ABI documentation.
This is common for x86 ABIs, but I'm not sure the ARM has separate registers for int and floats.

Seeing the disassembly of the functions would be helpful. Something simple, for example:


int func1()
{
return 42;
}

float func2()
{
return 3.141592f;
}

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

Ok. I made this little program:

#include <iostream>
void receivesFloat (float f)
{
std::cout << "Received " << f <<".\n";
}
void receivesInt(int i)
{
std::cout <<"Received " << i <<".\n";
}
float returnsFloat(void)
{
return 17.65f;
}
int returnsInt(void)
{
return 7;
}
int main()
{
receivesFloat(3.14);
receivesInt(1138);
std::cout << "Funcion returned " << returnsFloat() <<".\n";
std::cout << "Funcion returned " << returnsInt() <<".\n";
return 0;
}


Placed some breakpoints in main() and in every one of the functions to get the disassembly - is that correct? I got this:

main:


0x8738 push {r3, r4, r11, lr}
0x873c add r11, sp, #12
0x8740 vldr s0, [pc, #132] ; 0x87cc <main()+148>
0x8744 bl 0x8658 <receivesFloat(float)>
0x8748 ldr r0, [pc, #128] ; 0x87d0 <main()+152>
0x874c bl 0x86a8 <receivesInt(int)>
0x8750 ldr r0, [pc, #124] ; 0x87d4 <main()+156>
0x8754 ldr r1, [pc, #124] ; 0x87d8 <main()+160>
0x8758 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x875c mov r3, r0
0x8760 mov r4, r3
0x8764 bl 0x86f8 <returnsFloat()>
0x8768 vmov.f32 s15, s0
0x876c mov r0, r4
0x8770 vmov.f32 s0, s15
0x8774 bl 0x85a0 <std::ostream::operator<<(float)>
0x8778 mov r3, r0
0x877c mov r0, r3
0x8780 ldr r1, [pc, #84] ; 0x87dc <main()+164>
0x8784 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8788 ldr r0, [pc, #68] ; 0x87d4 <main()+156>
0x878c ldr r1, [pc, #68] ; 0x87d8 <main()+160>
0x8790 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8794 mov r3, r0
0x8798 mov r4, r3
0x879c bl 0x871c <returnsInt()>
0x87a0 mov r3, r0
0x87a4 mov r0, r4
0x87a8 mov r1, r3
0x87ac bl 0x8540 <std::ostream::operator<<(int)>
0x87b0 mov r3, r0
0x87b4 mov r0, r3
0x87b8 ldr r1, [pc, #28] ; 0x87dc <main()+164>
0x87bc bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87c0 mov r3, #0
0x87c4 mov r0, r3
0x87c8 pop {r3, r4, r11, pc}
0x87cc submi pc, r8, r3, asr #11
0x87d0 andeq r0, r0, r2, ror r4
0x87d4 andeq r0, r1, r0, lsr #21
0x87d8 andeq r8, r0, r0, ror #17
0x87dc ldrdeq r8, [r0], -r12


receivesFloat:


0x8658 push {r11, lr}
0x865c add r11, sp, #4
0x8660 sub sp, sp, #8
0x8664 vstr s0, [r11, #-8]
0x8668 ldr r0, [pc, #44] ; 0x869c <receivesFloat(float)+68>
0x866c ldr r1, [pc, #44] ; 0x86a0 <receivesFloat(float)+72>
0x8670 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8674 mov r3, r0
0x8678 mov r0, r3
0x867c vldr s0, [r11, #-8]
0x8680 bl 0x85a0 <std::ostream::operator<<(float)>
0x8684 mov r3, r0
0x8688 mov r0, r3
0x868c ldr r1, [pc, #16] ; 0x86a4 <receivesFloat(float)+76>
0x8690 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8694 sub sp, r11, #4
0x8698 pop {r11, pc}
0x869c andeq r0, r1, r0, lsr #21
0x86a0 ldrdeq r8, [r0], -r0
0x86a4 ldrdeq r8, [r0], -r12


receivesInt:


0x86a8 push {r11, lr}
0x86ac add r11, sp, #4
0x86b0 sub sp, sp, #8
0x86b4 str r0, [r11, #-8]
0x86b8 ldr r0, [pc, #44] ; 0x86ec <receivesInt(int)+68>
0x86bc ldr r1, [pc, #44] ; 0x86f0 <receivesInt(int)+72>
0x86c0 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x86c4 mov r3, r0
0x86c8 mov r0, r3
0x86cc ldr r1, [r11, #-8]
0x86d0 bl 0x8540 <std::ostream::operator<<(int)>
0x86d4 mov r3, r0
0x86d8 mov r0, r3
0x86dc ldr r1, [pc, #16] ; 0x86f4 <receivesInt(int)+76>
0x86e0 bl 0x8588 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x86e4 sub sp, r11, #4
0x86e8 pop {r11, pc}
0x86ec andeq r0, r1, r0, lsr #21
0x86f0 ldrdeq r8, [r0], -r0
0x86f4 ldrdeq r8, [r0], -r12


returnsFloat:


0x86f8 push {r11} ; (str r11, [sp, #-4]!)
0x86fc add r11, sp, #0
0x8700 ldr r3, [pc, #16] ; 0x8718 <returnsFloat()+32>
0x8704 vmov s15, r3
0x8708 vmov.f32 s0, s15
0x870c add sp, r11, #0
0x8710 pop {r11}
0x8714 bx lr
0x8718 orrmi r3, sp, r3, lsr r3


returnsInt:


0x871c push {r11} ; (str r11, [sp, #-4]!)
0x8720 add r11, sp, #0
0x8724 mov r3, #7
0x8728 mov r0, r3
0x872c add sp, r11, #0
0x8730 pop {r11}
0x8734 bx lr


Let me know if this is right and if I can do anything else to help.
Well, it's clear from the disassemblies that the ABI does indeed pass the float type in different registers.

For the int type, the register r0 is used both for passing the value are argument and returning the value. For the float type, the register s0 is used instead.

Based on this knowledge the code in the as_callfunc_arm.cpp and as_callfunc_arm_gcc.S needs to be modified to properly handle the float and double types with this ABI.

The function CallSystemFunctionNative() needs to be updated to prepare the arguments before calling the assembler routines. Either the arguments needs to be separated in two separate arrays, one for integers and one for floats, or the arguments can be kept as is but another array is created that identifies which of the arguments are floats. Then the assembler routines needs to be updated to load the registers correctly based on the arrays.

Before deciding how to implement the management of the argument you should identify how mixed arguments are handled in the ABI. For example, let's say you have a function like this:

void func(int a, float b, int c, float d) {}

We already know a will be placed into r0. But where does the other arguments go? There are two options that I believe are the most probable.

a -> r0, b -> s0, c -> r1, d -> s1

or

a -> r0, b -> s1, c -> r2, d -> s3

It would also be good to know how doubles and int64s are handled. On some platforms they take up 2 registers, and always aligned to an even numbered register, which would mean that you may have to handle skipping some registers in order to align the 64bit arguments.


Unfortunately I will not be able to do the coding myself, as without having the capability to test the code it would be extremely difficult to get it right. If you have time to invest in this should be able to get it to work on your own with a few days of work. It will be a bit of an investigative work to understand how the ABI works, but it's not so difficult if you have the capability to debug and disassemble.

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game


It will be a bit of an investigative work to understand how the ABI works, but it's not so difficult if you have the capability to debug and disassemble.


I can debug and disassemble. The poblem is that I can´t understand what I get after disassembling! But I guess it won´t hurt to give it a try... unless you agree to access my RPi online using VNC (which is the way I actually work . my RPi is sitting at home and I connect to it every time I get some spare time). Because with me doing it, it´s probable that by the time I get something barely usable, you would have already release Angelscript 5 with some clever routines that auto detect ABI and handles appropriately!biggrin.png
I think I´m getting to understand this a little better:

New code, to check mixed values and doubles (forgot int64, will check later):

#include <iostream>
void receivesDouble (double d)
{
std::cout << "Received " << d <<".\n";
}
void receivesFloat (float f)
{
std::cout << "Received " << f <<".\n";
}
void receivesInt(int i)
{
std::cout << "Received " << i <<".\n";
}
void receivesMixed(int a, float b, int c, double d)
{
std::cout << "Received " << a << ".\n";
std::cout << "Received " << b << ".\n";
std::cout << "Received " << c << ".\n";
std::cout << "Received " << d << ".\n";
}
float returnsFloat(void)
{
return 17.65f;
}
int returnsInt(void)
{
return 7;
}
int main()
{
receivesDouble(12.3456789);
receivesFloat(3.14f);
receivesInt(1138);
receivesMixed(1, 2.2f, 3, 4.456789);
std::cout << "Funcion returned " << returnsFloat() <<".\n";
std::cout << "Funcion returned " << returnsInt() <<".\n";
return 0;
}


DIsassembly for main():

0x88a8 push {r3, r4, r11, lr}
0x88ac add r11, sp, #12
0x88b0 vldr d0, [pc, #160] ; 0x8958 <main()+176>
0x88b4 bl 0x8698 <receivesDouble(double)>
0x88b8 vldr s0, [pc, #168] ; 0x8968 <main()+192>
0x88bc bl 0x86e8 <receivesFloat(float)>
0x88c0 ldr r0, [pc, #168] ; 0x8970 <main()+200>
0x88c4 bl 0x8738 <receivesInt(int)>
0x88c8 mov r0, #1
0x88cc vldr s0, [pc, #152] ; 0x896c <main()+196>
0x88d0 mov r1, #3
0x88d4 vldr d1, [pc, #132] ; 0x8960 <main()+184>
0x88d8 bl 0x8788 <receivesMixed(int, float, int, double)>
0x88dc ldr r0, [pc, #144] ; 0x8974 <main()+204>
0x88e0 ldr r1, [pc, #144] ; 0x8978 <main()+208>
0x88e4 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88e8 mov r3, r0
0x88ec mov r4, r3
0x88f0 bl 0x8868 <returnsFloat()>
0x88f4 vmov.f32 s15, s0
0x88f8 mov r0, r4
0x88fc vmov.f32 s0, s15
0x8900 bl 0x85d8 <std::ostream::operator<<(float)>
0x8904 mov r3, r0
0x8908 mov r0, r3
0x890c ldr r1, [pc, #104] ; 0x897c <main()+212>
0x8910 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8914 ldr r0, [pc, #88] ; 0x8974 <main()+204>
0x8918 ldr r1, [pc, #88] ; 0x8978 <main()+208>
0x891c bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8920 mov r3, r0
0x8924 mov r4, r3
0x8928 bl 0x888c <returnsInt()>
0x892c mov r3, r0
0x8930 mov r0, r4
0x8934 mov r1, r3
0x8938 bl 0x8578 <std::ostream::operator<<(int)>
0x893c mov r3, r0
0x8940 mov r0, r3
0x8944 ldr r1, [pc, #48] ; 0x897c <main()+212>
0x8948 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x894c mov r3, #0
0x8950 mov r0, r3
0x8954 pop {r3, r4, r11, pc}
0x8958 teqle r4, #679477248 ; 0x28800000
0x895c strdmi r11, [r8], -r12 ; <UNPREDICTABLE>
0x8960 cdpvc 0, 14, cr11, cr0, cr15, {5}
0x8964 andsmi sp, r1, r0, asr #7
0x8968 submi pc, r8, r3, asr #11
0x896c andmi r12, r12, sp, asr #25
0x8970 andeq r0, r0, r2, ror r4
0x8974 andeq r0, r1, r0, ror r12
0x8978 andeq r8, r0, r0, lsl #21
0x897c andeq r8, r0, r12, ror r10


Disassembly for receivesDouble(...):

0x8698 push {r11, lr}
0x869c add r11, sp, #4
0x86a0 sub sp, sp, #8
0x86a4 vstr d0, [r11, #-12]
0x86a8 ldr r0, [pc, #44] ; 0x86dc <receivesDouble(double)+68>
0x86ac ldr r1, [pc, #44] ; 0x86e0 <receivesDouble(double)+72>
0x86b0 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x86b4 mov r3, r0
0x86b8 mov r0, r3
0x86bc vldr d0, [r11, #-12]
0x86c0 bl 0x856c <std::ostream::operator<<(double)>
0x86c4 mov r3, r0
0x86c8 mov r0, r3
0x86cc ldr r1, [pc, #16] ; 0x86e4 <receivesDouble(double)+76>
0x86d0 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x86d4 sub sp, r11, #4
0x86d8 pop {r11, pc}
0x86dc andeq r0, r1, r0, ror r12
0x86e0 andeq r8, r0, r0, ror r10
0x86e4 andeq r8, r0, r12, ror r10


Disassembly for receivesMixed(...):

0x8788 push {r11, lr}
0x878c add r11, sp, #4
0x8790 sub sp, sp, #24
0x8794 str r0, [r11, #-8]
0x8798 vstr s0, [r11, #-12]
0x879c str r1, [r11, #-16]
0x87a0 vstr d1, [r11, #-28] ; 0xffffffe4
0x87a4 ldr r0, [pc, #176] ; 0x885c <receivesMixed(int, float, int, double)+212>
0x87a8 ldr r1, [pc, #176] ; 0x8860 <receivesMixed(int, float, int, double)+216>
0x87ac bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87b0 mov r3, r0
0x87b4 mov r0, r3
0x87b8 ldr r1, [r11, #-8]
0x87bc bl 0x8578 <std::ostream::operator<<(int)>
0x87c0 mov r3, r0
0x87c4 mov r0, r3
0x87c8 ldr r1, [pc, #148] ; 0x8864 <receivesMixed(int, float, int, double)+220>
0x87cc bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87d0 ldr r0, [pc, #132] ; 0x885c <receivesMixed(int, float, int, double)+212>
0x87d4 ldr r1, [pc, #132] ; 0x8860 <receivesMixed(int, float, int, double)+216>
0x87d8 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87dc mov r3, r0
0x87e0 mov r0, r3
0x87e4 vldr s0, [r11, #-12]
0x87e8 bl 0x85d8 <std::ostream::operator<<(float)>
0x87ec mov r3, r0
0x87f0 mov r0, r3
0x87f4 ldr r1, [pc, #104] ; 0x8864 <receivesMixed(int, float, int, double)+220>
0x87f8 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87fc ldr r0, [pc, #88] ; 0x885c <receivesMixed(int, float, int, double)+212>
0x8800 ldr r1, [pc, #88] ; 0x8860 <receivesMixed(int, float, int, double)+216>
0x8804 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8808 mov r3, r0
0x880c mov r0, r3
0x8810 ldr r1, [r11, #-16]
0x8814 bl 0x8578 <std::ostream::operator<<(int)>
0x8818 mov r3, r0
0x881c mov r0, r3
0x8820 ldr r1, [pc, #60] ; 0x8864 <receivesMixed(int, float, int, double)+220>
0x8824 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8828 ldr r0, [pc, #44] ; 0x885c <receivesMixed(int, float, int, double)+212>
0x882c ldr r1, [pc, #44] ; 0x8860 <receivesMixed(int, float, int, double)+216>
0x8830 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8834 mov r3, r0
0x8838 mov r0, r3
0x883c vldr d0, [r11, #-28] ; 0xffffffe4
0x8840 bl 0x856c <std::ostream::operator<<(double)>
0x8844 mov r3, r0
0x8848 mov r0, r3
0x884c ldr r1, [pc, #16] ; 0x8864 <receivesMixed(int, float, int, double)+220>
0x8850 bl 0x85c0 <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8854 sub sp, r11, #4
0x8858 pop {r11, pc}
0x885c andeq r0, r1, r0, ror r12
0x8860 andeq r8, r0, r0, ror r10
0x8864 andeq r8, r0, r12, ror r10


By looking at this, would it be correct to say that when passing a double, the value is stored in d0, and when passing mixed (int a, float b, int c, double d), a goes to r0, b to s0, c to r1 and d to d1? (And why d1 and not d0 like with receivesDouble(...) ?) - EDIT: Because according to some tech specs I´ve found, d0 is s0 + s1, and since s0 is already used, we can´t use d0...
Yes, it would seem that the ABI keeps two distinct arrays, one for floats and one for integers. Integers goes to r0, r1, r2, ..., and floats to s0, s1, s2, ...

If each d, register is in fact two s registers, then it is necessary to consider padding when mixing floats and doubles.

It would be interested to see a receivesMixed2(int a, double b, int c, float d). From what we've seen so far, these arguments should be passed as following: a -> r0, b -> d0, c -> r1, d -> s2. The last goes to s2 because d0 occupies both s0 and s1.

receivesMixed3(float a, double b, float c) should be as following: a -> s0, b -> d1, c -> s4. The last goes to s4, because d1 occupies both s2 and s3. In this case s1 is not used.

Another thing that needs to be checked before the best algorithm can be determined is how many registers that may be used for passing arguments. The iOS and Android ABI only uses 4 registers at most (r0 to r3), the arguments that don't fit into these 4 registers are pushed on the stack.

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

More info - this time I´ve used the examples you gave me and also tried with long long types and a function called receivesLots, which receives 10 doubles, 2 floats and 2 long long.

#include <iostream>
void receivesMixed(int a, double b, int c, float d)
{
std::cout << "Received " << a << ".\n";
std::cout << "Received " << b << ".\n";
std::cout << "Received " << c << ".\n";
std::cout << "Received " << d << ".\n";
}
void receivesMixed2(float a, double b, float c)
{
std::cout << "Received " << a << ".\n";
std::cout << "Received " << b << ".\n";
std::cout << "Received " << c << ".\n";
}
void receivesLots(double a0, double a1, double a2, double a3, double a4,
double a5, double a6, double a7, double a8, double a9,
float f0, float f1, long long i0, long long i1)
{
std::cout << "Received " << a1 << ".\n";
std::cout << "Received " << a2 << ".\n";
std::cout << "Received " << a3 << ".\n";
std::cout << "Received " << a4 << ".\n";
std::cout << "Received " << a5 << ".\n";
std::cout << "Received " << a6 << ".\n";
std::cout << "Received " << a7 << ".\n";
std::cout << "Received " << a8 << ".\n";
std::cout << "Received " << a9 << ".\n";
std::cout << "Received " << f0 << ".\n";
std::cout << "Received " << f1 << ".\n";
std::cout << "Received " << i0 << ".\n";
std::cout << "Received " << i1 << ".\n";
}
int main()
{
receivesMixed(1, 2.2345678, 3, 4.4f);
receivesMixed2(1.1f, 2.2345678, 4.4f);
receivesLots(0.12345, 1.12345, 2.34567, 3.456789, 4.5678901, 5.6789012, 6.78901234, 7.890123456, 8.901234, 9.012345,
10.2f, 11.23f, 100, 200);
return 0;
}


Disassembly for main:

0x8ae4 push {r11, lr}
0x8ae8 add r11, sp, #4
0x8aec sub sp, sp, #24
0x8af0 mov r0, #1
0x8af4 vldr d0, [pc, #132] ; 0x8b80 <main()+156>
0x8af8 mov r1, #3
0x8afc vldr s2, [pc, #212] ; 0x8bd8 <main()+244>
0x8b00 bl 0x86d0 <receivesMixed(int, double, int, float)>
0x8b04 vldr s0, [pc, #208] ; 0x8bdc <main()+248>
0x8b08 vldr d1, [pc, #112] ; 0x8b80 <main()+156>
0x8b0c vldr s1, [pc, #196] ; 0x8bd8 <main()+244>
0x8b10 bl 0x87b0 <receivesMixed2(float, double, float)>
0x8b14 add r3, pc, #108 ; 0x6c
0x8b18 ldrd r2, [r3]
0x8b1c strd r2, [sp]
0x8b20 add r3, pc, #104 ; 0x68
0x8b24 ldrd r2, [r3]
0x8b28 strd r2, [sp, #8]
0x8b2c ldr r3, [pc, #172] ; 0x8be0 <main()+252>
0x8b30 str r3, [sp, #16]
0x8b34 ldr r3, [pc, #168] ; 0x8be4 <main()+256>
0x8b38 str r3, [sp, #20]
0x8b3c vldr d0, [pc, #84] ; 0x8b98 <main()+180>
0x8b40 vldr d1, [pc, #88] ; 0x8ba0 <main()+188>
0x8b44 vldr d2, [pc, #92] ; 0x8ba8 <main()+196>
0x8b48 vldr d3, [pc, #96] ; 0x8bb0 <main()+204>
0x8b4c vldr d4, [pc, #100] ; 0x8bb8 <main()+212>
0x8b50 vldr d5, [pc, #104] ; 0x8bc0 <main()+220>
0x8b54 vldr d6, [pc, #108] ; 0x8bc8 <main()+228>
0x8b58 vldr d7, [pc, #112] ; 0x8bd0 <main()+236>
0x8b5c mov r0, #100 ; 0x64
0x8b60 mov r1, #0
0x8b64 mov r2, #200 ; 0xc8
0x8b68 mov r3, #0
0x8b6c bl 0x8860 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)>
0x8b70 mov r3, #0
0x8b74 mov r0, r3
0x8b78 sub sp, r11, #4
0x8b7c pop {r11, pc}
0x8b80 strne r8, [sp, #-3759]! ; 0xeaf
0x8b84 andmi lr, r1, r5, rrx
0x8b88 bhi 0xffe0e42c
0x8b8c eormi r12, r1, lr, ror #26
0x8b90 ldrbne r8, [r6, #-2506]! ; 0x9ca
0x8b94 eormi r0, r2, r2, asr r6
0x8b98 adcspl pc, r0, r12, ror r2 ; <UNPREDICTABLE>
0x8b9c svccc 0x00bf9a6b
0x8ba0 strlt r0, [r11, #-3880] ; 0xf28
0x8ba4 svccc 0x00f1f9a6
0x8ba8 andge r10, r9, #164, 20 ; 0xa4000
0x8bac andmi r12, r2, lr, ror #7
0x8bb0 stc2l 1, cr6, [r1, #380] ; 0x17c
0x8bb4 andmi r10, r11, r0, lsl #15
0x8bb8 blx 0x1f419c2
0x8bbc andsmi r4, r2, r4, lsl #11
0x8bc0 sub sp, r12, r2, asr r12
0x8bc4 andsmi r11, r6, r1, lsr r7
0x8bc8 ldmible r1, {r0, r8, r9, lr, pc}^
0x8bcc ; <UNDEFINED> instruction: 0x401b27f2
0x8bd0 ldrbhi r11, [r3, #163]! ; 0xa3
0x8bd4 andsmi r8, pc, r12, ror pc ; <UNPREDICTABLE>
0x8bd8 addmi r12, r12, sp, asr #25
0x8bdc svccc 0x008ccccd
0x8be0 teqmi r3, r3, lsr r3
0x8be4 teqmi r3, r4, lsl lr





Disassembly for receivesMixed:

0x86d0 push {r11, lr}
0x86d4 add r11, sp, #4
0x86d8 sub sp, sp, #24
0x86dc str r0, [r11, #-8]
0x86e0 vstr d0, [r11, #-20] ; 0xffffffec
0x86e4 str r1, [r11, #-12]
0x86e8 vstr s2, [r11, #-24] ; 0xffffffe8
0x86ec ldr r0, [pc, #176] ; 0x87a4 <receivesMixed(int, double, int, float)+212>
0x86f0 ldr r1, [pc, #176] ; 0x87a8 <receivesMixed(int, double, int, float)+216>
0x86f4 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x86f8 mov r3, r0
0x86fc mov r0, r3
0x8700 ldr r1, [r11, #-8]
0x8704 bl 0x85a4 <std::ostream::operator<<(int)>
0x8708 mov r3, r0
0x870c mov r0, r3
0x8710 ldr r1, [pc, #148] ; 0x87ac <receivesMixed(int, double, int, float)+220>
0x8714 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8718 ldr r0, [pc, #132] ; 0x87a4 <receivesMixed(int, double, int, float)+212>
0x871c ldr r1, [pc, #132] ; 0x87a8 <receivesMixed(int, double, int, float)+216>
0x8720 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8724 mov r3, r0
0x8728 mov r0, r3
0x872c vldr d0, [r11, #-20] ; 0xffffffec
0x8730 bl 0x8598 <std::ostream::operator<<(double)>
0x8734 mov r3, r0
0x8738 mov r0, r3
0x873c ldr r1, [pc, #104] ; 0x87ac <receivesMixed(int, double, int, float)+220>
0x8740 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8744 ldr r0, [pc, #88] ; 0x87a4 <receivesMixed(int, double, int, float)+212>
0x8748 ldr r1, [pc, #88] ; 0x87a8 <receivesMixed(int, double, int, float)+216>
0x874c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8750 mov r3, r0
0x8754 mov r0, r3
0x8758 ldr r1, [r11, #-12]
0x875c bl 0x85a4 <std::ostream::operator<<(int)>
0x8760 mov r3, r0
0x8764 mov r0, r3
0x8768 ldr r1, [pc, #60] ; 0x87ac <receivesMixed(int, double, int, float)+220>
0x876c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8770 ldr r0, [pc, #44] ; 0x87a4 <receivesMixed(int, double, int, float)+212>
0x8774 ldr r1, [pc, #44] ; 0x87a8 <receivesMixed(int, double, int, float)+216>
0x8778 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x877c mov r3, r0
0x8780 mov r0, r3
0x8784 vldr s0, [r11, #-24] ; 0xffffffe8
0x8788 bl 0x8604 <std::ostream::operator<<(float)>
0x878c mov r3, r0
0x8790 mov r0, r3
0x8794 ldr r1, [pc, #16] ; 0x87ac <receivesMixed(int, double, int, float)+220>
0x8798 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x879c sub sp, r11, #4
0x87a0 pop {r11, pc}
0x87a4 andeq r0, r1, r8, lsr #29
0x87a8 ldrdeq r8, [r0], -r8 ; <UNPREDICTABLE>
0x87ac andeq r8, r0, r4, ror #25





Disassembly for receivesMixed2:

0x87b0 push {r11, lr}
0x87b4 add r11, sp, #4
0x87b8 sub sp, sp, #16
0x87bc vstr s0, [r11, #-8]
0x87c0 vstr d1, [r11, #-20] ; 0xffffffec
0x87c4 vstr s1, [r11, #-12]
0x87c8 ldr r0, [pc, #132] ; 0x8854 <receivesMixed2(float, double, float)+164>
0x87cc ldr r1, [pc, #132] ; 0x8858 <receivesMixed2(float, double, float)+168>
0x87d0 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87d4 mov r3, r0
0x87d8 mov r0, r3
0x87dc vldr s0, [r11, #-8]
0x87e0 bl 0x8604 <std::ostream::operator<<(float)>
0x87e4 mov r3, r0
0x87e8 mov r0, r3
0x87ec ldr r1, [pc, #104] ; 0x885c <receivesMixed2(float, double, float)+172>
0x87f0 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x87f4 ldr r0, [pc, #88] ; 0x8854 <receivesMixed2(float, double, float)+164>
0x87f8 ldr r1, [pc, #88] ; 0x8858 <receivesMixed2(float, double, float)+168>
0x87fc bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8800 mov r3, r0
0x8804 mov r0, r3
0x8808 vldr d0, [r11, #-20] ; 0xffffffec
0x880c bl 0x8598 <std::ostream::operator<<(double)>
0x8810 mov r3, r0
0x8814 mov r0, r3
0x8818 ldr r1, [pc, #60] ; 0x885c <receivesMixed2(float, double, float)+172>
0x881c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8820 ldr r0, [pc, #44] ; 0x8854 <receivesMixed2(float, double, float)+164>
0x8824 ldr r1, [pc, #44] ; 0x8858 <receivesMixed2(float, double, float)+168>
0x8828 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x882c mov r3, r0
0x8830 mov r0, r3
0x8834 vldr s0, [r11, #-12]
0x8838 bl 0x8604 <std::ostream::operator<<(float)>
0x883c mov r3, r0
0x8840 mov r0, r3
0x8844 ldr r1, [pc, #16] ; 0x885c <receivesMixed2(float, double, float)+172>
0x8848 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x884c sub sp, r11, #4
0x8850 pop {r11, pc}
0x8854 andeq r0, r1, r8, lsr #29
0x8858 ldrdeq r8, [r0], -r8 ; <UNPREDICTABLE>
0x885c andeq r8, r0, r4, ror #25





Disassembly for receivesLots:

0x8860 push {r11, lr}
0x8864 add r11, sp, #4
0x8868 sub sp, sp, #80 ; 0x50
0x886c vstr d0, [r11, #-12]
0x8870 vstr d1, [r11, #-20] ; 0xffffffec
0x8874 vstr d2, [r11, #-28] ; 0xffffffe4
0x8878 vstr d3, [r11, #-36] ; 0xffffffdc
0x887c vstr d4, [r11, #-44] ; 0xffffffd4
0x8880 vstr d5, [r11, #-52] ; 0xffffffcc
0x8884 vstr d6, [r11, #-60] ; 0xffffffc4
0x8888 vstr d7, [r11, #-68] ; 0xffffffbc
0x888c strd r0, [r11, #-76] ; 0xffffffb4
0x8890 strd r2, [r11, #-84] ; 0xffffffac
0x8894 ldr r0, [pc, #572] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8898 ldr r1, [pc, #572] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x889c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88a0 mov r3, r0
0x88a4 mov r0, r3
0x88a8 vldr d0, [r11, #-20] ; 0xffffffec
0x88ac bl 0x8598 <std::ostream::operator<<(double)>
0x88b0 mov r3, r0
0x88b4 mov r0, r3
0x88b8 ldr r1, [pc, #544] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x88bc bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88c0 ldr r0, [pc, #528] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x88c4 ldr r1, [pc, #528] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x88c8 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88cc mov r3, r0
0x88d0 mov r0, r3
0x88d4 vldr d0, [r11, #-28] ; 0xffffffe4
0x88d8 bl 0x8598 <std::ostream::operator<<(double)>
0x88dc mov r3, r0
0x88e0 mov r0, r3
0x88e4 ldr r1, [pc, #500] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x88e8 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88ec ldr r0, [pc, #484] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x88f0 ldr r1, [pc, #484] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x88f4 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x88f8 mov r3, r0
0x88fc mov r0, r3
0x8900 vldr d0, [r11, #-36] ; 0xffffffdc
0x8904 bl 0x8598 <std::ostream::operator<<(double)>
0x8908 mov r3, r0
0x890c mov r0, r3
0x8910 ldr r1, [pc, #456] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8914 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8918 ldr r0, [pc, #440] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x891c ldr r1, [pc, #440] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8920 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8924 mov r3, r0
0x8928 mov r0, r3
0x892c vldr d0, [r11, #-44] ; 0xffffffd4
0x8930 bl 0x8598 <std::ostream::operator<<(double)>
0x8934 mov r3, r0
0x8938 mov r0, r3
0x893c ldr r1, [pc, #412] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8940 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8944 ldr r0, [pc, #396] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8948 ldr r1, [pc, #396] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x894c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8950 mov r3, r0
0x8954 mov r0, r3
0x8958 vldr d0, [r11, #-52] ; 0xffffffcc
0x895c bl 0x8598 <std::ostream::operator<<(double)>
0x8960 mov r3, r0
0x8964 mov r0, r3
0x8968 ldr r1, [pc, #368] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x896c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8970 ldr r0, [pc, #352] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8974 ldr r1, [pc, #352] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8978 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x897c mov r3, r0
0x8980 mov r0, r3
0x8984 vldr d0, [r11, #-60] ; 0xffffffc4
0x8988 bl 0x8598 <std::ostream::operator<<(double)>
0x898c mov r3, r0
0x8990 mov r0, r3
0x8994 ldr r1, [pc, #324] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8998 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x899c ldr r0, [pc, #308] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x89a0 ldr r1, [pc, #308] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x89a4 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x89a8 mov r3, r0
0x89ac mov r0, r3
0x89b0 vldr d0, [r11, #-68] ; 0xffffffbc
0x89b4 bl 0x8598 <std::ostream::operator<<(double)>
0x89b8 mov r3, r0
0x89bc mov r0, r3
0x89c0 ldr r1, [pc, #280] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x89c4 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x89c8 ldr r0, [pc, #264] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x89cc ldr r1, [pc, #264] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x89d0 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x89d4 mov r3, r0
0x89d8 mov r0, r3
0x89dc vldr d0, [r11, #4]
0x89e0 bl 0x8598 <std::ostream::operator<<(double)>
0x89e4 mov r3, r0
0x89e8 mov r0, r3
0x89ec ldr r1, [pc, #236] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x89f0 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x89f4 ldr r0, [pc, #220] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x89f8 ldr r1, [pc, #220] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x89fc bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a00 mov r3, r0
0x8a04 mov r0, r3
0x8a08 vldr d0, [r11, #12]
0x8a0c bl 0x8598 <std::ostream::operator<<(double)>
0x8a10 mov r3, r0
0x8a14 mov r0, r3
0x8a18 ldr r1, [pc, #192] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8a1c bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a20 ldr r0, [pc, #176] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8a24 ldr r1, [pc, #176] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8a28 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a2c mov r3, r0
0x8a30 mov r0, r3
0x8a34 vldr s0, [r11, #20]
0x8a38 bl 0x8604 <std::ostream::operator<<(float)>
0x8a3c mov r3, r0
0x8a40 mov r0, r3
0x8a44 ldr r1, [pc, #148] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8a48 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a4c ldr r0, [pc, #132] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8a50 ldr r1, [pc, #132] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8a54 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a58 mov r3, r0
0x8a5c mov r0, r3
0x8a60 vldr s0, [r11, #24]
0x8a64 bl 0x8604 <std::ostream::operator<<(float)>
0x8a68 mov r3, r0
0x8a6c mov r0, r3
0x8a70 ldr r1, [pc, #104] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8a74 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a78 ldr r0, [pc, #88] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8a7c ldr r1, [pc, #88] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8a80 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8a84 mov r3, r0
0x8a88 mov r0, r3
0x8a8c ldrd r2, [r11, #-76] ; 0xffffffb4
0x8a90 bl 0x8610 <std::ostream::operator<<(long long)>
0x8a94 mov r3, r0
0x8a98 mov r0, r3
0x8a9c ldr r1, [pc, #60] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8aa0 bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8aa4 ldr r0, [pc, #44] ; 0x8ad8 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+632>
0x8aa8 ldr r1, [pc, #44] ; 0x8adc <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+636>
0x8aac bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8ab0 mov r3, r0
0x8ab4 mov r0, r3
0x8ab8 ldrd r2, [r11, #-84] ; 0xffffffac
0x8abc bl 0x8610 <std::ostream::operator<<(long long)>
0x8ac0 mov r3, r0
0x8ac4 mov r0, r3
0x8ac8 ldr r1, [pc, #16] ; 0x8ae0 <receivesLots(double, double, double, double, double, double, double, double, double, double, float, float, long long, long long)+640>
0x8acc bl 0x85ec <std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)>
0x8ad0 sub sp, r11, #4
0x8ad4 pop {r11, pc}
0x8ad8 andeq r0, r1, r8, lsr #29
0x8adc ldrdeq r8, [r0], -r8 ; <UNPREDICTABLE>
0x8ae0 andeq r8, r0, r4, ror #25



I guess we can conclude that we have 8 "d" registers (or 16 "s"?) and long long are passed using 2 "r", right?

This topic is closed to new replies.

Advertisement