xref: /third_party/elfutils/backends/ppc_regs.c (revision da0c48c4)
1/* Register names and numbers for PowerPC DWARF.
2   Copyright (C) 2005, 2006, 2007 Red Hat, Inc.
3   This file is part of elfutils.
4
5   This file is free software; you can redistribute it and/or modify
6   it under the terms of either
7
8     * the GNU Lesser General Public License as published by the Free
9       Software Foundation; either version 3 of the License, or (at
10       your option) any later version
11
12   or
13
14     * the GNU General Public License as published by the Free
15       Software Foundation; either version 2 of the License, or (at
16       your option) any later version
17
18   or both in parallel, as here.
19
20   elfutils is distributed in the hope that it will be useful, but
21   WITHOUT ANY WARRANTY; without even the implied warranty of
22   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
23   General Public License for more details.
24
25   You should have received copies of the GNU General Public License and
26   the GNU Lesser General Public License along with this program.  If
27   not, see <http://www.gnu.org/licenses/>.  */
28
29#ifdef HAVE_CONFIG_H
30# include <config.h>
31#endif
32
33#include <string.h>
34#include <dwarf.h>
35
36#define BACKEND ppc_
37#include "libebl_CPU.h"
38
39ssize_t
40ppc_register_info (Ebl *ebl __attribute__ ((unused)),
41		   int regno, char *name, size_t namelen,
42		   const char **prefix, const char **setname,
43		   int *bits, int *type)
44{
45  if (name == NULL)
46    return 1156;
47
48  if (regno < 0 || regno > 1155 || namelen < 8)
49    return -1;
50
51  *prefix = "";
52  *bits = ebl->machine == EM_PPC64 ? 64 : 32;
53  *type = (regno < 32 ? DW_ATE_signed
54	   : regno < 64 ? DW_ATE_float : DW_ATE_unsigned);
55
56  if (regno < 32 || regno == 64 || regno == 66)
57    *setname = "integer";
58  else if (regno < 64 || regno == 65)
59    {
60      *setname = "FPU";
61      if (ebl->machine != EM_PPC64 && regno < 64)
62	*bits = 64;
63    }
64  else if (regno == 67 || regno == 356 || regno == 612 || regno >= 1124)
65    {
66      *setname = "vector";
67      *bits = regno >= 1124 ? 128 : 32;
68    }
69  else
70    *setname = "privileged";
71
72  switch (regno)
73    {
74    case 0 ... 9:
75      name[0] = 'r';
76      name[1] = regno + '0';
77      namelen = 2;
78      break;
79
80    case 10 ... 31:
81      name[0] = 'r';
82      name[1] = regno / 10 + '0';
83      name[2] = regno % 10 + '0';
84      namelen = 3;
85      break;
86
87    case 32 + 0 ... 32 + 9:
88      name[0] = 'f';
89      name[1] = (regno - 32) + '0';
90      namelen = 2;
91      break;
92
93    case 32 + 10 ... 32 + 31:
94      name[0] = 'f';
95      name[1] = (regno - 32) / 10 + '0';
96      name[2] = (regno - 32) % 10 + '0';
97      namelen = 3;
98      break;
99
100    case 64:
101      return stpcpy (name, "cr") + 1 - name;
102    case 65:
103      return stpcpy (name, "fpscr") + 1 - name;
104    case 66:
105      return stpcpy (name, "msr") + 1 - name;
106    case 67:			/* XXX unofficial assignment */
107      return stpcpy (name, "vscr") + 1 - name;
108
109    case 70 + 0 ... 70 + 9:
110      name[0] = 's';
111      name[1] = 'r';
112      name[2] = (regno - 70) + '0';
113      namelen = 3;
114      break;
115
116    case 70 + 10 ... 70 + 15:
117      name[0] = 's';
118      name[1] = 'r';
119      name[2] = (regno - 70) / 10 + '0';
120      name[3] = (regno - 70) % 10 + '0';
121      namelen = 4;
122      break;
123
124    case 101:
125      return stpcpy (name, "xer") + 1 - name;
126    case 108:
127      return stpcpy (name, "lr") + 1 - name;
128    case 109:
129      return stpcpy (name, "ctr") + 1 - name;
130    case 118:
131      return stpcpy (name, "dsisr") + 1 - name;
132    case 119:
133      return stpcpy (name, "dar") + 1 - name;
134    case 122:
135      return stpcpy (name, "dec") + 1 - name;
136    case 356:
137      return stpcpy (name, "vrsave") + 1 - name;
138    case 612:
139      return stpcpy (name, "spefscr") + 1 - name;
140    case 100:
141      if (*bits == 32)
142	return stpcpy (name, "mq") + 1 - name;
143      FALLTHROUGH;
144    case 102 ... 107:
145      name[0] = 's';
146      name[1] = 'p';
147      name[2] = 'r';
148      name[3] = (regno - 100) + '0';
149      namelen = 4;
150      break;
151
152    case 114:
153      return stpcpy (name, "tfhar") + 1 - name;
154    case 115:
155      return stpcpy (name, "tfiar") + 1 - name;
156    case 116:
157      return stpcpy (name, "texasr") + 1 - name;
158
159    case 110 ... 113:
160    case 117:
161    case 120 ... 121:
162    case 123 ... 199:
163      name[0] = 's';
164      name[1] = 'p';
165      name[2] = 'r';
166      name[3] = (regno - 100) / 10 + '0';
167      name[4] = (regno - 100) % 10 + '0';
168      namelen = 5;
169      break;
170
171    case 200 ... 355:
172    case 357 ... 611:
173    case 613 ... 999:
174      name[0] = 's';
175      name[1] = 'p';
176      name[2] = 'r';
177      name[3] = (regno - 100) / 100 + '0';
178      name[4] = ((regno - 100) % 100 / 10) + '0';
179      name[5] = (regno - 100) % 10 + '0';
180      namelen = 6;
181      break;
182
183    case 1124 + 0 ... 1124 + 9:
184      name[0] = 'v';
185      name[1] = 'r';
186      name[2] = (regno - 1124) + '0';
187      namelen = 3;
188      break;
189
190    case 1124 + 10 ... 1124 + 31:
191      name[0] = 'v';
192      name[1] = 'r';
193      name[2] = (regno - 1124) / 10 + '0';
194      name[3] = (regno - 1124) % 10 + '0';
195      namelen = 4;
196      break;
197
198    default:
199      *setname = NULL;
200      return 0;
201    }
202
203  name[namelen++] = '\0';
204  return namelen;
205}
206
207__typeof (ppc_register_info)
208     ppc64_register_info __attribute__ ((alias ("ppc_register_info")));
209