What's the best way to use "--all-files" option from python?

The only way I’ve been able to do it is by using the CommandInterpreter, i.e.,

res = lldb.SBCommandReturnObject()
lldb.debugger.GetCommandInterpreter().HandleCommand(‘breakpoint set -p “diag::%s” --all-files -N %s’ % (name, name), res);
lldb.debugger.GetCommandInterpreter().HandleCommand(‘breakpoint disable %s’ % name, res);

Is this the best way to do it? Can’t seem to figure out how to use SBTarget.BreakpointCreateBySourceRegex() for all files.

thanks…
don

Just pass an invalid FileSpec for the source file spec, like:

lldb.target.BreakpointCreateBySourceRegex("printf", lldb.SBFileSpec())

and it acts the same way as the --all-files option. That was pretty non-obvious, I'll update the docs.

Actually, the thing you CAN'T do is get the command line behavior where lldb uses the "default file" i.e. when you run "break set -p" but don't supply a file or the --all-files option. That seemed to me less useful for a programming interface since the default file is history dependent (it's the file with "main" in it before you run, then it's where you last set a breakpoint, or where you last stopped, etc.) If you needed this behavior it would be better to have the target vend the default file, though right now that's really only maintained by the breakpoint command...

Jim

Ah, great, thanks. I just figured the default was the same for both.

Just wish I could use a regex for the filename as well, which would cut down the number of files about about half.

thanks again…
don

Yeah, that would be easy to implement from the command line, maybe add a --file-is-regex flag or something.

From the SB API it would be better to have something like:

SBFileList SBTarget.GetFileListMatchingRegex("regex")

Please file an enhancement request for these of hack'em in if you're so motivated.

Jim

Will do…

thanks again…

It might be worth brainstorming if there’s ways to do this that are both intuitive and don’t require more options. As a command line user, I really value my keystrokes.

One idea would be to use a syntax that matches that of the ‘-name’ option to the standard ‘find’ utility. This way filename pattern matching would work in a way familiar to almost everyone, no sb api options would need to be added.

Do you mean just pass a pattern to the -f option or FileSpec?

Pass a pattern to the -f option.

I’d also like to include the path in the pattern, e.g., -f “/clang/”, which would cut the number of files examined by about half for my use case.

Are glob characters legal file characters on any systems? If so we can’t do the auto detect where we override the meaning of -f. If not, then we can. We could add a --glob option that goes along with the -f option if glob characters are valid file system characters.

There are a few breakpoint options that aren’t available via the lldb::SB API layer. Not skipping the prologue for breakpoints by name and regex is one of them.

It would be nice to follow other examples where we make a options class that has nice defaults and get sent to each breakpoint kind.

The current API is:

lldb::SBBreakpoint BreakpointCreateByName(const char *symbol_name,
const char *module_name = nullptr);

// This version uses name_type_mask = eFunctionNameTypeAuto
lldb::SBBreakpoint
BreakpointCreateByName(const char *symbol_name,
const SBFileSpecList &module_list,
const SBFileSpecList &comp_unit_list);

With a breakpoint options class we would add:

lldb::SBBreakpoint
BreakpointCreateByName(const char *symbol_name,
lldb::SBBreakpointOptions &options);

Then we can make SBBreakpointOptions be able to set any kinds of filters we want.

The missing things that come to mind are:

  • don’t skip prologue
  • don’t set inlined breakpoints (concrete only) (this is missing in the command line interface as well)
  • limiting to certain files or shared libraries (only available on some SBTarget::BreakpointCreateXXX() functions)
  • thread specific settings
  • hit count
  • skip count
  • setting condition on breakpoint right away instead of making another API call

All unix systems accept '*' as file names. In fact, the only system I
know of, where that is not a legal filename is windows.

Right, but you can still escape it no? You face the same issue with find . -name "*". That’s going to find everything. This is just optimizing usability for the common case. Because it’s pretty rare case to want to search for literal *, extremely common to want to search for wildcard stars, and everyone is already familiar with the way you get around it and force a search for a literal *

I have only one reservation to this plan, which is that at present I only have one breakpoint command that shares a common set of command options. So if we start overloading the meaning of -f, meaning a file in the case of file & line breakpoints and a restriction glob pattern for source regex breakpoints, then it makes command help & completion work poorly. OTOH, I have no problem with -f meaning something different for "-r" breakpoints and "-f, -l" breakpoints.

Not really sure how to do this better. I don't think anybody would like:

(lldb) break set-file
(lldb) break set-regex
(lldb) break set-address

But that's currently the only way you could start to tease these things apart.

Jim

err, we were actually talking about "-p" breakpoints here...

Jim

Are glob characters legal file characters on any systems? If so we can't do the auto detect where we override the meaning of -f. If not, then we can. We could add a --glob option that goes along with the -f option if glob characters are valid file system characters.

There are a few breakpoint options that aren't available via the lldb::SB API layer. Not skipping the prologue for breakpoints by name and regex is one of them.

It would be nice to follow other examples where we make a options class that has nice defaults and get sent to each breakpoint kind.

The current API is:

  lldb::SBBreakpoint BreakpointCreateByName(const char *symbol_name,
                                            const char *module_name = nullptr);

  // This version uses name_type_mask = eFunctionNameTypeAuto
  lldb::SBBreakpoint
  BreakpointCreateByName(const char *symbol_name,
                         const SBFileSpecList &module_list,
                         const SBFileSpecList &comp_unit_list);

With a breakpoint options class we would add:

  lldb::SBBreakpoint
  BreakpointCreateByName(const char *symbol_name,
                         lldb::SBBreakpointOptions &options);

Then we can make SBBreakpointOptions be able to set any kinds of filters we want.

The missing things that come to mind are:
- don't skip prologue
- don't set inlined breakpoints (concrete only) (this is missing in the command line interface as well)
- limiting to certain files or shared libraries (only available on some SBTarget::BreakpointCreateXXX() functions)
- thread specific settings
- hit count
- skip count
- setting condition on breakpoint right away instead of making another API call

I have no problem with this in general, but I don't want to have a single options class.

I want to keep the distinction between "things you can pass to a breakpoint that change what locations are set" and "things that you can pass to the breakpoint that change what you do when you hit a breakpoint". First off, keeping them separate avoid any confusion about what you can & can't change. You get read-only access to a breakpoint's setting options (maybe call these SBBreakpointSetOptions). But you get read-write access to the normal options, for instance.

So in the list above, the first 5 options can be done when setting breakpoints, but effect what locations you chose so currently can't be done after the fact. And even if we start allowing them after the fact they should stay separate because they add or remove locations, so are a very different kind of setting than the current SBBreakpointOptions. The last three are SBBreakpointOptions.

In this context, we'd add a "RestrictFilePattern" option. In the case of symbol name breakpoints it would restrict you to that symbol in this source file. In the source regex case we could use it as well as a list (sometimes a pattern is more annoying to generate than a list so we'd want both.) Even for file & line breakpoints, you want to say "set the breakpoint on the instances of SomeHeader.h, line 20 inlined INTO SomeFile.cpp". So it could have that meaning.

Doing this would mean we'd have to add one more API to all the setters,

BreakpointCreateByName(const char *symbol_name,
           lldb::SBBreakpointSetOptions &set_options,
                       lldb::SBBreakpointOptions &options);

But that seems to me still a fairly natural API, and maintains an important distinction.

Note, that on the SBBreakpointOptions front, I recently added the ability to make a set of "breakpoint reactions" independently of any breakpoint, and then applying them to breakpoints either before or after they've been made. That seems to me a useful feature. That's what the "breakpoint names configure" command I recently added does. With it you can do:

(lldb) breakpoint name configure -c "something == something_else" -C "bt" -C "frame var" MyOptions
(lldb) break set -f whatever -l 5 -N MyOptions

and it picks up the options from MyOptions. You can even play around with the sets live, changing the configuration of MyOptions changes the behavior of the breakpoints using the name. Part of the reason for doing this is that it provides a venue for us to publicize any fancy breakpoint commands and other stop reactions we can come up with, because we can make them built in lldb names, they will show up in "breakpoint name list" - the names can have help strings so we can explain what they do...

But the setting options are a different. You can see passing the same file restrict or shlib restrict list as you make them, but if you were to change it after the fact it would have a very different effect, changing where the stops are made, than do what we currently call the options do.

Jim