OSDN Git Service

2003-07-22 Elena Zannoni <ezannoni@redhat.com>
[pf3gnuchains/pf3gnuchains3x.git] / gdb / dwarf2loc.c
1 /* DWARF 2 location expression support for GDB.
2    Copyright 2003 Free Software Foundation, Inc.
3    Contributed by Daniel Jacobowitz, MontaVista Software, Inc.
4
5    This file is part of GDB.
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or (at
10    your option) any later version.
11
12    This program is distributed in the hope that it will be useful, but
13    WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15    General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 59 Temple Place - Suite 330,
20    Boston, MA 02111-1307, USA.  */
21
22 #include "defs.h"
23 #include "ui-out.h"
24 #include "value.h"
25 #include "frame.h"
26 #include "gdbcore.h"
27 #include "target.h"
28 #include "inferior.h"
29 #include "ax.h"
30 #include "ax-gdb.h"
31 #include "regcache.h"
32 #include "objfiles.h"
33
34 #include "elf/dwarf2.h"
35 #include "dwarf2expr.h"
36 #include "dwarf2loc.h"
37
38 #include "gdb_string.h"
39
40 #ifndef DWARF2_REG_TO_REGNUM
41 #define DWARF2_REG_TO_REGNUM(REG) (REG)
42 #endif
43
44 /* A helper function for dealing with location lists.  Given a
45    symbol baton (BATON) and a pc value (PC), find the appropriate
46    location expression, set *LOCEXPR_LENGTH, and return a pointer
47    to the beginning of the expression.  Returns NULL on failure.
48
49    For now, only return the first matching location expression; there
50    can be more than one in the list.  */
51
52 static char *
53 find_location_expression (struct dwarf2_loclist_baton *baton,
54                           size_t *locexpr_length, CORE_ADDR pc)
55 {
56   CORE_ADDR base_address = baton->base_address;
57   CORE_ADDR low, high;
58   char *loc_ptr, *buf_end;
59   unsigned int addr_size = TARGET_ADDR_BIT / TARGET_CHAR_BIT, length;
60   CORE_ADDR base_mask = ~(~(CORE_ADDR)1 << (addr_size * 8 - 1));
61
62   loc_ptr = baton->data;
63   buf_end = baton->data + baton->size;
64
65   while (1)
66     {
67       low = dwarf2_read_address (loc_ptr, buf_end, &length);
68       loc_ptr += length;
69       high = dwarf2_read_address (loc_ptr, buf_end, &length);
70       loc_ptr += length;
71
72       /* An end-of-list entry.  */
73       if (low == 0 && high == 0)
74         return NULL;
75
76       /* A base-address-selection entry.  */
77       if ((low & base_mask) == base_mask)
78         {
79           base_address = high;
80           continue;
81         }
82
83       /* Otherwise, a location expression entry.  */
84       low += base_address;
85       high += base_address;
86
87       length = extract_unsigned_integer (loc_ptr, 2);
88       loc_ptr += 2;
89
90       if (pc >= low && pc < high)
91         {
92           *locexpr_length = length;
93           return loc_ptr;
94         }
95
96       loc_ptr += length;
97     }
98 }
99
100 /* This is the baton used when performing dwarf2 expression
101    evaluation.  */
102 struct dwarf_expr_baton
103 {
104   struct frame_info *frame;
105   struct objfile *objfile;
106 };
107
108 /* Helper functions for dwarf2_evaluate_loc_desc.  */
109
110 /* Using the frame specified in BATON, read register REGNUM.  The lval
111    type will be returned in LVALP, and for lval_memory the register
112    save address will be returned in ADDRP.  */
113 static CORE_ADDR
114 dwarf_expr_read_reg (void *baton, int dwarf_regnum)
115 {
116   struct dwarf_expr_baton *debaton = (struct dwarf_expr_baton *) baton;
117   CORE_ADDR result, save_addr;
118   enum lval_type lval_type;
119   char *buf;
120   int optimized, regnum, realnum, regsize;
121
122   regnum = DWARF2_REG_TO_REGNUM (dwarf_regnum);
123   regsize = register_size (current_gdbarch, regnum);
124   buf = (char *) alloca (regsize);
125
126   frame_register (debaton->frame, regnum, &optimized, &lval_type, &save_addr,
127                   &realnum, buf);
128   /* NOTE: cagney/2003-05-22: This extract is assuming that a DWARF 2
129      address is always unsigned.  That may or may not be true.  */
130   result = extract_unsigned_integer (buf, regsize);
131
132   return result;
133 }
134
135 /* Read memory at ADDR (length LEN) into BUF.  */
136
137 static void
138 dwarf_expr_read_mem (void *baton, char *buf, CORE_ADDR addr, size_t len)
139 {
140   read_memory (addr, buf, len);
141 }
142
143 /* Using the frame specified in BATON, find the location expression
144    describing the frame base.  Return a pointer to it in START and
145    its length in LENGTH.  */
146 static void
147 dwarf_expr_frame_base (void *baton, unsigned char **start, size_t * length)
148 {
149   /* FIXME: cagney/2003-03-26: This code should be using
150      get_frame_base_address(), and then implement a dwarf2 specific
151      this_base method.  */
152   struct symbol *framefunc;
153   struct dwarf_expr_baton *debaton = (struct dwarf_expr_baton *) baton;
154
155   framefunc = get_frame_function (debaton->frame);
156
157   if (SYMBOL_LOCATION_FUNCS (framefunc) == &dwarf2_loclist_funcs)
158     {
159       struct dwarf2_loclist_baton *symbaton;
160       symbaton = SYMBOL_LOCATION_BATON (framefunc);
161       *start = find_location_expression (symbaton, length,
162                                          get_frame_pc (debaton->frame));
163     }
164   else
165     {
166       struct dwarf2_locexpr_baton *symbaton;
167       symbaton = SYMBOL_LOCATION_BATON (framefunc);
168       *length = symbaton->size;
169       *start = symbaton->data;
170     }
171
172   if (*start == NULL)
173     error ("Could not find the frame base for \"%s\".",
174            SYMBOL_NATURAL_NAME (framefunc));
175 }
176
177 /* Using the objfile specified in BATON, find the address for the
178    current thread's thread-local storage with offset OFFSET.  */
179 static CORE_ADDR
180 dwarf_expr_tls_address (void *baton, CORE_ADDR offset)
181 {
182   struct dwarf_expr_baton *debaton = (struct dwarf_expr_baton *) baton;
183   CORE_ADDR addr;
184
185   if (target_get_thread_local_address_p ())
186     addr = target_get_thread_local_address (inferior_ptid,
187                                             debaton->objfile,
188                                             offset);
189   /* It wouldn't be wrong here to try a gdbarch method, too; finding
190      TLS is an ABI-specific thing.  But we don't do that yet.  */
191   else
192     error ("Cannot find thread-local variables on this target");
193
194   return addr;
195 }
196
197 /* Evaluate a location description, starting at DATA and with length
198    SIZE, to find the current location of variable VAR in the context
199    of FRAME.  */
200 static struct value *
201 dwarf2_evaluate_loc_desc (struct symbol *var, struct frame_info *frame,
202                           unsigned char *data, unsigned short size,
203                           struct objfile *objfile)
204 {
205   CORE_ADDR result;
206   struct value *retval;
207   struct dwarf_expr_baton baton;
208   struct dwarf_expr_context *ctx;
209
210   if (size == 0)
211     {
212       retval = allocate_value (SYMBOL_TYPE (var));
213       VALUE_LVAL (retval) = not_lval;
214       VALUE_OPTIMIZED_OUT (retval) = 1;
215     }
216
217   baton.frame = frame;
218   baton.objfile = objfile;
219
220   ctx = new_dwarf_expr_context ();
221   ctx->baton = &baton;
222   ctx->read_reg = dwarf_expr_read_reg;
223   ctx->read_mem = dwarf_expr_read_mem;
224   ctx->get_frame_base = dwarf_expr_frame_base;
225   ctx->get_tls_address = dwarf_expr_tls_address;
226
227   dwarf_expr_eval (ctx, data, size);
228   result = dwarf_expr_fetch (ctx, 0);
229
230   if (ctx->in_reg)
231     {
232       int regnum = DWARF2_REG_TO_REGNUM (result);
233       retval = value_from_register (SYMBOL_TYPE (var), regnum, frame);
234     }
235   else
236     {
237       retval = allocate_value (SYMBOL_TYPE (var));
238       VALUE_BFD_SECTION (retval) = SYMBOL_BFD_SECTION (var);
239
240       VALUE_LVAL (retval) = lval_memory;
241       VALUE_LAZY (retval) = 1;
242       VALUE_ADDRESS (retval) = result;
243     }
244
245   free_dwarf_expr_context (ctx);
246
247   return retval;
248 }
249
250
251
252
253 \f
254 /* Helper functions and baton for dwarf2_loc_desc_needs_frame.  */
255
256 struct needs_frame_baton
257 {
258   int needs_frame;
259 };
260
261 /* Reads from registers do require a frame.  */
262 static CORE_ADDR
263 needs_frame_read_reg (void *baton, int regnum)
264 {
265   struct needs_frame_baton *nf_baton = baton;
266   nf_baton->needs_frame = 1;
267   return 1;
268 }
269
270 /* Reads from memory do not require a frame.  */
271 static void
272 needs_frame_read_mem (void *baton, char *buf, CORE_ADDR addr, size_t len)
273 {
274   memset (buf, 0, len);
275 }
276
277 /* Frame-relative accesses do require a frame.  */
278 static void
279 needs_frame_frame_base (void *baton, unsigned char **start, size_t * length)
280 {
281   static char lit0 = DW_OP_lit0;
282   struct needs_frame_baton *nf_baton = baton;
283
284   *start = &lit0;
285   *length = 1;
286
287   nf_baton->needs_frame = 1;
288 }
289
290 /* Thread-local accesses do require a frame.  */
291 static CORE_ADDR
292 needs_frame_tls_address (void *baton, CORE_ADDR offset)
293 {
294   struct needs_frame_baton *nf_baton = baton;
295   nf_baton->needs_frame = 1;
296   return 1;
297 }
298
299 /* Return non-zero iff the location expression at DATA (length SIZE)
300    requires a frame to evaluate.  */
301
302 static int
303 dwarf2_loc_desc_needs_frame (unsigned char *data, unsigned short size)
304 {
305   struct needs_frame_baton baton;
306   struct dwarf_expr_context *ctx;
307
308   baton.needs_frame = 0;
309
310   ctx = new_dwarf_expr_context ();
311   ctx->baton = &baton;
312   ctx->read_reg = needs_frame_read_reg;
313   ctx->read_mem = needs_frame_read_mem;
314   ctx->get_frame_base = needs_frame_frame_base;
315   ctx->get_tls_address = needs_frame_tls_address;
316
317   dwarf_expr_eval (ctx, data, size);
318
319   free_dwarf_expr_context (ctx);
320
321   return baton.needs_frame;
322 }
323
324 static void
325 dwarf2_tracepoint_var_ref (struct symbol * symbol, struct agent_expr * ax,
326                            struct axs_value * value, unsigned char *data,
327                            int size)
328 {
329   if (size == 0)
330     error ("Symbol \"%s\" has been optimized out.",
331            SYMBOL_PRINT_NAME (symbol));
332
333   if (size == 1
334       && data[0] >= DW_OP_reg0
335       && data[0] <= DW_OP_reg31)
336     {
337       value->kind = axs_lvalue_register;
338       value->u.reg = data[0] - DW_OP_reg0;
339     }
340   else if (data[0] == DW_OP_regx)
341     {
342       ULONGEST reg;
343       read_uleb128 (data + 1, data + size, &reg);
344       value->kind = axs_lvalue_register;
345       value->u.reg = reg;
346     }
347   else if (data[0] == DW_OP_fbreg)
348     {
349       /* And this is worse than just minimal; we should honor the frame base
350          as above.  */
351       int frame_reg;
352       LONGEST frame_offset;
353       unsigned char *buf_end;
354
355       buf_end = read_sleb128 (data + 1, data + size, &frame_offset);
356       if (buf_end != data + size)
357         error ("Unexpected opcode after DW_OP_fbreg for symbol \"%s\".",
358                SYMBOL_PRINT_NAME (symbol));
359
360       TARGET_VIRTUAL_FRAME_POINTER (ax->scope, &frame_reg, &frame_offset);
361       ax_reg (ax, frame_reg);
362       ax_const_l (ax, frame_offset);
363       ax_simple (ax, aop_add);
364
365       ax_const_l (ax, frame_offset);
366       ax_simple (ax, aop_add);
367       value->kind = axs_lvalue_memory;
368     }
369   else
370     error ("Unsupported DWARF opcode in the location of \"%s\".",
371            SYMBOL_PRINT_NAME (symbol));
372 }
373 \f
374 /* Return the value of SYMBOL in FRAME using the DWARF-2 expression
375    evaluator to calculate the location.  */
376 static struct value *
377 locexpr_read_variable (struct symbol *symbol, struct frame_info *frame)
378 {
379   struct dwarf2_locexpr_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
380   struct value *val;
381   val = dwarf2_evaluate_loc_desc (symbol, frame, dlbaton->data, dlbaton->size,
382                                   dlbaton->objfile);
383
384   return val;
385 }
386
387 /* Return non-zero iff we need a frame to evaluate SYMBOL.  */
388 static int
389 locexpr_read_needs_frame (struct symbol *symbol)
390 {
391   struct dwarf2_locexpr_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
392   return dwarf2_loc_desc_needs_frame (dlbaton->data, dlbaton->size);
393 }
394
395 /* Print a natural-language description of SYMBOL to STREAM.  */
396 static int
397 locexpr_describe_location (struct symbol *symbol, struct ui_file *stream)
398 {
399   /* FIXME: be more extensive.  */
400   struct dwarf2_locexpr_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
401
402   if (dlbaton->size == 1
403       && dlbaton->data[0] >= DW_OP_reg0
404       && dlbaton->data[0] <= DW_OP_reg31)
405     {
406       int regno = DWARF2_REG_TO_REGNUM (dlbaton->data[0] - DW_OP_reg0);
407       fprintf_filtered (stream,
408                         "a variable in register %s", REGISTER_NAME (regno));
409       return 1;
410     }
411
412   /* The location expression for a TLS variable looks like this (on a
413      64-bit LE machine):
414
415      DW_AT_location    : 10 byte block: 3 4 0 0 0 0 0 0 0 e0
416                         (DW_OP_addr: 4; DW_OP_GNU_push_tls_address)
417      
418      0x3 is the encoding for DW_OP_addr, which has an operand as long
419      as the size of an address on the target machine (here is 8
420      bytes).  0xe0 is the encoding for DW_OP_GNU_push_tls_address.
421      The operand represents the offset at which the variable is within
422      the thread local storage.  */
423
424   if (dlbaton->size > 1 
425       && dlbaton->data[dlbaton->size - 1] == DW_OP_GNU_push_tls_address)
426     if (dlbaton->data[0] == DW_OP_addr)
427       {
428         int bytes_read;
429         CORE_ADDR offset = dwarf2_read_address (&dlbaton->data[1],
430                                                 &dlbaton->data[dlbaton->size - 2],
431                                                 &bytes_read);
432         fprintf_filtered (stream, 
433                           "a thread-local variable at offset %s in the"
434                           "thread-local storage for `%s'",
435                           paddr_nz (offset), dlbaton->objfile->name);
436         return 1;
437       }
438   
439
440   fprintf_filtered (stream,
441                     "a variable with complex or multiple locations (DWARF2)");
442   return 1;
443 }
444
445
446 /* Describe the location of SYMBOL as an agent value in VALUE, generating
447    any necessary bytecode in AX.
448
449    NOTE drow/2003-02-26: This function is extremely minimal, because
450    doing it correctly is extremely complicated and there is no
451    publicly available stub with tracepoint support for me to test
452    against.  When there is one this function should be revisited.  */
453
454 static void
455 locexpr_tracepoint_var_ref (struct symbol * symbol, struct agent_expr * ax,
456                             struct axs_value * value)
457 {
458   struct dwarf2_locexpr_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
459
460   dwarf2_tracepoint_var_ref (symbol, ax, value, dlbaton->data, dlbaton->size);
461 }
462
463 /* The set of location functions used with the DWARF-2 expression
464    evaluator.  */
465 struct location_funcs dwarf2_locexpr_funcs = {
466   locexpr_read_variable,
467   locexpr_read_needs_frame,
468   locexpr_describe_location,
469   locexpr_tracepoint_var_ref
470 };
471
472
473 /* Wrapper functions for location lists.  These generally find
474    the appropriate location expression and call something above.  */
475
476 /* Return the value of SYMBOL in FRAME using the DWARF-2 expression
477    evaluator to calculate the location.  */
478 static struct value *
479 loclist_read_variable (struct symbol *symbol, struct frame_info *frame)
480 {
481   struct dwarf2_loclist_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
482   struct value *val;
483   unsigned char *data;
484   size_t size;
485
486   data = find_location_expression (dlbaton, &size,
487                                    frame ? get_frame_pc (frame) : 0);
488   if (data == NULL)
489     error ("Variable \"%s\" is not available.", SYMBOL_NATURAL_NAME (symbol));
490
491   val = dwarf2_evaluate_loc_desc (symbol, frame, data, size, dlbaton->objfile);
492
493   return val;
494 }
495
496 /* Return non-zero iff we need a frame to evaluate SYMBOL.  */
497 static int
498 loclist_read_needs_frame (struct symbol *symbol)
499 {
500   /* If there's a location list, then assume we need to have a frame
501      to choose the appropriate location expression.  With tracking of
502      global variables this is not necessarily true, but such tracking
503      is disabled in GCC at the moment until we figure out how to
504      represent it.  */
505
506   return 1;
507 }
508
509 /* Print a natural-language description of SYMBOL to STREAM.  */
510 static int
511 loclist_describe_location (struct symbol *symbol, struct ui_file *stream)
512 {
513   /* FIXME: Could print the entire list of locations.  */
514   fprintf_filtered (stream, "a variable with multiple locations");
515   return 1;
516 }
517
518 /* Describe the location of SYMBOL as an agent value in VALUE, generating
519    any necessary bytecode in AX.  */
520 static void
521 loclist_tracepoint_var_ref (struct symbol * symbol, struct agent_expr * ax,
522                             struct axs_value * value)
523 {
524   struct dwarf2_loclist_baton *dlbaton = SYMBOL_LOCATION_BATON (symbol);
525   unsigned char *data;
526   size_t size;
527
528   data = find_location_expression (dlbaton, &size, ax->scope);
529   if (data == NULL)
530     error ("Variable \"%s\" is not available.", SYMBOL_NATURAL_NAME (symbol));
531
532   dwarf2_tracepoint_var_ref (symbol, ax, value, data, size);
533 }
534
535 /* The set of location functions used with the DWARF-2 expression
536    evaluator and location lists.  */
537 struct location_funcs dwarf2_loclist_funcs = {
538   loclist_read_variable,
539   loclist_read_needs_frame,
540   loclist_describe_location,
541   loclist_tracepoint_var_ref
542 };