aboutsummaryrefslogtreecommitdiff
path: root/gdb/location.c
diff options
context:
space:
mode:
Diffstat (limited to 'gdb/location.c')
-rw-r--r--gdb/location.c179
1 files changed, 179 insertions, 0 deletions
diff --git a/gdb/location.c b/gdb/location.c
index fd35c48..3985e5a 100644
--- a/gdb/location.c
+++ b/gdb/location.c
@@ -50,6 +50,10 @@ struct event_location
/* An address in the inferior. */
CORE_ADDR address;
#define EL_ADDRESS(PTR) (PTR)->u.address
+
+ /* An explicit location. */
+ struct explicit_location explicit;
+#define EL_EXPLICIT(PTR) (&((PTR)->u.explicit))
} u;
/* Cached string representation of this location. This is used, e.g., to
@@ -68,6 +72,15 @@ event_location_type (const struct event_location *location)
/* See description in location.h. */
+void
+initialize_explicit_location (struct explicit_location *explicit)
+{
+ memset (explicit, 0, sizeof (struct explicit_location));
+ explicit->line_offset.sign = LINE_OFFSET_UNKNOWN;
+}
+
+/* See description in location.h. */
+
struct event_location *
new_linespec_location (char **linespec)
{
@@ -145,6 +158,137 @@ get_probe_location (const struct event_location *location)
/* See description in location.h. */
struct event_location *
+new_explicit_location (const struct explicit_location *explicit)
+{
+ struct event_location tmp;
+
+ memset (&tmp, 0, sizeof (struct event_location));
+ EL_TYPE (&tmp) = EXPLICIT_LOCATION;
+ initialize_explicit_location (EL_EXPLICIT (&tmp));
+ if (explicit != NULL)
+ {
+ if (explicit->source_filename != NULL)
+ {
+ EL_EXPLICIT (&tmp)->source_filename
+ = explicit->source_filename;
+ }
+
+ if (explicit->function_name != NULL)
+ EL_EXPLICIT (&tmp)->function_name
+ = explicit->function_name;
+
+ if (explicit->label_name != NULL)
+ EL_EXPLICIT (&tmp)->label_name = explicit->label_name;
+
+ if (explicit->line_offset.sign != LINE_OFFSET_UNKNOWN)
+ EL_EXPLICIT (&tmp)->line_offset = explicit->line_offset;
+ }
+
+ return copy_event_location (&tmp);
+}
+
+/* See description in location.h. */
+
+struct explicit_location *
+get_explicit_location (struct event_location *location)
+{
+ gdb_assert (EL_TYPE (location) == EXPLICIT_LOCATION);
+ return EL_EXPLICIT (location);
+}
+
+/* See description in location.h. */
+
+const struct explicit_location *
+get_explicit_location_const (const struct event_location *location)
+{
+ gdb_assert (EL_TYPE (location) == EXPLICIT_LOCATION);
+ return EL_EXPLICIT (location);
+}
+
+/* This convenience function returns a malloc'd string which
+ represents the location in EXPLICIT.
+
+ AS_LINESPEC is non-zero if this string should be a linespec.
+ Otherwise it will be output in explicit form. */
+
+static char *
+explicit_to_string_internal (int as_linespec,
+ const struct explicit_location *explicit)
+{
+ struct ui_file *buf;
+ char space, *result;
+ int need_space = 0;
+ struct cleanup *cleanup;
+
+ space = as_linespec ? ':' : ' ';
+ buf = mem_fileopen ();
+ cleanup = make_cleanup_ui_file_delete (buf);
+
+ if (explicit->source_filename != NULL)
+ {
+ if (!as_linespec)
+ fputs_unfiltered ("-source ", buf);
+ fputs_unfiltered (explicit->source_filename, buf);
+ need_space = 1;
+ }
+
+ if (explicit->function_name != NULL)
+ {
+ if (need_space)
+ fputc_unfiltered (space, buf);
+ if (!as_linespec)
+ fputs_unfiltered ("-function ", buf);
+ fputs_unfiltered (explicit->function_name, buf);
+ need_space = 1;
+ }
+
+ if (explicit->label_name != NULL)
+ {
+ if (need_space)
+ fputc_unfiltered (space, buf);
+ if (!as_linespec)
+ fputs_unfiltered ("-label ", buf);
+ fputs_unfiltered (explicit->label_name, buf);
+ need_space = 1;
+ }
+
+ if (explicit->line_offset.sign != LINE_OFFSET_UNKNOWN)
+ {
+ if (need_space)
+ fputc_unfiltered (space, buf);
+ if (!as_linespec)
+ fputs_unfiltered ("-line ", buf);
+ fprintf_filtered (buf, "%s%d",
+ (explicit->line_offset.sign == LINE_OFFSET_NONE ? ""
+ : (explicit->line_offset.sign
+ == LINE_OFFSET_PLUS ? "+" : "-")),
+ explicit->line_offset.offset);
+ }
+
+ result = ui_file_xstrdup (buf, NULL);
+ do_cleanups (cleanup);
+ return result;
+}
+
+/* See description in location.h. */
+
+char *
+explicit_location_to_string (const struct explicit_location *explicit)
+{
+ return explicit_to_string_internal (0, explicit);
+}
+
+/* See description in location.h. */
+
+char *
+explicit_location_to_linespec (const struct explicit_location *explicit)
+{
+ return explicit_to_string_internal (1, explicit);
+}
+
+/* See description in location.h. */
+
+struct event_location *
copy_event_location (const struct event_location *src)
{
struct event_location *dst;
@@ -165,6 +309,22 @@ copy_event_location (const struct event_location *src)
EL_ADDRESS (dst) = EL_ADDRESS (src);
break;
+ case EXPLICIT_LOCATION:
+ if (EL_EXPLICIT (src)->source_filename != NULL)
+ EL_EXPLICIT (dst)->source_filename
+ = xstrdup (EL_EXPLICIT (src)->source_filename);
+
+ if (EL_EXPLICIT (src)->function_name != NULL)
+ EL_EXPLICIT (dst)->function_name
+ = xstrdup (EL_EXPLICIT (src)->function_name);
+
+ if (EL_EXPLICIT (src)->label_name != NULL)
+ EL_EXPLICIT (dst)->label_name = xstrdup (EL_EXPLICIT (src)->label_name);
+
+ EL_EXPLICIT (dst)->line_offset = EL_EXPLICIT (src)->line_offset;
+ break;
+
+
case PROBE_LOCATION:
if (EL_PROBE (src) != NULL)
EL_PROBE (dst) = xstrdup (EL_PROBE (src));
@@ -214,6 +374,12 @@ delete_event_location (struct event_location *location)
/* Nothing to do. */
break;
+ case EXPLICIT_LOCATION:
+ xfree (EL_EXPLICIT (location)->source_filename);
+ xfree (EL_EXPLICIT (location)->function_name);
+ xfree (EL_EXPLICIT (location)->label_name);
+ break;
+
case PROBE_LOCATION:
xfree (EL_PROBE (location));
break;
@@ -246,6 +412,11 @@ event_location_to_string (struct event_location *location)
core_addr_to_string (EL_ADDRESS (location)));
break;
+ case EXPLICIT_LOCATION:
+ EL_STRING (location)
+ = explicit_location_to_string (EL_EXPLICIT (location));
+ break;
+
case PROBE_LOCATION:
EL_STRING (location) = xstrdup (EL_PROBE (location));
break;
@@ -312,6 +483,14 @@ event_location_empty_p (const struct event_location *location)
case ADDRESS_LOCATION:
return 0;
+ case EXPLICIT_LOCATION:
+ return (EL_EXPLICIT (location) == NULL
+ || (EL_EXPLICIT (location)->source_filename == NULL
+ && EL_EXPLICIT (location)->function_name == NULL
+ && EL_EXPLICIT (location)->label_name == NULL
+ && (EL_EXPLICIT (location)->line_offset.sign
+ == LINE_OFFSET_UNKNOWN)));
+
case PROBE_LOCATION:
return EL_PROBE (location) == NULL;