Clean up of get_function_name

Have it return a real string, instead of a pointer with uncertain
lifetime.
This commit is contained in:
ridiculousfish 2021-07-15 11:21:32 -07:00
parent bad1b84513
commit ccd1b4e4f4
4 changed files with 23 additions and 32 deletions

View File

@ -433,10 +433,11 @@ static int parse_cmd_opts(argparse_cmd_opts_t &opts, int *optind, //!OCLINT(hig
if (opts.name.empty()) {
// If no name has been given, we default to the function name.
// If any error happens, the backtrace will show which argparse it was.
const wchar_t *fn = parser.get_function_name(1);
if (!fn) fn = L"argparse";
opts.name = fn;
if (maybe_t<wcstring> fn = parser.get_function_name(1)) {
opts.name = fn.acquire();
} else {
opts.name = L"argparse";
}
}
*optind = w.woptind;

View File

@ -381,10 +381,8 @@ maybe_t<int> builtin_status(parser_t &parser, io_streams_t &streams, const wchar
}
case STATUS_FUNCTION: {
CHECK_FOR_UNEXPECTED_STATUS_ARGS(opts.status_cmd)
const wchar_t *fn = parser.get_function_name(opts.level);
if (!fn) fn = _(L"Not a function");
streams.out.append_format(L"%ls\n", fn);
maybe_t<wcstring> fn = parser.get_function_name(opts.level);
streams.out.append_format(L"%ls\n", fn ? fn->c_str() : _(L"Not a function"));
break;
}
case STATUS_LINE_NUMBER: {

View File

@ -412,26 +412,19 @@ wcstring parser_t::stack_trace() const {
return trace;
}
/// Returns the name of the currently evaluated function if we are currently evaluating a function,
/// NULL otherwise. This is tested by moving down the block-scope-stack, checking every block if it
/// is of type FUNCTION_CALL. If the caller doesn't specify a starting position in the stack we
/// begin with the current block.
const wchar_t *parser_t::is_function() const {
bool parser_t::is_function() const {
for (const auto &b : block_list) {
if (b.is_function_call()) {
return b.function_name.c_str();
return true;
} else if (b.type() == block_type_t::source) {
// If a function sources a file, obviously that function's offset doesn't
// contribute.
// If a function sources a file, don't descend further.
break;
}
}
return nullptr;
return false;
}
/// Return the function name for the specified stack frame. Default is zero (current frame).
/// The special value zero means the function frame immediately above the closest breakpoint frame.
const wchar_t *parser_t::get_function_name(int level) {
maybe_t<wcstring> parser_t::get_function_name(int level) {
if (level == 0) {
// Return the function name for the level preceding the most recent breakpoint. If there
// isn't one return the function name for the current level.
@ -441,13 +434,10 @@ const wchar_t *parser_t::get_function_name(int level) {
if (b.type() == block_type_t::breakpoint) {
found_breakpoint = true;
} else if (found_breakpoint && b.is_function_call()) {
return b.function_name.c_str();
return b.function_name;
}
}
return nullptr; // couldn't find a breakpoint frame
} else if (level == 1) {
// Return the function name for the current level.
return this->is_function();
return none(); // couldn't find a breakpoint frame
}
// Level 1 is the topmost function call. Level 2 is its caller. Etc.
@ -456,11 +446,15 @@ const wchar_t *parser_t::get_function_name(int level) {
if (b.is_function_call()) {
funcs_seen++;
if (funcs_seen == level) {
return b.function_name.c_str();
return b.function_name;
}
} else if (b.type() == block_type_t::source && level == 1) {
// Historical: If we want the topmost function, but we are really in a file sourced by a
// function, don't consider ourselves to be in a function.
break;
}
}
return nullptr; // couldn't find that function level
return none();
}
int parser_t::get_lineno() const {

View File

@ -282,10 +282,8 @@ class parser_t : public std::enable_shared_from_this<parser_t> {
/// Adds a job to the beginning of the job list.
void job_add(shared_ptr<job_t> job);
/// Returns the name of the currently evaluated function if we are currently evaluating a
/// function, null otherwise. This is tested by moving down the block-scope-stack, checking
/// every block if it is of type FUNCTION_CALL.
const wchar_t *is_function() const;
/// \return whether we are currently evaluating a function.
bool is_function() const;
/// Create a parser.
parser_t();
@ -394,7 +392,7 @@ class parser_t : public std::enable_shared_from_this<parser_t> {
static const wchar_t *get_block_desc(block_type_t block);
/// Return the function name for the specified stack frame. Default is one (current frame).
const wchar_t *get_function_name(int level = 1);
maybe_t<wcstring> get_function_name(int level = 1);
/// Promotes a job to the front of the list.
void job_promote(job_t *job);