microsoft / debug-adapter-protocol Goto Github PK
View Code? Open in Web Editor NEWDefines a common protocol for debug adapters.
Home Page: https://microsoft.github.io/debug-adapter-protocol/
License: Other
Defines a common protocol for debug adapters.
Home Page: https://microsoft.github.io/debug-adapter-protocol/
License: Other
When should a debugger use the ExitedEvent
vs the TerminatedEvent
? The PowerShell debugger is launched (it doesn't support attach yet) but we are sending a TerminatedEvent
at the end which apparently causes the client to send us a disconnectRequest
which is a bit odd. We don't respond to this message because we are in the middle of shutting the debug host down. This results (sometimes) in a Error Canceled
popup. It seems to happen when we pause/resume the debugger.
If I switch that to use the ExitedEvent
we don't get the disconnectRequest
message but the client pops a new error Error Debug adapter process has terminated unexpectedly
. And if the program was paused and resumed it also pops up Error Canceled
.
Currently the debug protocol has no way for a debug adapter to request that the IDE open up a web browser. Some debug adapters, such as the C# debug adapter, can start a web browser as part of launching a web server project. The debug adapter needs some control to be able to signal when the web server is ready.
This could either be designed as an event (ex: WebServerReady) or as a callback request like starting processes in the terminal.
Dependent issue: dotnet/vscode-csharp#2657
Related issue: microsoft/vscode-debugadapter-node#153
The Language Server Protocol specification provides a change log, which is helpful to see the progress and to have points of reference when an implementation targets a specific version. Currently, the Debug Adapter Protocol specification does not have this.
I see that it was tracked in the old repo's README, so it should be fairly simple to add.
We propose that adapters can present a set of CPU registers to the frontend by returning an additional scope in response to the scopes
request. The name of this scope would be provided in the adapter's Capabilities
to support frontends such as VS that show registers in a separate window. This allows adapters to localize the scope's name for display in VSCode while still allowing VS to find it:
export interface Capabilities {
// ....
/** Name of the scope that contains register variables. */
registersScopeName?: string;
}
In the simplest form, the scope would contain one variable for each register, e.g.:
Additionally, VS supports categorization of registers, and allows individual categories to be shown / hidden. This could be supported via nesting, where the intermediate level variable provides the category name and contains the actual register values as children, e.g.:
CC: @gregg-miskelly
These values have special meaning, and should be part of the protocol.
/** The reason for the event.
Values: 'changed', 'new', 'removed', etc.
*/
reason: string;
Some debuggers (WinDbg is a good example) support a command to display information for a particular type. dt ntdll!_PEB
. It would be nice if DAP supported a similar request, as this is a not-uncommon "power feature" in debuggers.
The main complicating factor here is that types can be pretty complicated, so there is the question of whether it is worth designing a serialization format for them and what granularity of information you wish to report (for example, would it only be sufficient for dumping a high-level representation of the type, or would it be sufficient for reconstructing an accurate AST?).
From @indiejames on April 30, 2016 3:35
The debug protocol identifies threads with a unique number
, but in some languages (e.g., on the JVM) threads are identified by names using a string. It would be more flexible if the debug protocol used any
instead of number
to reference threads.
Copied from original issue: microsoft/vscode#6006
The debug adapter protocol is independent from VS Code and contains quite a few features that are not implemented in VS Code but exist in VS or VS for Mac.
In the VS Code release notes you always try to clearly state whether a new DAP feature is implemented in VS Code or not.
But it is difficult to review all release notes to find if a feature of the DAP is implemented or not.
For now the only way I see is to test the feature and see if it does something. But when it doesn't I'm not sure if the feature is not implemented or if I misuse the DAP.
Maybe some labels like "VSCode-only" or "VS-only" in the DAP documentation could help developers what is available for the IDE they target ?
In your json, you have responses simply as extending generic response + description, which is incorrect because response has to have same command value as request. So it should be marked in same was as responses are, ie with constant enum for command. What I would propose is to fix those to this:
"LaunchResponse": {
"allOf": [ { "$ref": "#/definitions/Response" }, {
"type": "object",
"description": "Response to 'launch' request. This is just an acknowledgement, so no body field is required.",
"properties": {
"command": {
"type": "string",
"enum": [ "launch" ]
}
},
"required": [ "command" ]
}]
}
see microsoft/vscode-debugadapter-node#58 for details why JSON RPC hasn't been used from the beginning.
Nuclide has a "readOnlyTarget" capability flag which disables some unsupported features of the debugger, for debugging static dumps. This should exist in the debug protocol too.
Instead of a master flag like "readOnlyTarget", we would prefer more specific flags for individual features. But capabilities usually enable features, not disable them, and it seems weird to have a flag like supportsStepping
which must be set 99% of the time.
Which features are disabled by this flag? Do you think there would be different features supported in different situations (so they'd need to be disabled on a more granular level)?
VS docs: https://msdn.microsoft.com/en-us/library/d5zhxt22.aspx
I work on lldb and would like to provide functionality for lldb to be handed a pty slave and then attach it's standard command interpreter. Note that we'd like this functionality in addition to the Debug Console
prompt as that is only used for expression evaluation.
Within lldb-vscode, we just offer the user to prefix their Debug Console
input with a literal backtick to pass the command to the CommandInterpreter
class. This is a clumsy work around. It lacks completion, history, and the rest of the editline/readline repertoire that command line users are used to.
A temporary workaround I've done is to just launch lldb-vscode
in the terminal and attach the CommandInterpreter
to the standard stdin/out/err
pty slave and then listen to the DAP communication over a socket connection. But this is just another clumsy workaround.
We envision the server responding to initialize
with supportsAttachingCommandInterpreter: true
or a similar packet to which the client would respond by doing the ptyopen
dance and handing the slave to the server via commandInterpreterPty: "/dev/pty0123"
and then opening a new terminal emulator attached to the master. The server could then open("/dev/pty0123", "rw");
and dup
to stdout
and stderr
to have a full fidelity command line debugging experience on top of the lovely integrated GUI experience.
Debugger client shell be able to manage debugging session state to support remote debugging:
Use case 1: developer starts debugging session but wishes to start communication with debugger server only when either main thread is started or 1st break
point is reached.
Use case 2: debugging session has lead to undesired results and developer wishes to abort debugging
Use case 3: mutation of application state by developer resulted in undesired results and developer wishes to restore initial application state and re-start debugging session without re-opening UI and going through initialization phase - neither server nor client capabilities changed.
Development tools supporting remote debugging like Java and Chrome debuggers support this functionality.
The specification does not define when variablesReference
numbers become invalid and when previously used numbers can be used again without adverse or unexpected consequences.
As of 4102c79 the specification for logMessage
is lacking in detail on how to parse the attribute
If this attribute exists and is non-empty, the backend must not 'break' (stop) but log the message instead. Expressions within {} are interpolated.
For some languages it is quite normal for expressions to include the {
and }
delimiters, in Perl for instance you might want to log
Value of key field in hash is {$hash{key}} # ?
I would expect either \
-escaping or actually configurable delimiters. For Perl it might be better to use backticks instead of curly braces, for instance, in which case the specification should allow implementations to vary on that point.
I'm writing a debug adapter for a Z80 emulator. I would like to change some variables (e.g. memory or register values) at the emulator and then display the result in vscode. Currently I have put the registers in the VARIABLES area and on every step-over (next) vscode sends a variable request to get the variables updated. That works fine.
But how should it work if e.g. the debugger is paused and then a register value is changed manually at the emulator.
I would like to inform vscode about the new value but there doesn't seem to be any API for this.
Every update request is initated from vscode as it seems. Or am I missing something?
Right now, there is no way to grab subsource code, for instance compiled bytecode for bytecode stepping granularity.
Hi,
I was trying to read the vscode.debug.breakpoints array from the launchRequest method.
But unfortunately the array is defined but empty even if breakpoints are set in the sources.
Additional info: If I access the same array from the restartRequest the array is filled with all breakpoints.
The following link in the README is broken:
https://github.com/Microsoft/debug-adapter-protocol/blob/gh-pages/debugProtocol.json
The spec just says that all IDs are number
s - which is to say, 64-bit floats. It does not say much about how they should be compared, including weird cases like NaN
or positive/negative zero, which are seemingly legal.
In practice it seems that protocol clients have much more stringent limitations - for example, VS uses 32-bit integers internally for many IDs, and is unable to cope with any number that doesn't fit. It would be nice to reflect it in the spec itself, limiting the values to some sane subset that all current implementations support in practice (e.g. int32 > 0
?).
We should support additional details for Threads, including a presentationHint
, like on StackFrame.
Visual Studio shows several pieces of information for each thread: https://msdn.microsoft.com/en-us/library/w15yf86f.aspx
Maybe we reuse ColumnDescriptor
from Module for clients that want to support arbitrary thread details in a grid?
This proposal covers both disassembly and memory access, since they both depend on the same underlying primitive - a "memory reference".
A memory reference is an opaque identifier that can be used (along with an optional byte offset) to identify a single location in memory. An adapter has the option of providing a memory reference on several protocol objects that represent things a frontend might want to display in a memory view or use as a starting point for disassembly:
export interface EvaluateResponse {
// ...
/** Memory reference to an adapter-determined location appropriate for this result. For pointer types, this is generally a reference to the memory address contained in the pointer. */
memoryReference?: string;
}
export interface Variable {
// ...
/** Memory reference for the variable if the variable represents executable code, such as a function pointer. */
memoryReference?: string;
}
export interface StackFrame {
// ...
/** Memory reference for the current instruction pointer in this frame. */
instructionPointerReference?: string;
}
export interface GotoTarget {
// ...
/** Memory reference for the instruction pointer value represented by this target. */
instructionPointerReference?: string;
}
Memory references are expressed as strings rather than numbers because the most common implementation will likely be to use the address directly, and a 64-bit memory address will not fit in a JSON number.
Reading memory from a location represented by a memory reference and offset is accomplished via a new readMemory
request:
export interface Capabilities {
// ...
/** The debug adapter supports the 'readMemory' request. */
supportsReadMemoryRequest?: boolean;
}
/** Reads bytes from memory at the provided location. */
export interface ReadMemoryRequest extends Request {
// command: 'readMemory'
arguments: ReadMemoryArguments;
}
/** Arguments for 'readMemory' request. */
export interface ReadMemoryArguments {
/** Memory reference to the base location from which data should be read. */
memoryReference: string;
/** Optional offset (in bytes) to be applied to the reference location before reading data. Can be negative. */
offset?: number;
/** Number of bytes to read at the specified location and offset. */
count: number;
}
/** Response to 'readMemory' request. */
export interface ReadMemoryResponse extends Response {
body: {
/** The address of the first byte of data returned. Treated as a hex value if prefixed with '0x', or as a decimal value otherwise. */
address: string;
/** The number of unreadable bytes encountered after the last successfully read byte. This can be used to determine the number of bytes that must be skipped before a subsequent 'readMemory' request will succeed. */
unreadableBytes?: number;
/** The bytes read from memory, encoded using base64. **/
data: string;
}
}
Note that the read memory request should be considered to have succeeded even if none of the requested bytes are available. For instance, a read might extend into a page that is not mapped - in this case, the adapter would be expected to return the bytes it could read (if any), along with a value for unreadableBytes
that can be used to skip the unmapped page.
Additionally, it is intended that a zero-byte read (that is, a readMemory
request with a count
of zero) could be used to determine the actual address identified by the memory reference and offset.
Disassembling code at a location represented by a memory reference is accomplished via a new disassemble
request:
export interface Capabilities {
// ...
/** The debug adapters supports the 'disassemble' request. */
supportsDisassembleRequest?: boolean;
}
/** Disassembles code stored at the provided location. */
export interface DisassembleRequest extends Request {
// command: 'disassemble'
arguments: DisassembleArguments;
}
/** Arguments for 'disassemble' request. */
export interface DisassembleArguments {
/** Memory reference to the base location containing the instructions to disassemble. */
memoryReference: string;
/** Optional offset (in bytes) to be applied to the reference location before disassembling. Can be negative. */
offset?: number;
/** Optional offset (in instructions) to be applied after the byte offset (if any) before disassembling. Can be negative. */
instructionOffset?: number;
/** Number of instructions to disassemble starting at the specified location and offset. An adapter must return exactly this number of instructions - any unavailable instructions should be replaced with an implementation-defined 'invalid instruction' value. */
instructionCount: number;
/** If true, the adapter should attempt to resolve memory addresses and other values to symbolic names. */
resolveSymbols?: boolean;
}
/** Response to 'disassemble' request */
export interface DisassembleResponse extends Response {
body: {
/** The list of disassembled instructions. */
instructions: DisassembledInstruction[];
}
}
/** Represents a single disassembled instruction. */
export interface DisassembledInstruction {
/** The address of the instruction. Treated as a hex value if prefixed with '0x', or as a decimal value otherwise. */
address: string;
/** Raw bytes representing the instruction and its operands, in an implementation-defined format. */
instructionBytes?: string;
/** Text representing the instruction and its operands, in an implementation-defined format. */
instruction: string;
/** Name of the symbol that correponds with the location of this instruction, if any. */
symbol?: string;
/** Source location that coresponds to this instruction, if any. Should always be set (if available) on the first instruction returned, but can be omitted afterwards if this instruction maps to the same source file as the previous instruction. */
location?: Source;
/** The line within the source location that corresponds to this instruction, if any. */
line?: number;
/** The column within the line that corresponds to this instruction, if any. */
column?: number;
/** The end line of the range that corresponds to this instruction, if any. */
endLine?: number;
/** The end column of the range that corresponds to this instruction, if any. */
endColumn?: number;
}
The location
, line
, column
, endLine
and endColumn
members on DisassembledInstruction
are intended to provide a mapping between a disassembled instruction and the source code it was generated from, if this information is available to the adapter.
A debugger UI that implements this proposal will likely want to display addresses differently for 32-bit vs 64-bit processes. This information would be conveyed via an additional property on the process
event:
export interface ProcessEvent extends Event {
// ...
/** The size of a pointer or address for this process, in bits. */
pointerLength?: number;
}
CC: @gregg-miskelly
For details see microsoft/vscode#45683
It seems to me, after guessing and experiments with some debug adapters, that Variable.value
is supposed to hold a string that can be evaluated (in some unspecified context) to some approximately equivalent value. So, when the value is the 4-letter string null
, it is supposed to be something like "null"
.
The specification completely fails to discuss that, and existing debug adapters implement this improperly, including Microsoft's own debug adapters. For instance, when debugging typescript, and my variable holds a string that contains quote marks, they are not escaped. Consequently, when I right click the variable, select »Set Value«, and want to append a single character, I may have to go through the whole string to manually escape quote marks and possibly other characters, to make up an expression that can be evaluated.
Likewise, the specification never says for setVariable
that the value
is actually not a value but an expression that ought to be evaluated in the context of the variablesReference
first, before modifying the variable.
The specification should call this out explicitly, including the need to escape values properly, and probably ought to link Variables
requests semantically to SetVariable
requests (values from a response to the former should be valid input to the latter, with the general expectation that setting a variable to the value reported by the Variables
request, does not change the value or its properties like its type).
From @vadimcn on August 5, 2016 19:43
The new setVariable
request identifies variables by display name.
This is fragile because the name may have been generated by the adapter (e.g. [N]
for array indices).
There may also be more than one variable with the same name in the stack frame in languages that allow variable shadowing. For example, in C++ one can write
int a = 10;
{
int a = 20;
... // There are now two `a`'s here!
The debugger can see both, even though in C++ there's no way to access the outer one.
To make this work robustly, I would suggest adding an optional "handle" field into Variable
, which gets round-tripped back to the adapter in setVariable
.
Copied from original issue: microsoft/vscode#10219
https://github.com/Microsoft/vscode-debugadapter-node/wiki/VS-Code-Debug-Protocol-Implementations
I have joined the maintenance of the unity debugger extension: https://marketplace.visualstudio.com/items?itemName=Unity.unity-debug. Would it be possible to get me added to the name tags? I can see that @weinand was maintaining it.
Also the repository link can be added https://github.com/Unity-Technologies/vscode-unity-debug
I propose to clarify Debug Adapter protocol definition and add words "High level language" It will prevent protocol features inflation by features like "Arm processor register reading" or "Display content of nVidea GPU memory".
Any high level language is abstraction and debugger UI has its own abstraction: it has stack pane, global and local variables pane, breakpoints pane, variable watch pane, hosted editor pane to display and navigate through source code, Server can order source coding modification via passing editor commands. Command pane and message pane are displayed bellow. Callouts and Popup windows can appear to display requests results. Hoover over source code tokens produces events which trigger requests to server. Module source opening, code changes, save, etc are reported to the server as didOpened, didModified, didSaved notifications. Server notifies. UI in the cases when intermediate processing results should be reflected by UI immediately.
Expected UI behavior should be explained in implementation notes if it is self explainable like it is done in LSP protocol definition. These notes are used for future Debugger UI implementors. Nothing is assumed!
The specification does not define the lifetime of a GotoTarget
as obtained from a given GotoTargetsRequest
, so it is unclear if it's legal for an IDE to cache them and reuse them later (possibly across goto
, across continue
, or in different frames that just happen to use the same source), or whether the adapter can clean up associated resources more aggressively - e.g. on invalidate them on every goto
.
It's also unclear whether the adapter can return different IDs for the same file/line on a subsequent request, even if it ensures that old IDs are still valid to use in goto
- and if it can do so, then how should the IDE interpret this.
Add notifications used in remote debuggers and Cloud applications debuggers
They are used for debugging of application deployed to production cloud infrastructure
I work on the PowerShell debug adapter and that adapter provides a REPL while debugging. In the PowerShell Integrated Console during debugging, a user can use a PowerShell command Set-PSBreakpoint
to set both line and function breakpoints. On the line breakpoints we can use the BreakpointEvent to communicate this back to VSCode;
However I'm not finding an equivalent event for function breakpoints. What am I missing? Or is this missing from the debug protocol?
"Continue" currently says that if it can't continue just one thread, it should continue all threads.
The protocol shouldn't specify a fallback on different behavior - instead the continue request should fail, while a continue request without a threadID should mean "continue all threads".
I agree that the fallback semantics is a bad idea. Please file DAP protocol bug for this.
But please note that it might be impossible to fix this in the current version of the DAP in a non-breaking way.
Currently, the protocol allows the debug adapter to respond to a SetBreakpoints request with a response that contains a Breakpoint (https://github.com/Microsoft/vscode-debugadapter-node/blob/master/protocol/src/debugProtocol.ts#L1462)
Breakpoint, if representing a Verified breakpoint, has a single notion of the breakpoint's resolved location. But for many debug adapters, a single breakpoint might actually resolve to n locations. This is especially true for native debuggers where a function in a header file might be inlined all over the program.
The debug adapter can maintain this mapping internally and not share it with the UX, but then the user can't accurately see the location(s) a breakpoint resolved to.
Would it be possible to add something like an optional array of resolved locations to Breakpoint? Maybe something like:
export interface BreakpointLocation {
/** The source where the breakpoint is located. */
source?: Source;
/** The start line of the actual range covered by the breakpoint. */
line?: number;
/** An optional start column of the actual range covered by the breakpoint. */
column?: number;
/** An optional end line of the actual range covered by the breakpoint. */
endLine?: number;
/** An optional end column of the actual range covered by the breakpoint. If no end line is given, then the end column is assumed to be in the start line. */
endColumn?: number;
}
From @vadimcn on August 5, 2016 19:11
When a debug adapter reports that is supports setVariable, all leaf variables become editable, but compound objects do not. While a reasonable heuristic, this is not optimal because:
I'd suggest adding an explicit "settable" flag into Variable
.
Copied from original issue: microsoft/vscode#10217
Some clients display the breakpoint hit count, as a number next to the breakpoint decoration. Especially useful with hitCondition. We could use BreakpointEvent for this.
Enhancement request raised as a result of microsoft/vscode#61640
Apparently it is not possible for the response from RunInTerminalRequest to return in the (optional) processId value the PID in which the requested command was executed. I would like a new return value shellProcessId that gives us the PID of the shell. In some circumstances we may be able derive the command PID from that.
Looking at our protocol the breakpoint.id
is optional here
However when sending a changed
BreakpointEvent
it is required as there is no other way for us to identify the breakpoint. So it should not be defined as optional in that case
Currently GotoTargetsArguments
provides only source
, line
, and column
. This is not enough to identify if a given line is valid for the user to move there. It should have threadId
as an argument. This will allow the debugger to validate.
# test.py
def foo():
print('A') # suppose thread 2 is stopped here
def bar():
print('B') # suppose thread 1 is stopped here
print('C')
It is valid for thread 1
to move within the same block to print('C')
. It is not valid for thread 2
to move to print('C')
. There is no way to tell which thread the user wants to move from the arguments of gotoTargets
request. The goto
request will fail for thread 2
, but this can be avoided.
For the screenshot below, I forced a blank targets response. This allows IDE to show changes to cursor indicating the move invalid
The vscode-debug-perl
extension supports a launch.json
configuration where it just starts a TCP server and awaits an incoming connection from a debugger (possibly on a remote machine). It neither launches the debugger nor the debuggee, so it's not really request: launch
; it also does not attach to anything, so it's not request: attach
either.
It also supports launching debugger+debuggee on the local machine. That matches request: launch
, but it seems strange to use request: launch
for both scenarios. Perhaps another type could be allowed, like request: listen
(or await
) to cover the first scenario?
Some DAP requests return reference IDs that are used in subsequent requests to retrieve more data.
Since some of these reference IDs are only valid between two stop events, it is possible that a request arrives at the DA after a new stop event has already happened and the reference ID is no longer valid.
Since the DAP only requires that those reference IDs are unique for one stop event, a DA is free to reuse the IDs for every new stop. This makes it impossible for the DA to verify that an IDs is not from an old stop.
One idea to address this problem is to introduce a unique stop ID that the client receives with the stop event and can pass for any subsequent request that uses reference IDs of that stop event.
With this the DA can easily verify that a request refers to the same stop event that the DA sees. If the DAs has already seen a new stop event, stale requests can be detected and aborted.
See bug microsoft/vscode#27694 for details.
If we're going to support the enumDescriptions
field in the schema (as seen in PR microsoft/vscode-debugadapter-node#124) , I think every enum should have them.
If this is of interest, I'd be happy to do the work and send a PR - I'd like this for the C# protocol library we generate from the schema so that our enums can have proper doc-comments on the values.
Namedrops: @weinand @gregg-miskelly
In order to use the debug protocol in VS and Xamerin, we need the ability to differentiate between expressions that contain side effects and those that don't. In VS, for instance, the expression evaluator being used by the debugger can mark an expression as side effect free, therefore, safe for implicit evaluation, and non-side effect free evaluations. As mentioned above, this is primarily used to determine if an expression is safe to re-evaluate at each break mode, or if it should only evaluate once. Examples of expressions with side effects:
I=3;
Foo();
Examples of expressions without side effects:
squild.length where length is a property getter (still requiring func-eval but safe).
An optional flag on the evaluation result and the the variables result would be sufficient.
Note: Since it would be a breaking change if a client sends the new value to old DAs that are not expecting it, we will have to introduce a new capability for this.
Raised as a result of the suggestion from @weinand on microsoft/vscode#59746
The debug protocol provided by vscode allows the IDE to inform the debug server of function breakpoints that should be set by sending a SetFunctionBreakpoints request. This request contains an array of objects of type FunctionBreakpoint.
The debug protocol also allows the debug server to inform the IDE that breakpoints have been set by sending a BreakpointEvent. This event contains information on whether the breakpoint was added, removed or changed and contains an object of type Breakpoint representing the event.
Unfortunately this Breakpoint type is for source breakpoints and doesn't contain the ability to specify information about function breakpoints. I tried a few different things by not setting line numbers, source file etc. but they all resulted in issues with the breakpoints view in vscode.
I had a look through debugSession.ts in the vscode source (see line 365) and there is some logic for function breakpoints, but it doesn't apply if the reason on the event is 'new'
For a lot of languages it makes sense to set granularity for steps. For instance, in any bytecode language it makes sense for step normally step over lines, but sometimes it should step over bytecode instead.
Refs: microsoft/vscode#52866
https://microsoft.github.io/language-server-protocol/inspector/app
As you now nicely visualize LSP protocols we might consider in the future to reuse this to visualize debug adapter protocol messages.
fyi @weinand @roblourens
Actual:
It looks like DAP inherits single node architecture where application and debugger are located on same computer or local network, both are state-full and restart of both partners can be manually synchronized. in the real world cloud scenario the debugger client are stateful but everything between is stateless
Data breakpoints are only available if the supportsDataBreakpoints
capability is true:
/** Information about the capabilities of a debug adapter. */
export interface Capabilities {
// ...
/** The debug adapter supports data breakpoints. */
supportsDataBreakpoints?: boolean;
}
The dataBreakpointInfo
request must be used to determine whether a data breakpoint is available for a specific variable or expression and returns a "data id" for it.
/** DataBreakpointInfo request; value of command field is 'dataBreakpointInfo'.
Obtains information on a possible data breakpoint that could be set on an expression or variable.
*/
export interface DataBreakpointInfoRequest extends Request {
// command: 'dataBreakpointInfo';
arguments: DataBreakpointInfoArguments;
}
/** Arguments for 'dataBreakpointInfo' request. */
export interface DataBreakpointInfoArguments {
/** Reference to the Variable container if the data breakpoint is requested for a child of the container. */
variablesReference?: number;
/** The name of the Variable's child to obtain data breakpoint information for. If variableReference isn’t provided, this can be an expression. */
name: string;
}
/** Response to 'dataBreakpointInfo' request. */
export interface DataBreakpointInfoResponse extends Response {
body: {
/** An identifier for the data on which a data breakpoint can be registered with the setDataBreakpoints request or null if no data breakpoint is available. */
dataId: string | null;
/** UI string that describes on what data the breakpoint is set on or why a data breakpoint is not available. */
description: string;
/** Optional attribute listing the available access types for a potential data breakpoint. A UI frontend could surface this information. */
accessTypes?: DataBreakpointAccessType[];
/** Optional attribute indicating that a potential data breakpoint could be persisted across sessions. */
canPersist?: boolean;
};
}
The "data id" (and additional breakpoint options) can be used to create a DataBreakpoint
:
/** Properties of a data breakpoint passed to the setDataBreakpoints request. */
export interface DataBreakpoint {
/** An id representing the data. This id is returned from the dataBreakpointInfo request. */
dataId: string;
/** The access type of the data. */
accessType?: DataBreakpointAccessType;
/** An optional expression for conditional breakpoints. */
condition?: string;
/** An optional expression that controls how many hits of the breakpoint are ignored. The backend is expected to interpret the expression as needed. */
hitCondition?: string;
}
/** This enumeration defines all possible access types for data breakpoints. */
export type DataBreakpointAccessType = 'read' | 'write' | 'readWrite';
Multiple data breakpoints are registered and deregistered for a debug session with the setDataBreakpoints
request:
/** SetDataBreakpoints request; value of command field is 'setDataBreakpoints'.
Replaces all existing data breakpoints with new data breakpoints.
To clear all data breakpoints, specify an empty array.
When a data breakpoint is hit, a 'stopped' event (with reason 'data breakpoint') is generated.
*/
export interface SetDataBreakpointsRequest extends Request {
// command: 'setDataBreakpoints';
arguments: SetDataBreakpointsArguments;
}
/** Arguments for 'setDataBreakpoints' request. */
export interface SetDataBreakpointsArguments {
/** The contents of this array replaces all existing data breakpoints. An empty array clears all data breakpoints. */
breakpoints: DataBreakpoint[];
}
/** Response to 'setDataBreakpoints' request.
Returned is information about each breakpoint created by this request.
*/
export interface SetDataBreakpointsResponse extends Response {
body: {
/** Information about the data breakpoints. The array elements correspond to the elements of the input argument 'breakpoints' array. */
breakpoints: Breakpoint[];
};
}
And a new value dataBreakpoint
for the VariablePresentationHint
can be used to hint to the UI frontend that a data breakpoint is installed on a variable.
/** Optional properties of a variable that can be used to determine how to render the variable in the UI. */
export interface VariablePresentationHint {
/** The kind of variable. Before introducing additional values, try to use the listed values.
Values:
// ...
'dataBreakpoint': Indicates that a data breakpoint is registered for the object.
etc.
*/
kind?: string;
// ...
}
I might be missing something here, but the Breakpoint
type is for »Information about a Breakpoint created in setBreakpoints or setFunctionBreakpoints« while DataBreakpoint
is for »Properties of a data breakpoint passed to the setDataBreakpoints request« and the BreakpointEvent
is only for Breakpoint
breakpoints. So it does not make sense to use BreakpointEvent
for a change in a DataBreakpoint
.
There is no DataBreakpointEvent
. Is that an accidental omission?
I might want to create a data breakpoint based on a launch.json
configuration option and inform vscode about it, so users can disable the breakpoint if they so choose (or for that matter, users might configure data breakpoints through the debug console instead of the vscode ui, and then I might also want to surface such breakpoints through vscode anyways).
In Visual Studio, users can ignore first chance exceptions when they are raised in specific modules. This is useful when an external component raises a lot of exceptions that the user does not care about. This feature can be supported by the protocol by adding the concept of exception conditions. Although these conditions are currently either "Module == name" or "Module != name" this proposal lets the condition type be specified in case other condition types are added.
/** An ExceptionOptions assigns configuration options to a set of exceptions.*/
export interface ExceptionOptions {
// ....
/** A set of conditions used to determine whether the exception should result in a break.
The debugger will break only if the exception matches all listed conditions.*/
conditions?: ExceptionCondition[];
}
/** Condition to determine if the exception should be handled by the debugger.*/
export interface ExceptionCondition {
/** Type of the condition.*/
type: 'module';
/** Operation to apply to the condition value.*/
operator?: 'equals' | 'notEquals';
/** Value of the condition.*/
value: string;
}
/** Information about the capabilities of a debug adapter.*/
export interface Capabilities {
// ....
/** The debug adapter supports using exception conditions in exception options.*/
supportsExceptionConditions?: boolean;
}
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.