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