1 {
2     Copyright (c) 2002 by Florian Klaempfl
3 
4     Implements the PowerPC specific part of call nodes
5 
6     This program is free software; you can redistribute it and/or modify
7     it under the terms of the GNU General Public License as published by
8     the Free Software Foundation; either version 2 of the License, or
9     (at your option) any later version.
10 
11     This program is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.
15 
16     You should have received a copy of the GNU General Public License
17     along with this program; if not, write to the Free Software
18     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 
20  ****************************************************************************
21 }
22 unit nppccal;
23 
24 {$I fpcdefs.inc}
25 
26 interface
27 
28 uses
29   aasmdata, cgbase,
30   symdef, node, ncal, ncgcal;
31 
32 type
33 
34   tppccallparanode = class(tcgcallparanode)
35   end;
36 
37   tppccallnode = class(tcgcallnode)
38    protected
get_call_regnull39     function get_call_reg(list: TAsmList): tregister; override;
40     procedure unget_call_reg(list: TAsmList; reg: tregister); override;
41    public
pass_1null42     function pass_1: tnode; override;
43     procedure do_syscall; override;
44   end;
45 
46 implementation
47 
48 uses
49   globtype, systems,
50   cutils, verbose, globals,
51   symconst, symbase, symsym, symtable, defutil, paramgr, parabase,
52   pass_2,
53   cpuinfo, cpubase, aasmbase, aasmtai, aasmcpu,
54   nmem, nld, ncnv,
55   ncgutil, cgutils, cgobj, tgobj, rgobj, rgcpu,
56   cgcpu, cpupi, procinfo;
57 
58 
tppccallnode.get_call_regnull59 function tppccallnode.get_call_reg(list: TAsmList): tregister;
60   begin
61     { on the ppc64/ELFv2 abi, all indirect calls must go via R12, so that the
62       called function can use R12 as PIC base register }
63     cg.getcpuregister(list,NR_R12);
64     result:=NR_R12;
65   end;
66 
67 
68 procedure tppccallnode.unget_call_reg(list: TAsmList; reg: tregister);
69   begin
70     cg.ungetcpuregister(list,NR_R12);
71   end;
72 
tppccallnode.pass_1null73 function tppccallnode.pass_1: tnode;
74   begin
75     result:=inherited;
76     if assigned(result) then
77       exit;
78     { for ELFv2, we must load the TOC/GOT register in case this routine may
79       call an external routine (because the lookup of the target address is
80       TOC-based). Maybe needs to be extended to non-ELFv2 too }
81     if target_info.abi=abi_powerpc_elfv2 then
82       include(current_procinfo.flags,pi_needs_got);
83   end;
84 
85 
86 procedure tppccallnode.do_syscall;
87 begin
88   { no MorphOS style syscalls supported. Only implemented to avoid abstract
89    method not implemented compiler warning. }
90   internalerror(2005120401);
91 end;
92 
93 begin
94   ccallparanode:=tppccallparanode;
95   ccallnode := tppccallnode;
96 end.
97 
98