; #include <stdlib.h>
;
; void leaf_call(int b, int c, int d, int e, int f, int g, int h)
; {
; }
;
; void nonleaf_call(int a, int b, int c, int d, int e, int f, int g, int h)
; {
; /* use some local data */
; *(char*)alloca(220) = 'L';
; leaf_call(b, c, d, e, f, g, h);
; }
;
; int main()
; {
; nonleaf_call(0, 1, 2, 3, 4, 5, 6, 7);
; return 0;
; }
; output from freebsd-12.0_r333647-malta_mipselhf w/ gcc 4.2.1 ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <nonleaf_call>:
38: 3c1c0000 lui gp,0x0 ; |
3c: 279c0000 addiu gp,gp,0 ; |
40: 0399e021 addu gp,gp,t9 ; |
44: 27bdffc8 addiu sp,sp,-56 ; | prolog
48: afbf0034 sw ra,52(sp) ; |
4c: afbe0030 sw s8,48(sp) ; |
50: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
54: afbc0020 sw gp,32(sp) ; /
58: afc40038 sw a0,56(s8) ; \
5c: afc5003c sw a1,60(s8) ; |
60: afc60040 sw a2,64(s8) ; | spill first 4 args into prev frame's reserved spill space in param area (although not actually needing to spill, here but just do a temp copy, but space is reserved for them anyways)
64: afc70044 sw a3,68(s8) ; |
68: 27bdff18 addiu sp,sp,-232 ; alloca(220) - with padding to guarantee alignment
6c: 27a20020 addiu v0,sp,32 ; |
70: afc20028 sw v0,40(s8) ; |
74: 8fc30028 lw v1,40(s8) ; | start of alloca()'d memory -> v1, by ...
78: 24620007 addiu v0,v1,7 ; | ... using v0 as helper to align to 8b
7c: 000210c2 srl v0,v0,0x3 ; | @@@ unsure about use of helper space at 40(s8) in prev frame..?
80: 000210c0 sll v0,v0,0x3 ; |
84: afc20028 sw v0,40(s8) ; |
88: 8fc30028 lw v1,40(s8) ; |
8c: 2402004c li v0,76 ; 'L' -> v0, and...
90: a0620000 sb v0,0(v1) ; ... store in local area (of alloca()'d space)
94: 8fc2004c lw v0,76(s8) ; arg 4 (fetched from prev frame's param area), and ...
98: afa20010 sw v0,16(sp) ; ... "pushed" onto stack
9c: 8fc20050 lw v0,80(s8) ; arg 5 (fetched from prev frame's param area), and ...
a0: afa20014 sw v0,20(sp) ; ... "pushed" onto stack
a4: 8fc20054 lw v0,84(s8) ; arg 6 (fetched from prev frame's param area), and ...
a8: afa20018 sw v0,24(sp) ; ... "pushed" onto stack
ac: 8fc4003c lw a0,60(s8) ; arg 0 (fetched from spill area of prev frame)
b0: 8fc50040 lw a1,64(s8) ; arg 1 (fetched from spill area of prev frame)
b4: 8fc60044 lw a2,68(s8) ; arg 2 (fetched from spill area of prev frame)
b8: 8fc70048 lw a3,72(s8) ; arg 3 (fetched from prev frame's param area)
bc: 8f990000 lw t9,0(gp) ; func to call -> t9
c0: 0320f809 jalr t9 ; call and ret addr -> ra
c4: 00000000 nop ; branch delay slot
c8: 8fdc0020 lw gp,32(s8) ; |
cc: 03c0e821 move sp,s8 ; |
d0: 8fbf0034 lw ra,52(sp) ; |
d4: 8fbe0030 lw s8,48(sp) ; | epilog
d8: 03e00008 jr ra ; |
dc: 27bd0038 addiu sp,sp,56 ; |
000000e0 <main>:
e0: 3c1c0000 lui gp,0x0 ; |
e4: 279c0000 addiu gp,gp,0 ; |
e8: 0399e021 addu gp,gp,t9 ; |
ec: 27bdffd0 addiu sp,sp,-48 ; | prolog
f0: afbf002c sw ra,44(sp) ; |
f4: afbe0028 sw s8,40(sp) ; |
f8: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
fc: afbc0020 sw gp,32(sp) ; |
100: 24020004 li v0,4 ; arg 4, and ...
104: afa20010 sw v0,16(sp) ; ... "pushed" onto stack
108: 24020005 li v0,5 ; arg 5, and ...
10c: afa20014 sw v0,20(sp) ; ... "pushed" onto stack
110: 24020006 li v0,6 ; arg 6, and ...
114: afa20018 sw v0,24(sp) ; ... "pushed" onto stack
118: 24020007 li v0,7 ; arg 7, and ...
11c: afa2001c sw v0,28(sp) ; ... "pushed" onto stack
120: 00002021 move a0,zero ; arg 0
124: 24050001 li a1,1 ; arg 1
128: 24060002 li a2,2 ; arg 2
12c: 24070003 li a3,3 ; arg 3
130: 8f990000 lw t9,0(gp) ; func to call -> t9
134: 0320f809 jalr t9 ; call and ret addr -> ra
138: 00000000 nop ; branch delay slot
13c: 8fdc0020 lw gp,32(s8) ; |
140: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
144: 03c0e821 move sp,s8 ; |
148: 8fbf002c lw ra,44(sp) ; | epilog
14c: 8fbe0028 lw s8,40(sp) ; |
150: 03e00008 jr ra ; |
154: 27bd0030 addiu sp,sp,48 ; |
; output from netbsd-5.0.2-pmax_mipsel_o32 w/ gcc 4.1.3 ----->
; nearly the same, equivalent to above except non-optimal use of branch delay slots and $gp preserving in leaf call
00000000 <leaf_call>:
0: 27bdfff8 addiu sp,sp,-8
4: afbe0000 sw s8,0(sp)
8: 03a0f021 move s8,sp
c: afc40008 sw a0,8(s8)
10: afc5000c sw a1,12(s8)
14: afc60010 sw a2,16(s8)
18: afc70014 sw a3,20(s8)
1c: 03c0e821 move sp,s8
20: 8fbe0000 lw s8,0(sp)
24: 27bd0008 addiu sp,sp,8
28: 03e00008 jr ra
2c: 00000000 nop
00000030 <nonleaf_call>:
30: 3c1c0000 lui gp,0x0
34: 279c0000 addiu gp,gp,0
38: 0399e021 addu gp,gp,t9
3c: 27bdffc8 addiu sp,sp,-56
40: afbf0034 sw ra,52(sp)
44: afbe0030 sw s8,48(sp)
48: 03a0f021 move s8,sp
4c: afbc0020 sw gp,32(sp)
50: afc40038 sw a0,56(s8)
54: afc5003c sw a1,60(s8)
58: afc60040 sw a2,64(s8)
5c: afc70044 sw a3,68(s8)
60: 27bdff18 addiu sp,sp,-232
64: 27a20020 addiu v0,sp,32
68: afc20028 sw v0,40(s8)
6c: 8fc30028 lw v1,40(s8)
70: 00000000 nop
74: 24620007 addiu v0,v1,7
78: 000210c2 srl v0,v0,0x3
7c: 000210c0 sll v0,v0,0x3
80: afc20028 sw v0,40(s8)
84: 8fc30028 lw v1,40(s8)
88: 2402004c li v0,76
8c: a0620000 sb v0,0(v1)
90: 8fc2004c lw v0,76(s8)
94: 00000000 nop
98: afa20010 sw v0,16(sp)
9c: 8fc20050 lw v0,80(s8)
a0: 00000000 nop
a4: afa20014 sw v0,20(sp)
a8: 8fc20054 lw v0,84(s8)
ac: 00000000 nop
b0: afa20018 sw v0,24(sp)
b4: 8fc4003c lw a0,60(s8)
b8: 8fc50040 lw a1,64(s8)
bc: 8fc60044 lw a2,68(s8)
c0: 8fc70048 lw a3,72(s8)
c4: 8f990000 lw t9,0(gp)
c8: 00000000 nop
cc: 0320f809 jalr t9
d0: 00000000 nop
d4: 8fdc0020 lw gp,32(s8)
d8: 03c0e821 move sp,s8
dc: 8fbf0034 lw ra,52(sp)
e0: 8fbe0030 lw s8,48(sp)
e4: 27bd0038 addiu sp,sp,56
e8: 03e00008 jr ra
ec: 00000000 nop
000000f0 <main>:
f0: 3c1c0000 lui gp,0x0
f4: 279c0000 addiu gp,gp,0
f8: 0399e021 addu gp,gp,t9
fc: 27bdffd0 addiu sp,sp,-48
100: afbf002c sw ra,44(sp)
104: afbe0028 sw s8,40(sp)
108: 03a0f021 move s8,sp
10c: afbc0020 sw gp,32(sp)
110: 24020004 li v0,4
114: afa20010 sw v0,16(sp)
118: 24020005 li v0,5
11c: afa20014 sw v0,20(sp)
120: 24020006 li v0,6
124: afa20018 sw v0,24(sp)
128: 24020007 li v0,7
12c: afa2001c sw v0,28(sp)
130: 00002021 move a0,zero
134: 24050001 li a1,1
138: 24060002 li a2,2
13c: 24070003 li a3,3
140: 8f990000 lw t9,0(gp)
144: 00000000 nop
148: 0320f809 jalr t9
14c: 00000000 nop
150: 8fdc0020 lw gp,32(s8)
154: 00001021 move v0,zero
158: 03c0e821 move sp,s8
15c: 8fbf002c lw ra,44(sp)
160: 8fbe0028 lw s8,40(sp)
164: 27bd0030 addiu sp,sp,48
168: 03e00008 jr ra
16c: 00000000 nop
; ---------- structs by value ---------->
;
; struct A { int i, j; long long l; };
;
; void leaf_call(int b, int c, int d, int e, struct A f, int g, int h)
; {
; }
;
; void nonleaf_call(int a, int b, int c, int d, int e, struct A f, int g, int h)
; {
; /* use some local data */
; char l[100] ={ 'L'};
; leaf_call(b, c, d, e, f, g, h);
; }
;
; int main()
; {
; nonleaf_call(0, 1, 2, 3, 4, (struct A){5, 6, 7ll}, 8, 9);
; return 0;
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <nonleaf_call>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdff60 addiu sp,sp,-160
48: afbf009c sw ra,156(sp)
4c: afbe0098 sw s8,152(sp)
50: 03a0f021 move s8,sp
54: afbc0028 sw gp,40(sp)
58: afc400a0 sw a0,160(s8)
5c: afc500a4 sw a1,164(s8)
60: afc600a8 sw a2,168(s8)
64: afc700ac sw a3,172(s8)
68: 27c20030 addiu v0,s8,48
6c: 24030064 li v1,100
70: 00402021 move a0,v0
74: 00002821 move a1,zero
78: 00603021 move a2,v1
7c: 8f990000 lw t9,0(gp)
80: 0320f809 jalr t9
84: 00000000 nop
88: 8fdc0028 lw gp,40(s8)
8c: 2402004c li v0,76
90: a3c20030 sb v0,48(s8)
94: 8fc200b8 lw v0,184(s8)
98: 8fc300bc lw v1,188(s8)
9c: 8fc400c0 lw a0,192(s8)
a0: 8fc500c4 lw a1,196(s8)
a4: afa20010 sw v0,16(sp)
a8: afa30014 sw v1,20(sp)
ac: afa40018 sw a0,24(sp)
b0: afa5001c sw a1,28(sp)
b4: 8fc200c8 lw v0,200(s8)
b8: afa20020 sw v0,32(sp)
bc: 8fc200cc lw v0,204(s8)
c0: afa20024 sw v0,36(sp)
c4: 8fc400a4 lw a0,164(s8)
c8: 8fc500a8 lw a1,168(s8)
cc: 8fc600ac lw a2,172(s8)
d0: 8fc700b0 lw a3,176(s8)
d4: 8f990000 lw t9,0(gp)
d8: 0320f809 jalr t9
dc: 00000000 nop
e0: 8fdc0028 lw gp,40(s8)
e4: 03c0e821 move sp,s8
e8: 8fbf009c lw ra,156(sp)
ec: 8fbe0098 lw s8,152(sp)
f0: 03e00008 jr ra
f4: 27bd00a0 addiu sp,sp,160
000000f8 <main>:
f8: 3c1c0000 lui gp,0x0 ; |
fc: 279c0000 addiu gp,gp,0 ; |
100: 0399e021 addu gp,gp,t9 ; |
104: 27bdffb0 addiu sp,sp,-80 ; | prolog
108: afbf004c sw ra,76(sp) ; |
10c: afbe0048 sw s8,72(sp) ; |
110: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
114: afbc0030 sw gp,48(sp) ; /
118: 8f820000 lw v0,0(gp) ; \ \
11c: 24420000 addiu v0,v0,0 ; | | field j -> v0
120: 8c420000 lw v0,0(v0) ; | /
124: 8f830000 lw v1,0(gp) ; | \
128: 24630000 addiu v1,v1,0 ; | | field j -> v1
12c: 8c630004 lw v1,4(v1) ; | prep local struct A data ... /
130: 8f840000 lw a0,0(gp) ; | \
134: 24840000 addiu a0,a0,0 ; | |
138: 8c840008 lw a0,8(a0) ; | | field l -> a0 & a1
13c: 8f850000 lw a1,0(gp) ; | |
140: 24a50000 addiu a1,a1,0 ; | |
144: 8ca5000c lw a1,12(a1) ; / /
148: afc20038 sw v0,56(s8) ; \
14c: afc3003c sw v1,60(s8) ; | ... and write to local area
150: afc40040 sw a0,64(s8) ; |
154: afc50044 sw a1,68(s8) ; /
158: 24020004 li v0,4 ; push arg 4 ...
15c: afa20010 sw v0,16(sp) ; ... onto stack
160: 8fc20038 lw v0,56(s8) ; \
164: 8fc3003c lw v1,60(s8) ; |
168: 8fc40040 lw a0,64(s8) ; | prep arg 5 (struct A) ...
16c: 8fc50044 lw a1,68(s8) ; /
170: afa20018 sw v0,24(sp) ; \
174: afa3001c sw v1,28(sp) ; | ... and push onto stack
178: afa40020 sw a0,32(sp) ; |
17c: afa50024 sw a1,36(sp) ; /
180: 24020008 li v0,8 ; push arg 6 ...
184: afa20028 sw v0,40(sp) ; ... onto stack
188: 24020009 li v0,9 ; push arg 7 ...
18c: afa2002c sw v0,44(sp) ; ... onto stack
190: 00002021 move a0,zero ; arg 0
194: 24050001 li a1,1 ; arg 1
198: 24060002 li a2,2 ; arg 2
19c: 24070003 li a3,3 ; arg 3
1a0: 8f990000 lw t9,0(gp) ; func to call -> t9
1a4: 0320f809 jalr t9 ; call and ret addr -> ra
1a8: 00000000 nop ; branch delay slot
1ac: 8fdc0030 lw gp,48(s8) ; |
1b0: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
1b4: 03c0e821 move sp,s8 ; |
1b8: 8fbf004c lw ra,76(sp) ; | epilog
1bc: 8fbe0048 lw s8,72(sp) ; |
1c0: 03e00008 jr ra ; |
1c4: 27bd0050 addiu sp,sp,80 ; |
...
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <nonleaf_call>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdff60 addiu sp,sp,-160
48: afbf009c sw ra,156(sp)
4c: afbe0098 sw s8,152(sp)
50: 03a0f021 move s8,sp
54: afbc0028 sw gp,40(sp)
58: afc400a0 sw a0,160(s8)
5c: afc500a4 sw a1,164(s8)
60: afc600a8 sw a2,168(s8)
64: afc700ac sw a3,172(s8)
68: 27c20030 addiu v0,s8,48
6c: 24030064 li v1,100
70: 00402021 move a0,v0
74: 00002821 move a1,zero
78: 00603021 move a2,v1
7c: 8f990000 lw t9,0(gp)
80: 0320f809 jalr t9
84: 00000000 nop
88: 8fdc0028 lw gp,40(s8)
8c: 2402004c li v0,76
90: a3c20030 sb v0,48(s8)
94: 8fc200b8 lw v0,184(s8)
98: 8fc300bc lw v1,188(s8)
9c: 8fc400c0 lw a0,192(s8)
a0: 8fc500c4 lw a1,196(s8)
a4: afa20010 sw v0,16(sp)
a8: afa30014 sw v1,20(sp)
ac: afa40018 sw a0,24(sp)
b0: afa5001c sw a1,28(sp)
b4: 8fc200c8 lw v0,200(s8)
b8: afa20020 sw v0,32(sp)
bc: 8fc200cc lw v0,204(s8)
c0: afa20024 sw v0,36(sp)
c4: 8fc400a4 lw a0,164(s8)
c8: 8fc500a8 lw a1,168(s8)
cc: 8fc600ac lw a2,172(s8)
d0: 8fc700b0 lw a3,176(s8)
d4: 8f990000 lw t9,0(gp)
d8: 0320f809 jalr t9
dc: 00000000 nop
e0: 8fdc0028 lw gp,40(s8)
e4: 03c0e821 move sp,s8
e8: 8fbf009c lw ra,156(sp)
ec: 8fbe0098 lw s8,152(sp)
f0: 03e00008 jr ra
f4: 27bd00a0 addiu sp,sp,160
000000f8 <main>:
f8: 3c1c0000 lui gp,0x0 ; |
fc: 279c0000 addiu gp,gp,0 ; |
100: 0399e021 addu gp,gp,t9 ; |
104: 27bdffb0 addiu sp,sp,-80 ; | prolog
108: afbf004c sw ra,76(sp) ; |
10c: afbe0048 sw s8,72(sp) ; |
110: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
114: afbc0030 sw gp,48(sp) ; /
118: 8f820000 lw v0,0(gp) ; \ \
11c: 24420000 addiu v0,v0,0 ; | | field j -> v0
120: 8c420000 lw v0,0(v0) ; | /
124: 8f830000 lw v1,0(gp) ; | \
128: 24630000 addiu v1,v1,0 ; | | field j -> v1
12c: 8c630004 lw v1,4(v1) ; | prep local struct A data ... /
130: 8f840000 lw a0,0(gp) ; | \
134: 24840000 addiu a0,a0,0 ; | |
138: 8c840008 lw a0,8(a0) ; | | field l -> a0 & a1
13c: 8f850000 lw a1,0(gp) ; | |
140: 24a50000 addiu a1,a1,0 ; | |
144: 8ca5000c lw a1,12(a1) ; / /
148: afc20038 sw v0,56(s8) ; \
14c: afc3003c sw v1,60(s8) ; | ... and write to local area
150: afc40040 sw a0,64(s8) ; |
154: afc50044 sw a1,68(s8) ; /
158: 24020004 li v0,4 ; push arg 4 ...
15c: afa20010 sw v0,16(sp) ; ... onto stack
160: 8fc20038 lw v0,56(s8) ; \
164: 8fc3003c lw v1,60(s8) ; |
168: 8fc40040 lw a0,64(s8) ; | prep arg 5 (struct A) ...
16c: 8fc50044 lw a1,68(s8) ; /
170: afa20018 sw v0,24(sp) ; \
174: afa3001c sw v1,28(sp) ; | ... and push onto stack
178: afa40020 sw a0,32(sp) ; |
17c: afa50024 sw a1,36(sp) ; /
180: 24020008 li v0,8 ; push arg 6 ...
184: afa20028 sw v0,40(sp) ; ... onto stack
188: 24020009 li v0,9 ; push arg 7 ...
18c: afa2002c sw v0,44(sp) ; ... onto stack
190: 00002021 move a0,zero ; arg 0
194: 24050001 li a1,1 ; arg 1
198: 24060002 li a2,2 ; arg 2
19c: 24070003 li a3,3 ; arg 3
1a0: 8f990000 lw t9,0(gp) ; func to call -> t9
1a4: 0320f809 jalr t9 ; call and ret addr -> ra
1a8: 00000000 nop ; branch delay slot
1ac: 8fdc0030 lw gp,48(s8) ; |
1b0: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
1b4: 03c0e821 move sp,s8 ; |
1b8: 8fbf004c lw ra,76(sp) ; | epilog
1bc: 8fbe0048 lw s8,72(sp) ; |
1c0: 03e00008 jr ra ; |
1c4: 27bd0050 addiu sp,sp,80 ; |
...
; ---------- structs by value, complex example (multiple structs) ---------->
;
; struct A { int i, j; float f; };
; struct B { double d; long long l; };
;
; void leaf_call(int b, struct A c, struct B d, int e, int f, struct A g, struct B h, int i, int j)
; {
; }
;
; void nonleaf_call(int a, int b, struct A c, struct B d, int e, int f, struct A g, struct B h, int i, int j)
; {
; /* use some local data */
; char l[100] ={ 'L'};
; leaf_call(b, c, d, e, f, g, h, i, j);
; }
;
; int main()
; {
; nonleaf_call(0, 1, (struct A){2, 3, 4.f}, (struct B){5., 6ll}, 7, 8, (struct A){9, 10, 11.f}, (struct B){12., 13ll}, 14, 15);
; return 0;
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <nonleaf_call>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdff38 addiu sp,sp,-200
48: afbf00c4 sw ra,196(sp)
4c: afbe00c0 sw s8,192(sp)
50: 03a0f021 move s8,sp
54: afbc0050 sw gp,80(sp)
58: afc400c8 sw a0,200(s8)
5c: afc500cc sw a1,204(s8)
60: afc600d0 sw a2,208(s8)
64: afc700d4 sw a3,212(s8)
68: 27c20058 addiu v0,s8,88
6c: 24030064 li v1,100
70: 00402021 move a0,v0
74: 00002821 move a1,zero
78: 00603021 move a2,v1
7c: 8f990000 lw t9,0(gp)
80: 0320f809 jalr t9
84: 00000000 nop
88: 8fdc0050 lw gp,80(s8)
8c: 2402004c li v0,76
90: a3c20058 sb v0,88(s8)
94: 8fc200e0 lw v0,224(s8)
98: 8fc300e4 lw v1,228(s8)
9c: 8fc400e8 lw a0,232(s8)
a0: 8fc500ec lw a1,236(s8)
a4: afa20010 sw v0,16(sp)
a8: afa30014 sw v1,20(sp)
ac: afa40018 sw a0,24(sp)
b0: afa5001c sw a1,28(sp)
b4: 8fc200f0 lw v0,240(s8)
b8: afa20020 sw v0,32(sp)
bc: 8fc200f4 lw v0,244(s8)
c0: afa20024 sw v0,36(sp)
c4: 8fc200f8 lw v0,248(s8)
c8: 8fc300fc lw v1,252(s8)
cc: 8fc40100 lw a0,256(s8)
d0: afa20028 sw v0,40(sp)
d4: afa3002c sw v1,44(sp)
d8: afa40030 sw a0,48(sp)
dc: 8fc20108 lw v0,264(s8)
e0: 8fc3010c lw v1,268(s8)
e4: 8fc40110 lw a0,272(s8)
e8: 8fc50114 lw a1,276(s8)
ec: afa20038 sw v0,56(sp)
f0: afa3003c sw v1,60(sp)
f4: afa40040 sw a0,64(sp)
f8: afa50044 sw a1,68(sp)
fc: 8fc20118 lw v0,280(s8)
100: afa20048 sw v0,72(sp)
104: 8fc2011c lw v0,284(s8)
108: afa2004c sw v0,76(sp)
10c: 8fc400cc lw a0,204(s8)
110: 8fc500d0 lw a1,208(s8)
114: 8fc600d4 lw a2,212(s8)
118: 8fc700d8 lw a3,216(s8)
11c: 8f990000 lw t9,0(gp)
120: 0320f809 jalr t9
124: 00000000 nop
128: 8fdc0050 lw gp,80(s8)
12c: 03c0e821 move sp,s8
130: 8fbf00c4 lw ra,196(sp)
134: 8fbe00c0 lw s8,192(sp)
138: 03e00008 jr ra
13c: 27bd00c8 addiu sp,sp,200
00000140 <main>:
140: 3c1c0000 lui gp,0x0 ; |
144: 279c0000 addiu gp,gp,0 ; |
148: 0399e021 addu gp,gp,t9 ; |
14c: 27bdff58 addiu sp,sp,-168 ; | prolog
150: afbf00a4 sw ra,164(sp) ; |
154: afbe00a0 sw s8,160(sp) ; |
158: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
15c: afbc0058 sw gp,88(sp) ; /
160: 8f820000 lw v0,0(gp) ; \ |
164: 24420030 addiu v0,v0,48 ; | | field j -> v0
168: 8c420000 lw v0,0(v0) ; | /
16c: 8f830000 lw v1,0(gp) ; | prep (first) local struct A data ... \
170: 24630030 addiu v1,v1,48 ; | | field j -> v1
174: 8c630004 lw v1,4(v1) ; | /
178: 8f840000 lw a0,0(gp) ; | \
17c: 24840030 addiu a0,a0,48 ; | | field f -> a0
180: 8c840008 lw a0,8(a0) ; / |
184: afc20090 sw v0,144(s8) ; \
188: afc30094 sw v1,148(s8) ; | ... and write to local area
18c: afc40098 sw a0,152(s8) ; /
190: 8f820000 lw v0,0(gp) ; \ |
194: 24420020 addiu v0,v0,32 ; | |
198: 8c420000 lw v0,0(v0) ; | |
19c: 8f830000 lw v1,0(gp) ; | | field d -> v0 & v1
1a0: 24630020 addiu v1,v1,32 ; | |
1a4: 8c630004 lw v1,4(v1) ; | prep (first) local struct B data ... /
1a8: 8f840000 lw a0,0(gp) ; | \
1ac: 24840020 addiu a0,a0,32 ; | |
1b0: 8c840008 lw a0,8(a0) ; | |
1b4: 8f850000 lw a1,0(gp) ; | | field l -> a0 & a1
1b8: 24a50020 addiu a1,a1,32 ; | |
1bc: 8ca5000c lw a1,12(a1) ; / |
1c0: afc20080 sw v0,128(s8) ; \
1c4: afc30084 sw v1,132(s8) ; |
1c8: afc40088 sw a0,136(s8) ; | ... and write to local area
1cc: afc5008c sw a1,140(s8) ; /
1d0: 8f820000 lw v0,0(gp) ; \ |
1d4: 24420010 addiu v0,v0,16 ; | | field j -> v0
1d8: 8c420000 lw v0,0(v0) ; | /
1dc: 8f830000 lw v1,0(gp) ; | prep (second) local struct A data ... \
1e0: 24630010 addiu v1,v1,16 ; | | field j -> v1
1e4: 8c630004 lw v1,4(v1) ; | /
1e8: 8f840000 lw a0,0(gp) ; | \
1ec: 24840010 addiu a0,a0,16 ; | | field f -> a0
1f0: 8c840008 lw a0,8(a0) ; / |
1f4: afc20070 sw v0,112(s8) ; \
1f8: afc30074 sw v1,116(s8) ; | ... and write to local area
1fc: afc40078 sw a0,120(s8) ; /
200: 8f820000 lw v0,0(gp) ; \ |
204: 24420000 addiu v0,v0,0 ; | |
208: 8c420000 lw v0,0(v0) ; | |
20c: 8f830000 lw v1,0(gp) ; | | field d -> v0 & v1
210: 24630000 addiu v1,v1,0 ; | |
214: 8c630004 lw v1,4(v1) ; | prep (second) local struct B data ... /
218: 8f840000 lw a0,0(gp) ; | \
21c: 24840000 addiu a0,a0,0 ; | |
220: 8c840008 lw a0,8(a0) ; | |
224: 8f850000 lw a1,0(gp) ; | | field l -> a0 & a1
228: 24a50000 addiu a1,a1,0 ; | |
22c: 8ca5000c lw a1,12(a1) ; / |
230: afc20060 sw v0,96(s8) ; \
234: afc30064 sw v1,100(s8) ; |
238: afc40068 sw a0,104(s8) ; | ... and write to local area
23c: afc5006c sw a1,108(s8) ; /
240: 8fc20080 lw v0,128(s8) ; \
244: 8fc30084 lw v1,132(s8) ; |
248: 8fc40088 lw a0,136(s8) ; |
24c: 8fc5008c lw a1,140(s8) ; |
250: afa20018 sw v0,24(sp) ; | | d
254: afa3001c sw v1,28(sp) ; | arg 3 (first struct B) /
258: afa40020 sw a0,32(sp) ; | \
25c: afa50024 sw a1,36(sp) ; / | l
260: 24020007 li v0,7 ; \
264: afa20028 sw v0,40(sp) ; / arg 4
268: 24020008 li v0,8 ; \
26c: afa2002c sw v0,44(sp) ; / arg 5
270: 8fc20070 lw v0,112(s8) ; \
274: 8fc30074 lw v1,116(s8) ; |
278: 8fc40078 lw a0,120(s8) ; | arg 6 (second struct A, note that 60(sp) isn't used, so sizeof(struct A) is probably a padded 16)
27c: afa20030 sw v0,48(sp) ; | i
280: afa30034 sw v1,52(sp) ; | j
284: afa40038 sw a0,56(sp) ; / f
288: 8fc20060 lw v0,96(s8) ; \
28c: 8fc30064 lw v1,100(s8) ; |
290: 8fc40068 lw a0,104(s8) ; |
294: 8fc5006c lw a1,108(s8) ; |
298: afa20040 sw v0,64(sp) ; | | d
29c: afa30044 sw v1,68(sp) ; | arg 7 (second struct B) /
2a0: afa40048 sw a0,72(sp) ; | \
2a4: afa5004c sw a1,76(sp) ; | | l
2a8: 2402000e li v0,14 ; arg 8 pushed ...
2ac: afa20050 sw v0,80(sp) ; ... onto stack
2b0: 2402000f li v0,15 ; arg 9 pushed ...
2b4: afa20054 sw v0,84(sp) ; ... onto stack
2b8: 8fc20098 lw v0,152(s8) ; | | f (via stack, first slot after save area)
2bc: afa20010 sw v0,16(sp) ; | | note that 20(sp) isn't used, so sizeof(struct A) is probably a padded 16
2c0: 8fc60090 lw a2,144(s8) ; | arg 2 (first struct A) i (via reg)
2c4: 8fc70094 lw a3,148(s8) ; | j (via reg)
2c8: 00002021 move a0,zero ; arg 0
2cc: 24050001 li a1,1 ; arg 1
2d0: 8f990000 lw t9,0(gp) ; func to call -> t9
2d4: 0320f809 jalr t9 ; call and ret addr -> ra
2d8: 00000000 nop ; branch delay slot
2dc: 8fdc0058 lw gp,88(s8) ; |
2e0: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
2e4: 03c0e821 move sp,s8 ; |
2e8: 8fbf00a4 lw ra,164(sp) ; | epilog
2ec: 8fbe00a0 lw s8,160(sp) ; |
2f0: 03e00008 jr ra ; |
2f4: 27bd00a8 addiu sp,sp,168 ; |
...
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <nonleaf_call>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdff38 addiu sp,sp,-200
48: afbf00c4 sw ra,196(sp)
4c: afbe00c0 sw s8,192(sp)
50: 03a0f021 move s8,sp
54: afbc0050 sw gp,80(sp)
58: afc400c8 sw a0,200(s8)
5c: afc500cc sw a1,204(s8)
60: afc600d0 sw a2,208(s8)
64: afc700d4 sw a3,212(s8)
68: 27c20058 addiu v0,s8,88
6c: 24030064 li v1,100
70: 00402021 move a0,v0
74: 00002821 move a1,zero
78: 00603021 move a2,v1
7c: 8f990000 lw t9,0(gp)
80: 0320f809 jalr t9
84: 00000000 nop
88: 8fdc0050 lw gp,80(s8)
8c: 2402004c li v0,76
90: a3c20058 sb v0,88(s8)
94: 8fc200e0 lw v0,224(s8)
98: 8fc300e4 lw v1,228(s8)
9c: 8fc400e8 lw a0,232(s8)
a0: 8fc500ec lw a1,236(s8)
a4: afa20010 sw v0,16(sp)
a8: afa30014 sw v1,20(sp)
ac: afa40018 sw a0,24(sp)
b0: afa5001c sw a1,28(sp)
b4: 8fc200f0 lw v0,240(s8)
b8: afa20020 sw v0,32(sp)
bc: 8fc200f4 lw v0,244(s8)
c0: afa20024 sw v0,36(sp)
c4: 8fc200f8 lw v0,248(s8)
c8: 8fc300fc lw v1,252(s8)
cc: 8fc40100 lw a0,256(s8)
d0: afa20028 sw v0,40(sp)
d4: afa3002c sw v1,44(sp)
d8: afa40030 sw a0,48(sp)
dc: 8fc20108 lw v0,264(s8)
e0: 8fc3010c lw v1,268(s8)
e4: 8fc40110 lw a0,272(s8)
e8: 8fc50114 lw a1,276(s8)
ec: afa20038 sw v0,56(sp)
f0: afa3003c sw v1,60(sp)
f4: afa40040 sw a0,64(sp)
f8: afa50044 sw a1,68(sp)
fc: 8fc20118 lw v0,280(s8)
100: afa20048 sw v0,72(sp)
104: 8fc2011c lw v0,284(s8)
108: afa2004c sw v0,76(sp)
10c: 8fc400cc lw a0,204(s8)
110: 8fc500d0 lw a1,208(s8)
114: 8fc600d4 lw a2,212(s8)
118: 8fc700d8 lw a3,216(s8)
11c: 8f990000 lw t9,0(gp)
120: 0320f809 jalr t9
124: 00000000 nop
128: 8fdc0050 lw gp,80(s8)
12c: 03c0e821 move sp,s8
130: 8fbf00c4 lw ra,196(sp)
134: 8fbe00c0 lw s8,192(sp)
138: 03e00008 jr ra
13c: 27bd00c8 addiu sp,sp,200
00000140 <main>:
140: 3c1c0000 lui gp,0x0 ; |
144: 279c0000 addiu gp,gp,0 ; |
148: 0399e021 addu gp,gp,t9 ; |
14c: 27bdff58 addiu sp,sp,-168 ; | prolog
150: afbf00a4 sw ra,164(sp) ; |
154: afbe00a0 sw s8,160(sp) ; |
158: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
15c: afbc0058 sw gp,88(sp) ; /
160: 8f820000 lw v0,0(gp) ; \ |
164: 24420030 addiu v0,v0,48 ; | | field j -> v0
168: 8c420000 lw v0,0(v0) ; | /
16c: 8f830000 lw v1,0(gp) ; | prep (first) local struct A data ... \
170: 24630030 addiu v1,v1,48 ; | | field j -> v1
174: 8c630004 lw v1,4(v1) ; | /
178: 8f840000 lw a0,0(gp) ; | \
17c: 24840030 addiu a0,a0,48 ; | | field f -> a0
180: 8c840008 lw a0,8(a0) ; / |
184: afc20090 sw v0,144(s8) ; \
188: afc30094 sw v1,148(s8) ; | ... and write to local area
18c: afc40098 sw a0,152(s8) ; /
190: 8f820000 lw v0,0(gp) ; \ |
194: 24420020 addiu v0,v0,32 ; | |
198: 8c420000 lw v0,0(v0) ; | |
19c: 8f830000 lw v1,0(gp) ; | | field d -> v0 & v1
1a0: 24630020 addiu v1,v1,32 ; | |
1a4: 8c630004 lw v1,4(v1) ; | prep (first) local struct B data ... /
1a8: 8f840000 lw a0,0(gp) ; | \
1ac: 24840020 addiu a0,a0,32 ; | |
1b0: 8c840008 lw a0,8(a0) ; | |
1b4: 8f850000 lw a1,0(gp) ; | | field l -> a0 & a1
1b8: 24a50020 addiu a1,a1,32 ; | |
1bc: 8ca5000c lw a1,12(a1) ; / |
1c0: afc20080 sw v0,128(s8) ; \
1c4: afc30084 sw v1,132(s8) ; |
1c8: afc40088 sw a0,136(s8) ; | ... and write to local area
1cc: afc5008c sw a1,140(s8) ; /
1d0: 8f820000 lw v0,0(gp) ; \ |
1d4: 24420010 addiu v0,v0,16 ; | | field j -> v0
1d8: 8c420000 lw v0,0(v0) ; | /
1dc: 8f830000 lw v1,0(gp) ; | prep (second) local struct A data ... \
1e0: 24630010 addiu v1,v1,16 ; | | field j -> v1
1e4: 8c630004 lw v1,4(v1) ; | /
1e8: 8f840000 lw a0,0(gp) ; | \
1ec: 24840010 addiu a0,a0,16 ; | | field f -> a0
1f0: 8c840008 lw a0,8(a0) ; / |
1f4: afc20070 sw v0,112(s8) ; \
1f8: afc30074 sw v1,116(s8) ; | ... and write to local area
1fc: afc40078 sw a0,120(s8) ; /
200: 8f820000 lw v0,0(gp) ; \ |
204: 24420000 addiu v0,v0,0 ; | |
208: 8c420000 lw v0,0(v0) ; | |
20c: 8f830000 lw v1,0(gp) ; | | field d -> v0 & v1
210: 24630000 addiu v1,v1,0 ; | |
214: 8c630004 lw v1,4(v1) ; | prep (second) local struct B data ... /
218: 8f840000 lw a0,0(gp) ; | \
21c: 24840000 addiu a0,a0,0 ; | |
220: 8c840008 lw a0,8(a0) ; | |
224: 8f850000 lw a1,0(gp) ; | | field l -> a0 & a1
228: 24a50000 addiu a1,a1,0 ; | |
22c: 8ca5000c lw a1,12(a1) ; / |
230: afc20060 sw v0,96(s8) ; \
234: afc30064 sw v1,100(s8) ; |
238: afc40068 sw a0,104(s8) ; | ... and write to local area
23c: afc5006c sw a1,108(s8) ; /
240: 8fc20080 lw v0,128(s8) ; \
244: 8fc30084 lw v1,132(s8) ; |
248: 8fc40088 lw a0,136(s8) ; |
24c: 8fc5008c lw a1,140(s8) ; |
250: afa20018 sw v0,24(sp) ; | | d
254: afa3001c sw v1,28(sp) ; | arg 3 (first struct B) /
258: afa40020 sw a0,32(sp) ; | \
25c: afa50024 sw a1,36(sp) ; / | l
260: 24020007 li v0,7 ; \
264: afa20028 sw v0,40(sp) ; / arg 4
268: 24020008 li v0,8 ; \
26c: afa2002c sw v0,44(sp) ; / arg 5
270: 8fc20070 lw v0,112(s8) ; \
274: 8fc30074 lw v1,116(s8) ; |
278: 8fc40078 lw a0,120(s8) ; | arg 6 (second struct A, note that 60(sp) isn't used, so sizeof(struct A) is probably a padded 16)
27c: afa20030 sw v0,48(sp) ; | i
280: afa30034 sw v1,52(sp) ; | j
284: afa40038 sw a0,56(sp) ; / f
288: 8fc20060 lw v0,96(s8) ; \
28c: 8fc30064 lw v1,100(s8) ; |
290: 8fc40068 lw a0,104(s8) ; |
294: 8fc5006c lw a1,108(s8) ; |
298: afa20040 sw v0,64(sp) ; | | d
29c: afa30044 sw v1,68(sp) ; | arg 7 (second struct B) /
2a0: afa40048 sw a0,72(sp) ; | \
2a4: afa5004c sw a1,76(sp) ; | | l
2a8: 2402000e li v0,14 ; arg 8 pushed ...
2ac: afa20050 sw v0,80(sp) ; ... onto stack
2b0: 2402000f li v0,15 ; arg 9 pushed ...
2b4: afa20054 sw v0,84(sp) ; ... onto stack
2b8: 8fc20098 lw v0,152(s8) ; | | f (via stack, first slot after save area)
2bc: afa20010 sw v0,16(sp) ; | | note that 20(sp) isn't used, so sizeof(struct A) is probably a padded 16
2c0: 8fc60090 lw a2,144(s8) ; | arg 2 (first struct A) i (via reg)
2c4: 8fc70094 lw a3,148(s8) ; | j (via reg)
2c8: 00002021 move a0,zero ; arg 0
2cc: 24050001 li a1,1 ; arg 1
2d0: 8f990000 lw t9,0(gp) ; func to call -> t9
2d4: 0320f809 jalr t9 ; call and ret addr -> ra
2d8: 00000000 nop ; branch delay slot
2dc: 8fdc0058 lw gp,88(s8) ; |
2e0: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
2e4: 03c0e821 move sp,s8 ; |
2e8: 8fbf00a4 lw ra,164(sp) ; | epilog
2ec: 8fbe00a0 lw s8,160(sp) ; |
2f0: 03e00008 jr ra ; |
2f4: 27bd00a8 addiu sp,sp,168 ; |
...
; ---------- returning structs by value ---------->
;
; struct Small { char x; };
; struct Big { long long i,j,k,l; long m; }; /* bigger than 16b */
;
; struct Small f0()
; {
; struct Small s = { 132 };
; return s;
; }
;
; struct Big f1()
; {
; struct Big b = { 7171LL, 99LL, -99LL, -3102LL, 32 };
; return b;
; }
;
; int main()
; {
; struct Small s = f0();
; struct Big b = f1();
; return b.j + b.k + b.m + s.x;
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <f0>:
0: 3c1c0000 lui gp,0x0 ; |
4: 279c0000 addiu gp,gp,0 ; |
8: 0399e021 addu gp,gp,t9 ; | prolog
c: 27bdffe8 addiu sp,sp,-24 ; |
10: afbe0010 sw s8,16(sp) ; |
14: 03a0f021 move s8,sp ; |
18: 00801021 move v0,a0 ; hidden first arg (ptr to struct ret) -> v0
1c: 2403ff84 li v1,-124 ; | put together local struct
20: a3c30008 sb v1,8(s8) ; /
24: 93c30008 lbu v1,8(s8) ; read struct data from local area ...
28: a0430000 sb v1,0(v0) ; ... and write to return value area
2c: 03c0e821 move sp,s8 ; \
30: 8fbe0010 lw s8,16(sp) ; |
34: 03e00008 jr ra ; | epilog
38: 27bd0018 addiu sp,sp,24 ; |
0000003c <f1>:
3c: 3c1c0000 lui gp,0x0 ; |
40: 279c0000 addiu gp,gp,0 ; |
44: 0399e021 addu gp,gp,t9 ; |
48: 27bdffb0 addiu sp,sp,-80 ; |
4c: afbf0048 sw ra,72(sp) ; | prolog
50: afbe0044 sw s8,68(sp) ; |
54: afb00040 sw s0,64(sp) ; |
58: 03a0f021 move s8,sp ; |
5c: afbc0010 sw gp,16(sp) ; |
60: 00808021 move s0,a0 ; hidden first arg (ptr to struct ret) -> s0
64: 27c20018 addiu v0,s8,24 ;
68: 8f830000 lw v1,0(gp) ;
6c: 24630000 addiu v1,v1,0 ;
70: 24060028 li a2,40 ;
74: 00402021 move a0,v0 ;
78: 00602821 move a1,v1 ;
7c: 8f990000 lw t9,0(gp) ;
80: 0320f809 jalr t9 ;
84: 00000000 nop ; @@@ unsure why those two jumps, but seems to put return value data together
88: 8fdc0010 lw gp,16(s8) ;
8c: 02001021 move v0,s0 ;
90: 27c30018 addiu v1,s8,24 ;
94: 24060028 li a2,40 ;
98: 00402021 move a0,v0 ;
9c: 00602821 move a1,v1 ;
a0: 8f990000 lw t9,0(gp) ;
a4: 0320f809 jalr t9 ;
a8: 00000000 nop ;
ac: 8fdc0010 lw gp,16(s8) ; |
b0: 02001021 move v0,s0 ; : return value (hidden ptr): not part of epilog, but unordered (branch delay slot style)
b4: 03c0e821 move sp,s8 ; |
b8: 8fbf0048 lw ra,72(sp) ; |
bc: 8fbe0044 lw s8,68(sp) ; | epilog
c0: 8fb00040 lw s0,64(sp) ; |
c4: 03e00008 jr ra ; |
c8: 27bd0050 addiu sp,sp,80 ; |
000000cc <main>:
cc: 3c1c0000 lui gp,0x0 ; |
d0: 279c0000 addiu gp,gp,0 ; |
d4: 0399e021 addu gp,gp,t9 ; |
d8: 27bdffb0 addiu sp,sp,-80 ; |
dc: afbf004c sw ra,76(sp) ; | prolog
e0: afbe0048 sw s8,72(sp) ; |
e4: 03a0f021 move s8,sp ; |
e8: afbc0010 sw gp,16(sp) ; /
ec: 27c20018 addiu v0,s8,24 ; \
f0: 00402021 move a0,v0 ; | hidden first arg (ptr to space for ret val)
f4: 8f990000 lw t9,0(gp) ; func to call (f0) -> t9
f8: 0320f809 jalr t9 ; call and ret addr -> ra
fc: 00000000 nop ; branch delay slot
100: 8fdc0010 lw gp,16(s8) ; restore gp @@@ unsure why?
104: 27c20020 addiu v0,s8,32 ; |
108: 00402021 move a0,v0 ; | hidden first arg (ptr to space for ret val)
10c: 8f990000 lw t9,0(gp) ; func to call (f1) -> t9
110: 0320f809 jalr t9 ; call and ret addr -> ra
114: 00000000 nop ; branch delay slot
118: 8fdc0010 lw gp,16(s8) ; restore gp @@@ unsure why?
11c: 8fc3002c lw v1,44(s8) ; | |
120: 8fc20028 lw v0,40(s8) ; | | b.j -> v0 & v1
124: 00602021 move a0,v1 ; | a0 = (int)b.j
128: 8fc30034 lw v1,52(s8) ; | |
12c: 8fc20030 lw v0,48(s8) ; | | b.j -> v0 & v1
130: 00601021 move v0,v1 ; | return value v0 = (int)b.k
134: 00821821 addu v1,a0,v0 ; | (int)b.j + (int)b.k -> v1
138: 8fc20040 lw v0,64(s8) ; | b.m -> v0
13c: 00621821 addu v1,v1,v0 ; | ((int)b.j + (int)b.k) + b.m -> v1
140: 83c20018 lb v0,24(s8) ; | s.x -> v0
144: 00621021 addu v0,v1,v0 ; / (((int)b.j + (int)b.k) + b.m) + s.x -> v0
148: 03c0e821 move sp,s8 ; \
14c: 8fbf004c lw ra,76(sp) ; |
150: 8fbe0048 lw s8,72(sp) ; | epilog
154: 03e00008 jr ra ; |
158: 27bd0050 addiu sp,sp,80 ; |
15c: 00000000 nop ; |
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <f0>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdffe8 addiu sp,sp,-24
10: afbe0010 sw s8,16(sp)
14: 03a0f021 move s8,sp
18: 00801021 move v0,a0
1c: 2403ff84 li v1,-124
20: a3c30008 sb v1,8(s8)
24: 93c30008 lbu v1,8(s8)
28: a0430000 sb v1,0(v0)
2c: 03c0e821 move sp,s8
30: 8fbe0010 lw s8,16(sp)
34: 03e00008 jr ra
38: 27bd0018 addiu sp,sp,24
0000003c <f1>:
3c: 3c1c0000 lui gp,0x0
40: 279c0000 addiu gp,gp,0
44: 0399e021 addu gp,gp,t9
48: 27bdffb0 addiu sp,sp,-80
4c: afbf0048 sw ra,72(sp)
50: afbe0044 sw s8,68(sp)
54: afb00040 sw s0,64(sp)
58: 03a0f021 move s8,sp
5c: afbc0010 sw gp,16(sp)
60: 00808021 move s0,a0
64: 27c20018 addiu v0,s8,24
68: 8f830000 lw v1,0(gp)
6c: 24630000 addiu v1,v1,0
70: 24060028 li a2,40
74: 00402021 move a0,v0
78: 00602821 move a1,v1
7c: 8f990000 lw t9,0(gp)
80: 0320f809 jalr t9
84: 00000000 nop
88: 8fdc0010 lw gp,16(s8)
8c: 02001021 move v0,s0
90: 27c30018 addiu v1,s8,24
94: 24060028 li a2,40
98: 00402021 move a0,v0
9c: 00602821 move a1,v1
a0: 8f990000 lw t9,0(gp)
a4: 0320f809 jalr t9
a8: 00000000 nop
ac: 8fdc0010 lw gp,16(s8)
b0: 02001021 move v0,s0
b4: 03c0e821 move sp,s8
b8: 8fbf0048 lw ra,72(sp)
bc: 8fbe0044 lw s8,68(sp)
c0: 8fb00040 lw s0,64(sp)
c4: 03e00008 jr ra
c8: 27bd0050 addiu sp,sp,80
000000cc <main>:
cc: 3c1c0000 lui gp,0x0
d0: 279c0000 addiu gp,gp,0
d4: 0399e021 addu gp,gp,t9
d8: 27bdffb0 addiu sp,sp,-80
dc: afbf004c sw ra,76(sp)
e0: afbe0048 sw s8,72(sp)
e4: 03a0f021 move s8,sp
e8: afbc0010 sw gp,16(sp)
ec: 27c20018 addiu v0,s8,24
f0: 00402021 move a0,v0
f4: 8f990000 lw t9,0(gp)
f8: 0320f809 jalr t9
fc: 00000000 nop
100: 8fdc0010 lw gp,16(s8)
104: 27c20020 addiu v0,s8,32
108: 00402021 move a0,v0
10c: 8f990000 lw t9,0(gp)
110: 0320f809 jalr t9
114: 00000000 nop
118: 8fdc0010 lw gp,16(s8)
11c: 8fc3002c lw v1,44(s8)
120: 8fc20028 lw v0,40(s8)
124: 00602021 move a0,v1
128: 8fc30034 lw v1,52(s8)
12c: 8fc20030 lw v0,48(s8)
130: 00601021 move v0,v1
134: 00821821 addu v1,a0,v0
138: 8fc20040 lw v0,64(s8)
13c: 00621821 addu v1,v1,v0
140: 83c20018 lb v0,24(s8)
144: 00621021 addu v0,v1,v0
148: 03c0e821 move sp,s8
14c: 8fbf004c lw ra,76(sp)
150: 8fbe0048 lw s8,72(sp)
154: 03e00008 jr ra
158: 27bd0050 addiu sp,sp,80
15c: 00000000 nop
; ---------- returning long long ---------->
;
; long long f()
; {
; return 7171LL;
; }
;
; int main()
; {
; return (int)f();
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <f>:
0: 3c1c0000 lui gp,0x0 ;
4: 279c0000 addiu gp,gp,0 ;
8: 0399e021 addu gp,gp,t9 ;
c: 27bdfff8 addiu sp,sp,-8 ;
10: afbe0000 sw s8,0(sp) ;
14: 03a0f021 move s8,sp ;
18: 24031c03 li v1,7171 ; | return value
1c: 00001021 move v0,zero ; |
20: 03c0e821 move sp,s8 ;
24: 8fbe0000 lw s8,0(sp) ;
28: 03e00008 jr ra ;
2c: 27bd0008 addiu sp,sp,8 ;
00000030 <main>:
30: 3c1c0000 lui gp,0x0
34: 279c0000 addiu gp,gp,0
38: 0399e021 addu gp,gp,t9
3c: 27bdffe0 addiu sp,sp,-32
40: afbf001c sw ra,28(sp)
44: afbe0018 sw s8,24(sp)
48: 03a0f021 move s8,sp
4c: afbc0010 sw gp,16(sp)
50: 8f990000 lw t9,0(gp)
54: 0320f809 jalr t9
58: 00000000 nop
5c: 8fdc0010 lw gp,16(s8)
60: 00601021 move v0,v1
64: 03c0e821 move sp,s8
68: 8fbf001c lw ra,28(sp)
6c: 8fbe0018 lw s8,24(sp)
70: 03e00008 jr ra
74: 27bd0020 addiu sp,sp,32
...
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <f>:
0: 3c1c0000 lui gp,0x0 ;
4: 279c0000 addiu gp,gp,0 ;
8: 0399e021 addu gp,gp,t9 ;
c: 27bdfff8 addiu sp,sp,-8 ;
10: afbe0000 sw s8,0(sp) ;
14: 03a0f021 move s8,sp ;
18: 24031c03 li v1,7171 ; | return value
1c: 00001021 move v0,zero ; |
20: 03c0e821 move sp,s8 ;
24: 8fbe0000 lw s8,0(sp) ;
28: 03e00008 jr ra ;
2c: 27bd0008 addiu sp,sp,8 ;
00000030 <main>:
30: 3c1c0000 lui gp,0x0
34: 279c0000 addiu gp,gp,0
38: 0399e021 addu gp,gp,t9
3c: 27bdffe0 addiu sp,sp,-32
40: afbf001c sw ra,28(sp)
44: afbe0018 sw s8,24(sp)
48: 03a0f021 move s8,sp
4c: afbc0010 sw gp,16(sp)
50: 8f990000 lw t9,0(gp)
54: 0320f809 jalr t9
58: 00000000 nop
5c: 8fdc0010 lw gp,16(s8)
60: 00601021 move v0,v1
64: 03c0e821 move sp,s8
68: 8fbf001c lw ra,28(sp)
6c: 8fbe0018 lw s8,24(sp)
70: 03e00008 jr ra
74: 27bd0020 addiu sp,sp,32
...
; ---------- passing structs with only fp parts ---------->
;
; struct A { float a; };
; struct B { float a, b; };
; struct C { float a, b, c; };
; struct D { double a; };
; struct E { double a, b; };
; struct F { double a, b, c; };
;
; void leaf_call(struct A a, struct B b, struct C c, struct D d, struct E e, struct F f)
; {
; }
;
; int main()
; {
; leaf_call((struct A){1.f}, (struct B){2.f,3.f}, (struct C){4.f,5.f,6.f}, (struct D){1.}, (struct E){2.,3.}, (struct F){4.,5.,6.});
; return 0;
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <main>:
38: 3c1c0000 lui gp,0x0 ; |
3c: 279c0000 addiu gp,gp,0 ; |
40: 0399e021 addu gp,gp,t9 ; |
44: 27bdff60 addiu sp,sp,-160 ; | prolog
48: afbf009c sw ra,156(sp) ; |
4c: afbe0098 sw s8,152(sp) ; |
50: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
54: afbc0048 sw gp,72(sp) ; /
58: 8f820000 lw v0,0(gp) ; \
5c: 24420044 addiu v0,v0,68 ; | prep local struct A data ...
60: 8c420000 lw v0,0(v0) ; /
64: afc20094 sw v0,148(s8) ; ... and write to local area
68: 8f820000 lw v0,0(gp) ; \
6c: 2442003c addiu v0,v0,60 ; |
70: 8c420000 lw v0,0(v0) ; |
74: 8f830000 lw v1,0(gp) ; | prep local struct B data ...
78: 2463003c addiu v1,v1,60 ; |
7c: 8c630004 lw v1,4(v1) ; /
80: afc2008c sw v0,140(s8) ; \ ... and write to local area a
84: afc30090 sw v1,144(s8) ; / b
88: 8f820000 lw v0,0(gp) ; \
8c: 24420030 addiu v0,v0,48 ; |
90: 8c420000 lw v0,0(v0) ; |
94: 8f830000 lw v1,0(gp) ; |
98: 24630030 addiu v1,v1,48 ; | prep local struct C data ...
9c: 8c630004 lw v1,4(v1) ; |
a0: 8f840000 lw a0,0(gp) ; |
a4: 24840030 addiu a0,a0,48 ; |
a8: 8c840008 lw a0,8(a0) ; /
ac: afc20080 sw v0,128(s8) ; \ a
b0: afc30084 sw v1,132(s8) ; | ... and write to local area b
b4: afc40088 sw a0,136(s8) ; / c
b8: 8f830000 lw v1,0(gp) ; \
bc: 24630028 addiu v1,v1,40 ; |
c0: 8c630004 lw v1,4(v1) ; |
c4: 8f820000 lw v0,0(gp) ; | prep local struct D data ...
c8: 24420028 addiu v0,v0,40 ; |
cc: 8c420000 lw v0,0(v0) ; /
d0: afc3007c sw v1,124(s8) ; \ ... and write to local area
d4: afc20078 sw v0,120(s8) ; /
d8: 8f820000 lw v0,0(gp) ; \
dc: 24420018 addiu v0,v0,24 ; |
e0: 8c420000 lw v0,0(v0) ; |
e4: 8f830000 lw v1,0(gp) ; |
e8: 24630018 addiu v1,v1,24 ; |
ec: 8c630004 lw v1,4(v1) ; | prep local struct E data ...
f0: 8f840000 lw a0,0(gp) ; |
f4: 24840018 addiu a0,a0,24 ; |
f8: 8c840008 lw a0,8(a0) ; |
fc: 8f850000 lw a1,0(gp) ; |
100: 24a50018 addiu a1,a1,24 ; |
104: 8ca5000c lw a1,12(a1) ; /
108: afc20068 sw v0,104(s8) ; \ | a
10c: afc3006c sw v1,108(s8) ; | ... and write to local area /
110: afc40070 sw a0,112(s8) ; | \
114: afc50074 sw a1,116(s8) ; / | b
118: 8f820000 lw v0,0(gp) ; \
11c: 24420000 addiu v0,v0,0 ; |
120: 8c420000 lw v0,0(v0) ; |
124: 8f830000 lw v1,0(gp) ; |
128: 24630000 addiu v1,v1,0 ; |
12c: 8c630004 lw v1,4(v1) ; |
130: 8f840000 lw a0,0(gp) ; |
134: 24840000 addiu a0,a0,0 ; |
138: 8c840008 lw a0,8(a0) ; |
13c: 8f850000 lw a1,0(gp) ; | prep local struct F data ...
140: 24a50000 addiu a1,a1,0 ; |
144: 8ca5000c lw a1,12(a1) ; |
148: 8f860000 lw a2,0(gp) ; |
14c: 24c60000 addiu a2,a2,0 ; |
150: 8cc60010 lw a2,16(a2) ; |
154: 8f870000 lw a3,0(gp) ; |
158: 24e70000 addiu a3,a3,0 ; |
15c: 8ce70014 lw a3,20(a3) ; /
160: afc20050 sw v0,80(s8) ; \ | a
164: afc30054 sw v1,84(s8) ; | /
168: afc40058 sw a0,88(s8) ; | \ b
16c: afc5005c sw a1,92(s8) ; | ... and write to local area /
170: afc60060 sw a2,96(s8) ; | \
174: afc70064 sw a3,100(s8) ; / | c
178: 8fc3007c lw v1,124(s8) ; \
17c: 8fc20078 lw v0,120(s8) ; |
180: afa3001c sw v1,28(sp) ; | arg 3 (struct D)
184: afa20018 sw v0,24(sp) ; /
188: 8fc20068 lw v0,104(s8) ; \
18c: 8fc3006c lw v1,108(s8) ; |
190: 8fc40070 lw a0,112(s8) ; |
194: 8fc50074 lw a1,116(s8) ; |
198: afa20020 sw v0,32(sp) ; | arg 4 (struct E)
19c: afa30024 sw v1,36(sp) ; |
1a0: afa40028 sw a0,40(sp) ; |
1a4: afa5002c sw a1,44(sp) ; /
1a8: 8fc20050 lw v0,80(s8) ; \
1ac: 8fc30054 lw v1,84(s8) ; |
1b0: 8fc40058 lw a0,88(s8) ; |
1b4: 8fc5005c lw a1,92(s8) ; |
1b8: 8fc60060 lw a2,96(s8) ; |
1bc: 8fc70064 lw a3,100(s8) ; |
1c0: afa20030 sw v0,48(sp) ; | arg 5 (struct F)
1c4: afa30034 sw v1,52(sp) ; |
1c8: afa40038 sw a0,56(sp) ; |
1cc: afa5003c sw a1,60(sp) ; |
1d0: afa60040 sw a2,64(sp) ; |
1d4: afa70044 sw a3,68(sp) ; /
1d8: 8fc20084 lw v0,132(s8) ; \
1dc: 8fc30088 lw v1,136(s8) ; |
1e0: afa20010 sw v0,16(sp) ; | arg 2 (struct C) b (via stack)
1e4: afa30014 sw v1,20(sp) ; | c (via stack)
1e8: 8fc70080 lw a3,128(s8) ; | a (via reg)
1ec: 8fc40094 lw a0,148(s8) ; arg 0 (struct A, via reg)
1f0: 8fc5008c lw a1,140(s8) ; | arg 1 (struct B, via regs) a
1f4: 8fc60090 lw a2,144(s8) ; | b
1f8: 8f990000 lw t9,0(gp) ; func to call -> t9
1fc: 0320f809 jalr t9 ; call and ret addr -> ra
200: 00000000 nop ; branch delay slot
204: 8fdc0048 lw gp,72(s8) ; |
208: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
20c: 03c0e821 move sp,s8 ; |
210: 8fbf009c lw ra,156(sp) ; | epilog
214: 8fbe0098 lw s8,152(sp) ; |
218: 03e00008 jr ra ; |
21c: 27bd00a0 addiu sp,sp,160 ; |
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <main>:
38: 3c1c0000 lui gp,0x0 ; |
3c: 279c0000 addiu gp,gp,0 ; |
40: 0399e021 addu gp,gp,t9 ; |
44: 27bdff60 addiu sp,sp,-160 ; | prolog
48: afbf009c sw ra,156(sp) ; |
4c: afbe0098 sw s8,152(sp) ; |
50: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
54: afbc0048 sw gp,72(sp) ; /
58: 8f810000 lw at,0(gp) ; \
5c: 24210044 addiu at,at,68 ; | prep local struct A (single float field) data ...
60: c4200000 lwc1 $f0,0(at) ; /
64: e7c00094 swc1 $f0,148(s8) ; ... and write to local area
68: 8f820000 lw v0,0(gp) ; \
6c: 2442003c addiu v0,v0,60 ; |
70: 8c420000 lw v0,0(v0) ; |
74: 8f830000 lw v1,0(gp) ; | prep local struct B data ...
78: 2463003c addiu v1,v1,60 ; |
7c: 8c630004 lw v1,4(v1) ; /
80: afc2008c sw v0,140(s8) ; \ ... and write to local area a
84: afc30090 sw v1,144(s8) ; / b
88: 8f820000 lw v0,0(gp) ; \
8c: 24420030 addiu v0,v0,48 ; |
90: 8c420000 lw v0,0(v0) ; |
94: 8f830000 lw v1,0(gp) ; |
98: 24630030 addiu v1,v1,48 ; | prep local struct C data ...
9c: 8c630004 lw v1,4(v1) ; |
a0: 8f840000 lw a0,0(gp) ; |
a4: 24840030 addiu a0,a0,48 ; |
a8: 8c840008 lw a0,8(a0) ; /
ac: afc20080 sw v0,128(s8) ; \ a
b0: afc30084 sw v1,132(s8) ; | ... and write to local area b
b4: afc40088 sw a0,136(s8) ; / c
b8: 8f810000 lw at,0(gp) ; \
bc: 24210028 addiu at,at,40 ; | prep local struct D (single double field) data ...
c0: d4200000 ldc1 $f0,0(at) ; /
c4: f7c00078 sdc1 $f0,120(s8) ; ... and write to local area
c8: 8f820000 lw v0,0(gp) ; \
cc: 24420018 addiu v0,v0,24 ; |
d0: 8c420000 lw v0,0(v0) ; |
d4: 8f830000 lw v1,0(gp) ; |
d8: 24630018 addiu v1,v1,24 ; |
dc: 8c630004 lw v1,4(v1) ; | prep local struct E data ...
e0: 8f840000 lw a0,0(gp) ; |
e4: 24840018 addiu a0,a0,24 ; |
e8: 8c840008 lw a0,8(a0) ; |
ec: 8f850000 lw a1,0(gp) ; |
f0: 24a50018 addiu a1,a1,24 ; |
f4: 8ca5000c lw a1,12(a1) ; /
f8: afc20068 sw v0,104(s8) ; \ | a
fc: afc3006c sw v1,108(s8) ; | ... and write to local area /
100: afc40070 sw a0,112(s8) ; | \
104: afc50074 sw a1,116(s8) ; / | b
108: 8f820000 lw v0,0(gp) ; \
10c: 24420000 addiu v0,v0,0 ; |
110: 8c420000 lw v0,0(v0) ; |
114: 8f830000 lw v1,0(gp) ; |
118: 24630000 addiu v1,v1,0 ; |
11c: 8c630004 lw v1,4(v1) ; |
120: 8f840000 lw a0,0(gp) ; |
124: 24840000 addiu a0,a0,0 ; |
128: 8c840008 lw a0,8(a0) ; |
12c: 8f850000 lw a1,0(gp) ; | prep local struct F data ...
130: 24a50000 addiu a1,a1,0 ; |
134: 8ca5000c lw a1,12(a1) ; |
138: 8f860000 lw a2,0(gp) ; |
13c: 24c60000 addiu a2,a2,0 ; |
140: 8cc60010 lw a2,16(a2) ; |
144: 8f870000 lw a3,0(gp) ; |
148: 24e70000 addiu a3,a3,0 ; |
14c: 8ce70014 lw a3,20(a3) ; /
150: afc20050 sw v0,80(s8) ; \ | a
154: afc30054 sw v1,84(s8) ; | /
158: afc40058 sw a0,88(s8) ; | \ b
15c: afc5005c sw a1,92(s8) ; | ... and write to local area /
160: afc60060 sw a2,96(s8) ; | \
164: afc70064 sw a3,100(s8) ; / | c
168: d7c00078 ldc1 $f0,120(s8) ; \
16c: f7a00018 sdc1 $f0,24(sp) ; / arg 3 (struct D)
170: 8fc20068 lw v0,104(s8) ; \
174: 8fc3006c lw v1,108(s8) ; |
178: 8fc40070 lw a0,112(s8) ; |
17c: 8fc50074 lw a1,116(s8) ; |
180: afa20020 sw v0,32(sp) ; | arg 4 (struct E)
184: afa30024 sw v1,36(sp) ; |
188: afa40028 sw a0,40(sp) ; |
18c: afa5002c sw a1,44(sp) ; /
190: 8fc20050 lw v0,80(s8) ; \
194: 8fc30054 lw v1,84(s8) ; |
198: 8fc40058 lw a0,88(s8) ; |
19c: 8fc5005c lw a1,92(s8) ; |
1a0: 8fc60060 lw a2,96(s8) ; |
1a4: 8fc70064 lw a3,100(s8) ; |
1a8: afa20030 sw v0,48(sp) ; | arg 5 (struct F)
1ac: afa30034 sw v1,52(sp) ; |
1b0: afa40038 sw a0,56(sp) ; |
1b4: afa5003c sw a1,60(sp) ; |
1b8: afa60040 sw a2,64(sp) ; |
1bc: afa70044 sw a3,68(sp) ; /
1c0: 8fc20084 lw v0,132(s8) ; \
1c4: 8fc30088 lw v1,136(s8) ; |
1c8: afa20010 sw v0,16(sp) ; | arg 2 (struct C) b (via stack)
1cc: afa30014 sw v1,20(sp) ; | c (via stack)
1d0: 8fc70080 lw a3,128(s8) ; | a (via reg)
1d4: 8fc40094 lw a0,148(s8) ; arg 0 (struct A, via reg)
1d8: 8fc5008c lw a1,140(s8) ; | arg 1 (struct B, via regs) a
1dc: 8fc60090 lw a2,144(s8) ; | b
1e0: 8f990000 lw t9,0(gp) ; func to call -> t9
1e4: 0320f809 jalr t9 ; call and ret addr -> ra
1e8: 00000000 nop ; branch delay slot
1ec: 8fdc0048 lw gp,72(s8) ; |
1f0: 00001021 move v0,zero ; : return value: not part of epilog, but unordered (branch delay slot style)
1f4: 03c0e821 move sp,s8 ; |
1f8: 8fbf009c lw ra,156(sp) ; | epilog
1fc: 8fbe0098 lw s8,152(sp) ; |
200: 03e00008 jr ra ; |
204: 27bd00a0 addiu sp,sp,160 ; |
...
; ---------- single-field structs by values (and small array fields) ---------->
;
; struct C { char c; };
; struct S { short s; };
; struct I { int i; };
; struct F { float f; };
; struct D { double d; };
;
; struct C2 { char c[2]; };
; struct C3 { char c[3]; };
;
; void leaf_call(struct C2 a, struct C b, struct S c, struct I d, struct F e, struct D f, struct C3 g)
; {
; }
;
; int main()
; {
; leaf_call((struct C2){{0,1}}, (struct C){2}, (struct S){3}, (struct I){4}, (struct F){5.f}, (struct D){6.}, (struct C3){{7,8,9}});
; return 0;
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <main>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdffa0 addiu sp,sp,-96
48: afbf005c sw ra,92(sp)
4c: afbe0058 sw s8,88(sp)
50: 03a0f021 move s8,sp
54: afbc0028 sw gp,40(sp)
58: 8f820000 lw v0,0(gp)
5c: 24420010 addiu v0,v0,16
60: 90420000 lbu v0,0(v0)
64: a3c2004b sb v0,75(s8)
68: 8f820000 lw v0,0(gp)
6c: 24420010 addiu v0,v0,16
70: 90420001 lbu v0,1(v0)
74: a3c2004c sb v0,76(s8)
78: 24020002 li v0,2
7c: a3c2004a sb v0,74(s8)
80: 24020003 li v0,3
84: a7c20048 sh v0,72(s8)
88: 24020004 li v0,4
8c: afc20044 sw v0,68(s8)
90: 8f820000 lw v0,0(gp)
94: 24420014 addiu v0,v0,20
98: 8c420000 lw v0,0(v0)
9c: afc20040 sw v0,64(s8)
a0: 8f830000 lw v1,0(gp)
a4: 24630008 addiu v1,v1,8
a8: 8c630004 lw v1,4(v1)
ac: 8f820000 lw v0,0(gp)
b0: 24420008 addiu v0,v0,8
b4: 8c420000 lw v0,0(v0)
b8: afc3003c sw v1,60(s8)
bc: afc20038 sw v0,56(s8)
c0: 8f820000 lw v0,0(gp)
c4: 24420000 addiu v0,v0,0
c8: 94420000 lhu v0,0(v0)
cc: a7c20030 sh v0,48(s8)
d0: 8f820000 lw v0,0(gp)
d4: 24420000 addiu v0,v0,0
d8: 90420002 lbu v0,2(v0)
dc: a3c20032 sb v0,50(s8)
e0: 8fc20040 lw v0,64(s8)
e4: afa20010 sw v0,16(sp)
e8: 8fc3003c lw v1,60(s8)
ec: 8fc20038 lw v0,56(s8)
f0: afa3001c sw v1,28(sp)
f4: afa20018 sw v0,24(sp)
f8: 97c20030 lhu v0,48(s8)
fc: a7a20020 sh v0,32(sp)
100: 93c20032 lbu v0,50(s8)
104: a3a20022 sb v0,34(sp)
108: 93c2004b lbu v0,75(s8)
10c: 00021a00 sll v1,v0,0x8
110: 93c2004c lbu v0,76(s8)
114: 00431025 or v0,v0,v1
118: afc00050 sw zero,80(s8)
11c: 00021c00 sll v1,v0,0x10
120: 8fc40050 lw a0,80(s8)
124: 3082ffff andi v0,a0,0xffff
128: 00431025 or v0,v0,v1
12c: afc20050 sw v0,80(s8)
130: 8fc40050 lw a0,80(s8)
134: 93c5004a lbu a1,74(s8)
138: 00052e00 sll a1,a1,0x18
13c: 97c60048 lhu a2,72(s8)
140: 00063400 sll a2,a2,0x10
144: 8fc70044 lw a3,68(s8)
148: 8f990000 lw t9,0(gp)
14c: 0320f809 jalr t9
150: 00000000 nop
154: 8fdc0028 lw gp,40(s8)
158: 00001021 move v0,zero
15c: 03c0e821 move sp,s8
160: 8fbf005c lw ra,92(sp)
164: 8fbe0058 lw s8,88(sp)
168: 03e00008 jr ra
16c: 27bd0060 addiu sp,sp,96
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1 *and* -mhard-float ----->
00000000 <leaf_call>:
0: 3c1c0000 lui gp,0x0
4: 279c0000 addiu gp,gp,0
8: 0399e021 addu gp,gp,t9
c: 27bdfff8 addiu sp,sp,-8
10: afbe0000 sw s8,0(sp)
14: 03a0f021 move s8,sp
18: afc40008 sw a0,8(s8)
1c: afc5000c sw a1,12(s8)
20: afc60010 sw a2,16(s8)
24: afc70014 sw a3,20(s8)
28: 03c0e821 move sp,s8
2c: 8fbe0000 lw s8,0(sp)
30: 03e00008 jr ra
34: 27bd0008 addiu sp,sp,8
00000038 <main>:
38: 3c1c0000 lui gp,0x0
3c: 279c0000 addiu gp,gp,0
40: 0399e021 addu gp,gp,t9
44: 27bdffa0 addiu sp,sp,-96
48: afbf005c sw ra,92(sp)
4c: afbe0058 sw s8,88(sp)
50: 03a0f021 move s8,sp
54: afbc0028 sw gp,40(sp)
58: 8f820000 lw v0,0(gp)
5c: 24420010 addiu v0,v0,16
60: 90420000 lbu v0,0(v0)
64: a3c2004b sb v0,75(s8)
68: 8f820000 lw v0,0(gp)
6c: 24420010 addiu v0,v0,16
70: 90420001 lbu v0,1(v0)
74: a3c2004c sb v0,76(s8)
78: 24020002 li v0,2
7c: a3c2004a sb v0,74(s8)
80: 24020003 li v0,3
84: a7c20048 sh v0,72(s8)
88: 24020004 li v0,4
8c: afc20044 sw v0,68(s8)
90: 8f810000 lw at,0(gp)
94: 24210014 addiu at,at,20
98: c4200000 lwc1 $f0,0(at)
9c: e7c00040 swc1 $f0,64(s8)
a0: 8f810000 lw at,0(gp)
a4: 24210008 addiu at,at,8
a8: d4200000 ldc1 $f0,0(at)
ac: f7c00038 sdc1 $f0,56(s8)
b0: 8f820000 lw v0,0(gp)
b4: 24420000 addiu v0,v0,0
b8: 94420000 lhu v0,0(v0)
bc: a7c20030 sh v0,48(s8)
c0: 8f820000 lw v0,0(gp)
c4: 24420000 addiu v0,v0,0
c8: 90420002 lbu v0,2(v0)
cc: a3c20032 sb v0,50(s8)
d0: c7c00040 lwc1 $f0,64(s8)
d4: e7a00010 swc1 $f0,16(sp)
d8: d7c00038 ldc1 $f0,56(s8)
dc: f7a00018 sdc1 $f0,24(sp)
e0: 97c20030 lhu v0,48(s8)
e4: a7a20020 sh v0,32(sp)
e8: 93c20032 lbu v0,50(s8)
ec: a3a20022 sb v0,34(sp)
f0: 93c2004b lbu v0,75(s8)
f4: 00021a00 sll v1,v0,0x8
f8: 93c2004c lbu v0,76(s8)
fc: 00431025 or v0,v0,v1
100: afc00050 sw zero,80(s8)
104: 00021c00 sll v1,v0,0x10
108: 8fc40050 lw a0,80(s8)
10c: 3082ffff andi v0,a0,0xffff
110: 00431025 or v0,v0,v1
114: afc20050 sw v0,80(s8)
118: 8fc40050 lw a0,80(s8)
11c: 93c5004a lbu a1,74(s8)
120: 00052e00 sll a1,a1,0x18
124: 97c60048 lhu a2,72(s8)
128: 00063400 sll a2,a2,0x10
12c: 8fc70044 lw a3,68(s8)
130: 8f990000 lw t9,0(gp)
134: 0320f809 jalr t9
138: 00000000 nop
13c: 8fdc0028 lw gp,40(s8)
140: 00001021 move v0,zero
144: 03c0e821 move sp,s8
148: 8fbf005c lw ra,92(sp)
14c: 8fbe0058 lw s8,88(sp)
150: 03e00008 jr ra
154: 27bd0060 addiu sp,sp,96
...
; ---------- C++ trivial and non-trivial aggrs passed to C funcs ---------->
;
; struct Trivial { int a; };
; struct NonTrivial { int a; NonTrivial() : a(0) {} NonTrivial(const NonTrivial& rhs) : a(rhs.a) { } };
;
; extern "C" {
;
; void f1(struct Trivial s) { }
; void f2(struct NonTrivial s) { }
;
; void f()
; {
; struct Trivial t;
; struct NonTrivial n;
; int a=1;
; a += 123;
; f1(t);
; a -= 123;
; f2(n);
; a -= 12;
; }
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1
004008c0 <f1>:
4008c0: 3c1c0002 lui gp,0x2
4008c4: 279c8330 addiu gp,gp,-31952
4008c8: 0399e021 addu gp,gp,t9
4008cc: 27bdfff8 addiu sp,sp,-8
4008d0: afbe0000 sw s8,0(sp)
4008d4: 03a0f021 move s8,sp
4008d8: afc40008 sw a0,8(s8)
4008dc: 03c0e821 move sp,s8
4008e0: 8fbe0000 lw s8,0(sp)
4008e4: 03e00008 jr ra
4008e8: 27bd0008 addiu sp,sp,8
004008ec <f2>:
4008ec: 3c1c0002 lui gp,0x2
4008f0: 279c8304 addiu gp,gp,-31996
4008f4: 0399e021 addu gp,gp,t9
4008f8: 27bdfff8 addiu sp,sp,-8
4008fc: afbe0000 sw s8,0(sp)
400900: 03a0f021 move s8,sp
400904: afc40008 sw a0,8(s8)
400908: 03c0e821 move sp,s8
40090c: 8fbe0000 lw s8,0(sp)
400910: 03e00008 jr ra
400914: 27bd0008 addiu sp,sp,8
00400918 <f>:
400918: 3c1c0002 lui gp,0x2 ;
40091c: 279c82d8 addiu gp,gp,-32040 ;
400920: 0399e021 addu gp,gp,t9 ;
400924: 27bdffd0 addiu sp,sp,-48 ;
400928: afbf002c sw ra,44(sp) ;
40092c: afbe0028 sw s8,40(sp) ;
400930: 03a0f021 move s8,sp ;
400934: afbc0010 sw gp,16(sp) ;
400938: 27c20024 addiu v0,s8,36 ;
40093c: 00402021 move a0,v0 ;
400940: 8f998064 lw t9,-32668(gp) ; |
400944: 0320f809 jalr t9 ; | NonTrivial::NonTrivial() / ctor
400948: 00000000 nop ;
40094c: 8fdc0010 lw gp,16(s8) ;
400950: 24020001 li v0,1 ;
400954: afc20018 sw v0,24(s8) ;
400958: 8fc20018 lw v0,24(s8) ;
40095c: 2442007b addiu v0,v0,123 ;
400960: afc20018 sw v0,24(s8) ;
400964: 8fc40020 lw a0,32(s8) ;
400968: 8f998060 lw t9,-32672(gp) ; |
40096c: 0320f809 jalr t9 ; | call f1(struct Trivial)
400970: 00000000 nop ;
400974: 8fdc0010 lw gp,16(s8) ;
400978: 8fc20018 lw v0,24(s8) ;
40097c: 2442ff85 addiu v0,v0,-123 ;
400980: afc20018 sw v0,24(s8) ;
400984: 27c2001c addiu v0,s8,28 ;
400988: 27c30024 addiu v1,s8,36 ;
40098c: 00402021 move a0,v0 ; | ptr to dest of copy of n
400990: 00602821 move a1,v1 ; | ptr to n
400994: 8f998050 lw t9,-32688(gp) ; | copy n |
400998: 0320f809 jalr t9 ; | | NonTrivial::NonTrivial(const NonTrivial&) / copy ctor
40099c: 00000000 nop ;
4009a0: 8fdc0010 lw gp,16(s8) ;
4009a4: 27c2001c addiu v0,s8,28 ; get ptr to copy of n -> v0
4009a8: 00402021 move a0,v0 ; f2 arg 0 (ptr to copy of struct NonTrivial), via ptr as non-trivial
4009ac: 8f998058 lw t9,-32680(gp) ; |
4009b0: 0320f809 jalr t9 ; | call f2(struct NonTrivial)
4009b4: 00000000 nop ;
4009b8: 8fdc0010 lw gp,16(s8) ;
4009bc: 8fc20018 lw v0,24(s8) ;
4009c0: 2442fff4 addiu v0,v0,-12 ;
4009c4: afc20018 sw v0,24(s8) ;
4009c8: 03c0e821 move sp,s8 ;
4009cc: 8fbf002c lw ra,44(sp) ;
4009d0: 8fbe0028 lw s8,40(sp) ;
4009d4: 03e00008 jr ra ;
4009d8: 27bd0030 addiu sp,sp,48 ;
; ... snip, removed code of ctor and copy ctor ...
; ---------- C++ trivial and non-trivial aggrs as return values ---------->
;
; struct Trivial { int a; };
; struct NonTrivial { int a; NonTrivial() : a(0) {} NonTrivial(const NonTrivial& rhs) : a(rhs.a) { } };
;
; extern "C" {
; struct Trivial f1() { return Trivial(); }
; }
;
; struct NonTrivial f2() { return NonTrivial(); }
;
; extern "C" {
; void f()
; {
; int a=1;
; a += 123;
; struct Trivial t = f1();
; a -= 123;
; struct NonTrivial n = f2();
; a -= 12;
; }
; }
; output from freebsd-12.0_r333647-malta_mipsebhf w/ gcc 4.2.1
004008b0 <f1>:
4008b0: 3c1c0002 lui gp,0x2
4008b4: 279c8310 addiu gp,gp,-31984
4008b8: 0399e021 addu gp,gp,t9
4008bc: 27bdfff8 addiu sp,sp,-8
4008c0: afbe0000 sw s8,0(sp)
4008c4: 03a0f021 move s8,sp
4008c8: 00801021 move v0,a0 ; ptr to retval space -> v0
4008cc: ac400000 sw zero,0(v0) ; return val
4008d0: 03c0e821 move sp,s8
4008d4: 8fbe0000 lw s8,0(sp)
4008d8: 03e00008 jr ra
4008dc: 27bd0008 addiu sp,sp,8
004008e0 <_Z2f2v>:
4008e0: 3c1c0002 lui gp,0x2 ; |
4008e4: 279c82e0 addiu gp,gp,-32032 ; |
4008e8: 0399e021 addu gp,gp,t9 ; |
4008ec: 27bdffd8 addiu sp,sp,-40 ; | prolog
4008f0: afbf0020 sw ra,32(sp) ; |
4008f4: afbe001c sw s8,28(sp) ; |
4008f8: afb00018 sw s0,24(sp) ; |
4008fc: 03a0f021 move s8,sp ; | frame pointer (note: with offset to frame start, but static compared to sp)
400900: afbc0010 sw gp,16(sp) ;
400904: 00808021 move s0,a0 ;
400908: 02001021 move v0,s0 ;
40090c: 00402021 move a0,v0 ;
400910: 8f998060 lw t9,-32672(gp) ;
400914: 0320f809 jalr t9 ;
400918: 00000000 nop ;
40091c: 8fdc0010 lw gp,16(s8) ;
400920: 02001021 move v0,s0 ; ptr to retval space -> v0
400924: 03c0e821 move sp,s8 ; |
400928: 8fbf0020 lw ra,32(sp) ; |
40092c: 8fbe001c lw s8,28(sp) ; |
400930: 8fb00018 lw s0,24(sp) ; | epilog
400934: 03e00008 jr ra ; |
400938: 27bd0028 addiu sp,sp,40 ; |
0040093c <f>:
40093c: 3c1c0002 lui gp,0x2 ;
400940: 279c8284 addiu gp,gp,-32124 ;
400944: 0399e021 addu gp,gp,t9 ;
400948: 27bdffd0 addiu sp,sp,-48 ;
40094c: afbf002c sw ra,44(sp) ;
400950: afbe0028 sw s8,40(sp) ;
400954: 03a0f021 move s8,sp ;
400958: afbc0010 sw gp,16(sp) ;
40095c: 24020001 li v0,1 ;
400960: afc20018 sw v0,24(s8) ;
400964: 8fc20018 lw v0,24(s8) ;
400968: 2442007b addiu v0,v0,123 ;
40096c: afc20018 sw v0,24(s8) ;
400970: 27c2001c addiu v0,s8,28 ;
400974: 00402021 move a0,v0 ; hidden first arg (ptr to space for ret val)
400978: 8f99805c lw t9,-32676(gp) ; |
40097c: 0320f809 jalr t9 ; | call f1()
400980: 00000000 nop ;
400984: 8fdc0010 lw gp,16(s8) ;
400988: 8fc20018 lw v0,24(s8) ;
40098c: 2442ff85 addiu v0,v0,-123 ;
400990: afc20018 sw v0,24(s8) ;
400994: 27c20020 addiu v0,s8,32 ;
400998: 00402021 move a0,v0 ; hidden first arg (ptr to space for ret val)
40099c: 8f998064 lw t9,-32668(gp) ; |
4009a0: 0320f809 jalr t9 ; | call f2()
4009a4: 00000000 nop ;
4009a8: 8fdc0010 lw gp,16(s8) ;
4009ac: 8fc20018 lw v0,24(s8) ;
4009b0: 2442fff4 addiu v0,v0,-12 ;
4009b4: afc20018 sw v0,24(s8) ;
4009b8: 03c0e821 move sp,s8 ;
4009bc: 8fbf002c lw ra,44(sp) ;
4009c0: 8fbe0028 lw s8,40(sp) ;
4009c4: 03e00008 jr ra ;
4009c8: 27bd0030 addiu sp,sp,48 ;
; vim: ft=asm