]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - gdb/location.c
Update copyright year range in header of all files managed by GDB
[thirdparty/binutils-gdb.git] / gdb / location.c
1 /* Data structures and API for location specs in GDB.
2 Copyright (C) 2013-2024 Free Software Foundation, Inc.
3
4 This file is part of GDB.
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 3 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, see <http://www.gnu.org/licenses/>. */
18
19 #include "defs.h"
20 #include "gdbsupport/gdb_assert.h"
21 #include "gdbsupport/gdb-checked-static-cast.h"
22 #include "location.h"
23 #include "symtab.h"
24 #include "language.h"
25 #include "linespec.h"
26 #include "cli/cli-utils.h"
27 #include "probe.h"
28 #include "cp-support.h"
29
30 #include <ctype.h>
31 #include <string.h>
32
33 static std::string
34 explicit_to_string_internal (bool as_linespec,
35 const explicit_location_spec *explicit_loc);
36
37 /* Return a xstrdup of STR if not NULL, otherwise return NULL. */
38
39 static char *
40 maybe_xstrdup (const char *str)
41 {
42 return (str != nullptr ? xstrdup (str) : nullptr);
43 }
44
45 probe_location_spec::probe_location_spec (std::string &&probe)
46 : location_spec (PROBE_LOCATION_SPEC, std::move (probe))
47 {
48 }
49
50 location_spec_up
51 probe_location_spec::clone () const
52 {
53 return location_spec_up (new probe_location_spec (*this));
54 }
55
56 bool
57 probe_location_spec::empty_p () const
58 {
59 return false;
60 }
61
62 std::string probe_location_spec::compute_string () const
63 {
64 return std::move (m_as_string);
65 }
66
67 /* A "normal" linespec. */
68 linespec_location_spec::linespec_location_spec
69 (const char **linespec, symbol_name_match_type match_type_)
70 : location_spec (LINESPEC_LOCATION_SPEC),
71 match_type (match_type_)
72 {
73 if (*linespec != NULL)
74 {
75 const char *p;
76 const char *orig = *linespec;
77
78 linespec_lex_to_end (linespec);
79 p = remove_trailing_whitespace (orig, *linespec);
80
81 /* If there is no valid linespec then this will leave the
82 spec_string as nullptr. This behaviour is relied on in the
83 breakpoint setting code, where spec_string being nullptr means
84 to use the default breakpoint location. */
85 if ((p - orig) > 0)
86 spec_string.reset (savestring (orig, p - orig));
87 }
88 }
89
90 location_spec_up
91 linespec_location_spec::clone () const
92 {
93 return location_spec_up (new linespec_location_spec (*this));
94 }
95
96 bool
97 linespec_location_spec::empty_p () const
98 {
99 return false;
100 }
101
102 linespec_location_spec::linespec_location_spec
103 (const linespec_location_spec &other)
104 : location_spec (other),
105 match_type (other.match_type),
106 spec_string (maybe_xstrdup (other.spec_string.get ()))
107 {
108 }
109
110 std::string
111 linespec_location_spec::compute_string () const
112 {
113 if (spec_string != nullptr)
114 {
115 if (match_type == symbol_name_match_type::FULL)
116 return std::string ("-qualified ") + spec_string.get ();
117 else
118 return spec_string.get ();
119 }
120 return {};
121 }
122
123 address_location_spec::address_location_spec (CORE_ADDR addr,
124 const char *addr_string,
125 int addr_string_len)
126 : location_spec (ADDRESS_LOCATION_SPEC),
127 address (addr)
128 {
129 if (addr_string != nullptr)
130 m_as_string = std::string (addr_string, addr_string_len);
131 }
132
133 location_spec_up
134 address_location_spec::clone () const
135 {
136 return location_spec_up (new address_location_spec (*this));
137 }
138
139 bool
140 address_location_spec::empty_p () const
141 {
142 return false;
143 }
144
145 address_location_spec::address_location_spec
146 (const address_location_spec &other)
147 : location_spec (other),
148 address (other.address)
149 {
150 }
151
152 std::string
153 address_location_spec::compute_string () const
154 {
155 const char *addr_string = core_addr_to_string (address);
156 return std::string ("*") + addr_string;
157 }
158
159 explicit_location_spec::explicit_location_spec (const char *function_name)
160 : location_spec (EXPLICIT_LOCATION_SPEC),
161 function_name (maybe_xstrdup (function_name))
162 {
163 }
164
165 explicit_location_spec::explicit_location_spec
166 (const explicit_location_spec &other)
167 : location_spec (other),
168 source_filename (maybe_xstrdup (other.source_filename.get ())),
169 function_name (maybe_xstrdup (other.function_name.get ())),
170 func_name_match_type (other.func_name_match_type),
171 label_name (maybe_xstrdup (other.label_name.get ())),
172 line_offset (other.line_offset)
173 {
174 }
175
176 location_spec_up
177 explicit_location_spec::clone () const
178 {
179 return location_spec_up (new explicit_location_spec (*this));
180 }
181
182 bool
183 explicit_location_spec::empty_p () const
184 {
185 return (source_filename == nullptr
186 && function_name == nullptr
187 && label_name == nullptr
188 && line_offset.sign == LINE_OFFSET_UNKNOWN);
189 }
190
191 std::string
192 explicit_location_spec::compute_string () const
193 {
194 return explicit_to_string_internal (false, this);
195 }
196
197 /* See description in location.h. */
198
199 location_spec_up
200 new_linespec_location_spec (const char **linespec,
201 symbol_name_match_type match_type)
202 {
203 return location_spec_up (new linespec_location_spec (linespec,
204 match_type));
205 }
206
207 /* See description in location.h. */
208
209 const linespec_location_spec *
210 as_linespec_location_spec (const location_spec *locspec)
211 {
212 gdb_assert (locspec->type () == LINESPEC_LOCATION_SPEC);
213 return gdb::checked_static_cast<const linespec_location_spec *> (locspec);
214 }
215
216 /* See description in location.h. */
217
218 location_spec_up
219 new_address_location_spec (CORE_ADDR addr, const char *addr_string,
220 int addr_string_len)
221 {
222 return location_spec_up (new address_location_spec (addr, addr_string,
223 addr_string_len));
224 }
225
226 /* See description in location.h. */
227
228 const address_location_spec *
229 as_address_location_spec (const location_spec *locspec)
230 {
231 gdb_assert (locspec->type () == ADDRESS_LOCATION_SPEC);
232 return gdb::checked_static_cast<const address_location_spec *> (locspec);
233 }
234
235 /* See description in location.h. */
236
237 location_spec_up
238 new_probe_location_spec (std::string &&probe)
239 {
240 return location_spec_up (new probe_location_spec (std::move (probe)));
241 }
242
243 /* See description in location.h. */
244
245 const probe_location_spec *
246 as_probe_location_spec (const location_spec *locspec)
247 {
248 gdb_assert (locspec->type () == PROBE_LOCATION_SPEC);
249 return gdb::checked_static_cast<const probe_location_spec *> (locspec);
250 }
251
252 /* See description in location.h. */
253
254 const explicit_location_spec *
255 as_explicit_location_spec (const location_spec *locspec)
256 {
257 gdb_assert (locspec->type () == EXPLICIT_LOCATION_SPEC);
258 return gdb::checked_static_cast<const explicit_location_spec *> (locspec);
259 }
260
261 /* See description in location.h. */
262
263 explicit_location_spec *
264 as_explicit_location_spec (location_spec *locspec)
265 {
266 gdb_assert (locspec->type () == EXPLICIT_LOCATION_SPEC);
267 return gdb::checked_static_cast<explicit_location_spec *> (locspec);
268 }
269
270 /* Return a string representation of the explicit location spec in
271 EXPLICIT_LOCSPEC.
272
273 AS_LINESPEC is true if this string should be a linespec. Otherwise
274 it will be output in explicit form. */
275
276 static std::string
277 explicit_to_string_internal (bool as_linespec,
278 const explicit_location_spec *explicit_loc)
279 {
280 bool need_space = false;
281 char space = as_linespec ? ':' : ' ';
282 string_file buf;
283
284 if (explicit_loc->source_filename != NULL)
285 {
286 if (!as_linespec)
287 buf.puts ("-source ");
288 buf.puts (explicit_loc->source_filename.get ());
289 need_space = true;
290 }
291
292 if (explicit_loc->function_name != NULL)
293 {
294 if (need_space)
295 buf.putc (space);
296 if (explicit_loc->func_name_match_type == symbol_name_match_type::FULL)
297 buf.puts ("-qualified ");
298 if (!as_linespec)
299 buf.puts ("-function ");
300 buf.puts (explicit_loc->function_name.get ());
301 need_space = true;
302 }
303
304 if (explicit_loc->label_name != NULL)
305 {
306 if (need_space)
307 buf.putc (space);
308 if (!as_linespec)
309 buf.puts ("-label ");
310 buf.puts (explicit_loc->label_name.get ());
311 need_space = true;
312 }
313
314 if (explicit_loc->line_offset.sign != LINE_OFFSET_UNKNOWN)
315 {
316 if (need_space)
317 buf.putc (space);
318 if (!as_linespec)
319 buf.puts ("-line ");
320 buf.printf ("%s%d",
321 (explicit_loc->line_offset.sign == LINE_OFFSET_NONE ? ""
322 : (explicit_loc->line_offset.sign
323 == LINE_OFFSET_PLUS ? "+" : "-")),
324 explicit_loc->line_offset.offset);
325 }
326
327 return buf.release ();
328 }
329
330 /* See description in location.h. */
331
332 std::string
333 explicit_location_spec::to_linespec () const
334 {
335 return explicit_to_string_internal (true, this);
336 }
337
338 /* Find an instance of the quote character C in the string S that is
339 outside of all single- and double-quoted strings (i.e., any quoting
340 other than C). */
341
342 static const char *
343 find_end_quote (const char *s, char end_quote_char)
344 {
345 /* zero if we're not in quotes;
346 '"' if we're in a double-quoted string;
347 '\'' if we're in a single-quoted string. */
348 char nested_quote_char = '\0';
349
350 for (const char *scan = s; *scan != '\0'; scan++)
351 {
352 if (nested_quote_char != '\0')
353 {
354 if (*scan == nested_quote_char)
355 nested_quote_char = '\0';
356 else if (scan[0] == '\\' && *(scan + 1) != '\0')
357 scan++;
358 }
359 else if (*scan == end_quote_char && nested_quote_char == '\0')
360 return scan;
361 else if (*scan == '"' || *scan == '\'')
362 nested_quote_char = *scan;
363 }
364
365 return 0;
366 }
367
368 /* A lexer for explicit location specs. This function will advance
369 INP past any strings that it lexes. Returns a malloc'd copy of the
370 lexed string or NULL if no lexing was done. */
371
372 static gdb::unique_xmalloc_ptr<char>
373 explicit_location_spec_lex_one (const char **inp,
374 const struct language_defn *language,
375 explicit_completion_info *completion_info)
376 {
377 const char *start = *inp;
378
379 if (*start == '\0')
380 return NULL;
381
382 /* If quoted, skip to the ending quote. */
383 if (strchr (get_gdb_linespec_parser_quote_characters (), *start))
384 {
385 if (completion_info != NULL)
386 completion_info->quoted_arg_start = start;
387
388 const char *end = find_end_quote (start + 1, *start);
389
390 if (end == NULL)
391 {
392 if (completion_info == NULL)
393 error (_("Unmatched quote, %s."), start);
394
395 end = start + strlen (start);
396 *inp = end;
397 return gdb::unique_xmalloc_ptr<char> (savestring (start + 1,
398 *inp - start - 1));
399 }
400
401 if (completion_info != NULL)
402 completion_info->quoted_arg_end = end;
403 *inp = end + 1;
404 return gdb::unique_xmalloc_ptr<char> (savestring (start + 1,
405 *inp - start - 2));
406 }
407
408 /* If the input starts with '-' or '+', the string ends with the next
409 whitespace or comma. */
410 if (*start == '-' || *start == '+')
411 {
412 while (*inp[0] != '\0' && *inp[0] != ',' && !isspace (*inp[0]))
413 ++(*inp);
414 }
415 else
416 {
417 /* Handle numbers first, stopping at the next whitespace or ','. */
418 while (isdigit (*inp[0]))
419 ++(*inp);
420 if (*inp[0] == '\0' || isspace (*inp[0]) || *inp[0] == ',')
421 return gdb::unique_xmalloc_ptr<char> (savestring (start,
422 *inp - start));
423
424 /* Otherwise stop at the next occurrence of whitespace, '\0',
425 keyword, or ','. */
426 *inp = start;
427 while ((*inp)[0]
428 && (*inp)[0] != ','
429 && !(isspace ((*inp)[0])
430 || linespec_lexer_lex_keyword (&(*inp)[1])))
431 {
432 /* Special case: C++ operator,. */
433 if (language->la_language == language_cplus
434 && startswith (*inp, CP_OPERATOR_STR))
435 (*inp) += CP_OPERATOR_LEN;
436 ++(*inp);
437 }
438 }
439
440 if (*inp - start > 0)
441 return gdb::unique_xmalloc_ptr<char> (savestring (start, *inp - start));
442
443 return NULL;
444 }
445
446 /* Return true if COMMA points past "operator". START is the start of
447 the line that COMMAND points to, hence when reading backwards, we
448 must not read any character before START. */
449
450 static bool
451 is_cp_operator (const char *start, const char *comma)
452 {
453 if (comma != NULL
454 && (comma - start) >= CP_OPERATOR_LEN)
455 {
456 const char *p = comma;
457
458 while (p > start && isspace (p[-1]))
459 p--;
460 if (p - start >= CP_OPERATOR_LEN)
461 {
462 p -= CP_OPERATOR_LEN;
463 if (strncmp (p, CP_OPERATOR_STR, CP_OPERATOR_LEN) == 0
464 && (p == start
465 || !(isalnum (p[-1]) || p[-1] == '_')))
466 {
467 return true;
468 }
469 }
470 }
471 return false;
472 }
473
474 /* When scanning the input string looking for the next explicit
475 location spec option/delimiter, we jump to the next option by looking
476 for ",", and "-". Such a character can also appear in C++ symbols
477 like "operator," and "operator-". So when we find such a
478 character, we call this function to check if we found such a
479 symbol, meaning we had a false positive for an option string. In
480 that case, we keep looking for the next delimiter, until we find
481 one that is not a false positive, or we reach end of string. FOUND
482 is the character that scanning found (either '-' or ','), and START
483 is the start of the line that FOUND points to, hence when reading
484 backwards, we must not read any character before START. Returns a
485 pointer to the next non-false-positive delimiter character, or NULL
486 if none was found. */
487
488 static const char *
489 skip_op_false_positives (const char *start, const char *found)
490 {
491 while (found != NULL && is_cp_operator (start, found))
492 {
493 if (found[0] == '-' && found[1] == '-')
494 start = found + 2;
495 else
496 start = found + 1;
497 found = find_toplevel_char (start, *found);
498 }
499
500 return found;
501 }
502
503 /* Assuming both FIRST and NEW_TOK point into the same string, return
504 the pointer that is closer to the start of the string. If FIRST is
505 NULL, returns NEW_TOK. If NEW_TOK is NULL, returns FIRST. */
506
507 static const char *
508 first_of (const char *first, const char *new_tok)
509 {
510 if (first == NULL)
511 return new_tok;
512 else if (new_tok != NULL && new_tok < first)
513 return new_tok;
514 else
515 return first;
516 }
517
518 /* A lexer for functions in explicit location specs. This function will
519 advance INP past a function until the next option, or until end of
520 string. Returns a malloc'd copy of the lexed string or NULL if no
521 lexing was done. */
522
523 static gdb::unique_xmalloc_ptr<char>
524 explicit_location_spec_lex_one_function
525 (const char **inp,
526 const struct language_defn *language,
527 explicit_completion_info *completion_info)
528 {
529 const char *start = *inp;
530
531 if (*start == '\0')
532 return NULL;
533
534 /* If quoted, skip to the ending quote. */
535 if (strchr (get_gdb_linespec_parser_quote_characters (), *start))
536 {
537 char quote_char = *start;
538
539 /* If the input is not an Ada operator, skip to the matching
540 closing quote and return the string. */
541 if (!(language->la_language == language_ada
542 && quote_char == '\"' && is_ada_operator (start)))
543 {
544 if (completion_info != NULL)
545 completion_info->quoted_arg_start = start;
546
547 const char *end = find_toplevel_char (start + 1, quote_char);
548
549 if (end == NULL)
550 {
551 if (completion_info == NULL)
552 error (_("Unmatched quote, %s."), start);
553
554 end = start + strlen (start);
555 *inp = end;
556 char *saved = savestring (start + 1, *inp - start - 1);
557 return gdb::unique_xmalloc_ptr<char> (saved);
558 }
559
560 if (completion_info != NULL)
561 completion_info->quoted_arg_end = end;
562 *inp = end + 1;
563 char *saved = savestring (start + 1, *inp - start - 2);
564 return gdb::unique_xmalloc_ptr<char> (saved);
565 }
566 }
567
568 const char *comma = find_toplevel_char (start, ',');
569
570 /* If we have "-function -myfunction", or perhaps better example,
571 "-function -[BasicClass doIt]" (objc selector), treat
572 "-myfunction" as the function name. I.e., skip the first char if
573 it is an hyphen. Don't skip the first char always, because we
574 may have C++ "operator<", and find_toplevel_char needs to see the
575 'o' in that case. */
576 const char *hyphen
577 = (*start == '-'
578 ? find_toplevel_char (start + 1, '-')
579 : find_toplevel_char (start, '-'));
580
581 /* Check for C++ "operator," and "operator-". */
582 comma = skip_op_false_positives (start, comma);
583 hyphen = skip_op_false_positives (start, hyphen);
584
585 /* Pick the one that appears first. */
586 const char *end = first_of (hyphen, comma);
587
588 /* See if a linespec keyword appears first. */
589 const char *s = start;
590 const char *ws = find_toplevel_char (start, ' ');
591 while (ws != NULL && linespec_lexer_lex_keyword (ws + 1) == NULL)
592 {
593 s = ws + 1;
594 ws = find_toplevel_char (s, ' ');
595 }
596 if (ws != NULL)
597 end = first_of (end, ws + 1);
598
599 /* If we don't have any terminator, then take the whole string. */
600 if (end == NULL)
601 end = start + strlen (start);
602
603 /* Trim whitespace at the end. */
604 while (end > start && end[-1] == ' ')
605 end--;
606
607 *inp = end;
608
609 if (*inp - start > 0)
610 return gdb::unique_xmalloc_ptr<char> (savestring (start, *inp - start));
611
612 return NULL;
613 }
614
615 /* See description in location.h. */
616
617 location_spec_up
618 string_to_explicit_location_spec (const char **argp,
619 const struct language_defn *language,
620 explicit_completion_info *completion_info)
621 {
622 /* It is assumed that input beginning with '-' and a non-digit
623 character is an explicit location. "-p" is reserved, though,
624 for probe locations. */
625 if (argp == NULL
626 || *argp == NULL
627 || *argp[0] != '-'
628 || !isalpha ((*argp)[1])
629 || ((*argp)[0] == '-' && (*argp)[1] == 'p'))
630 return NULL;
631
632 std::unique_ptr<explicit_location_spec> locspec
633 (new explicit_location_spec ());
634
635 /* Process option/argument pairs. dprintf_command
636 requires that processing stop on ','. */
637 while ((*argp)[0] != '\0' && (*argp)[0] != ',')
638 {
639 int len;
640 const char *start;
641
642 /* Clear these on each iteration, since they should be filled
643 with info about the last option. */
644 if (completion_info != NULL)
645 {
646 completion_info->quoted_arg_start = NULL;
647 completion_info->quoted_arg_end = NULL;
648 }
649
650 /* If *ARGP starts with a keyword, stop processing
651 options. */
652 if (linespec_lexer_lex_keyword (*argp) != NULL)
653 break;
654
655 /* Mark the start of the string in case we need to rewind. */
656 start = *argp;
657
658 if (completion_info != NULL)
659 completion_info->last_option = start;
660
661 /* Get the option string. */
662 gdb::unique_xmalloc_ptr<char> opt
663 = explicit_location_spec_lex_one (argp, language, NULL);
664
665 /* Use the length of the option to allow abbreviations. */
666 len = strlen (opt.get ());
667
668 /* Get the argument string. */
669 *argp = skip_spaces (*argp);
670
671 /* All options have a required argument. Checking for this
672 required argument is deferred until later. */
673 gdb::unique_xmalloc_ptr<char> oarg;
674 /* True if we have an argument. This is required because we'll
675 move from OARG before checking whether we have an
676 argument. */
677 bool have_oarg = false;
678
679 /* True if the option needs an argument. */
680 bool need_oarg = false;
681
682 /* Convenience to consistently set both OARG/HAVE_OARG from
683 ARG. */
684 auto set_oarg = [&] (gdb::unique_xmalloc_ptr<char> arg)
685 {
686 if (completion_info != NULL)
687 {
688 /* We do this here because the set of options that take
689 arguments matches the set of explicit location
690 options. */
691 completion_info->saw_explicit_location_spec_option = true;
692 }
693 oarg = std::move (arg);
694 have_oarg = oarg != NULL;
695 need_oarg = true;
696 };
697
698 if (strncmp (opt.get (), "-source", len) == 0)
699 {
700 set_oarg (explicit_location_spec_lex_one (argp, language,
701 completion_info));
702 locspec->source_filename = std::move (oarg);
703 }
704 else if (strncmp (opt.get (), "-function", len) == 0)
705 {
706 set_oarg (explicit_location_spec_lex_one_function (argp, language,
707 completion_info));
708 locspec->function_name = std::move (oarg);
709 }
710 else if (strncmp (opt.get (), "-qualified", len) == 0)
711 {
712 locspec->func_name_match_type = symbol_name_match_type::FULL;
713 }
714 else if (strncmp (opt.get (), "-line", len) == 0)
715 {
716 set_oarg (explicit_location_spec_lex_one (argp, language, NULL));
717 *argp = skip_spaces (*argp);
718 if (have_oarg)
719 {
720 locspec->line_offset = linespec_parse_line_offset (oarg.get ());
721 continue;
722 }
723 }
724 else if (strncmp (opt.get (), "-label", len) == 0)
725 {
726 set_oarg (explicit_location_spec_lex_one (argp, language,
727 completion_info));
728 locspec->label_name = std::move (oarg);
729 }
730 /* Only emit an "invalid argument" error for options
731 that look like option strings. */
732 else if (opt.get ()[0] == '-' && !isdigit (opt.get ()[1]))
733 {
734 if (completion_info == NULL)
735 error (_("invalid explicit location argument, \"%s\""), opt.get ());
736 }
737 else
738 {
739 /* End of the explicit location specification.
740 Stop parsing and return whatever explicit location was
741 parsed. */
742 *argp = start;
743 break;
744 }
745
746 *argp = skip_spaces (*argp);
747
748 /* It's a little lame to error after the fact, but in this
749 case, it provides a much better user experience to issue
750 the "invalid argument" error before any missing
751 argument error. */
752 if (need_oarg && !have_oarg && completion_info == NULL)
753 error (_("missing argument for \"%s\""), opt.get ());
754 }
755
756 /* One special error check: If a source filename was given
757 without offset, function, or label, issue an error. */
758 if (locspec->source_filename != NULL
759 && locspec->function_name == NULL
760 && locspec->label_name == NULL
761 && (locspec->line_offset.sign == LINE_OFFSET_UNKNOWN)
762 && completion_info == NULL)
763 {
764 error (_("Source filename requires function, label, or "
765 "line offset."));
766 }
767
768 return location_spec_up (locspec.release ());
769 }
770
771 /* See description in location.h. */
772
773 location_spec_up
774 string_to_location_spec_basic (const char **stringp,
775 const struct language_defn *language,
776 symbol_name_match_type match_type)
777 {
778 location_spec_up locspec;
779 const char *cs;
780
781 /* Try the input as a probe spec. */
782 cs = *stringp;
783 if (cs != NULL && probe_linespec_to_static_ops (&cs) != NULL)
784 {
785 locspec = new_probe_location_spec (*stringp);
786 *stringp += strlen (*stringp);
787 }
788 else
789 {
790 /* Try an address location spec. */
791 if (*stringp != NULL && **stringp == '*')
792 {
793 const char *arg, *orig;
794 CORE_ADDR addr;
795
796 orig = arg = *stringp;
797 addr = linespec_expression_to_pc (&arg);
798 locspec = new_address_location_spec (addr, orig, arg - orig);
799 *stringp += arg - orig;
800 }
801 else
802 {
803 /* Everything else is a linespec. */
804 locspec = new_linespec_location_spec (stringp, match_type);
805 }
806 }
807
808 return locspec;
809 }
810
811 /* See description in location.h. */
812
813 location_spec_up
814 string_to_location_spec (const char **stringp,
815 const struct language_defn *language,
816 symbol_name_match_type match_type)
817 {
818 const char *arg, *orig;
819
820 /* Try an explicit location spec. */
821 orig = arg = *stringp;
822 location_spec_up locspec
823 = string_to_explicit_location_spec (&arg, language, NULL);
824 if (locspec != nullptr)
825 {
826 /* It was a valid explicit location. Advance STRINGP to
827 the end of input. */
828 *stringp += arg - orig;
829
830 /* If the user really specified a location spec, then we're
831 done. */
832 if (!locspec->empty_p ())
833 return locspec;
834
835 /* Otherwise, the user _only_ specified optional flags like
836 "-qualified", otherwise string_to_explicit_location_spec
837 would have thrown an error. Save the flags for "basic"
838 linespec parsing below and discard the explicit location
839 spec. */
840 explicit_location_spec *xloc
841 = gdb::checked_static_cast<explicit_location_spec *> (locspec.get ());
842 match_type = xloc->func_name_match_type;
843 }
844
845 /* Everything else is a "basic" linespec, address, or probe location
846 spec. */
847 return string_to_location_spec_basic (stringp, language, match_type);
848 }