mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-28 23:31:56 +00:00
Merge inbound to mozilla-central. a=merge
This commit is contained in:
commit
00c0d068ec
@ -11,7 +11,7 @@ import {
|
||||
getASTLocation,
|
||||
assertLocation,
|
||||
makeBreakpointId,
|
||||
makeSourceActorLocation
|
||||
makeBreakpointLocation
|
||||
} from "../../utils/breakpoint";
|
||||
import { PROMISE } from "../utils/middleware/promise";
|
||||
import {
|
||||
@ -71,15 +71,8 @@ async function addBreakpointPromise(getState, client, sourceMaps, breakpoint) {
|
||||
return newBreakpoint;
|
||||
}
|
||||
|
||||
const sourceActors = getSourceActors(state, generatedSource.id);
|
||||
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
generatedLocation
|
||||
);
|
||||
await client.setBreakpoint(sourceActorLocation, breakpoint.options);
|
||||
}
|
||||
const breakpointLocation = makeBreakpointLocation(getState(), generatedLocation);
|
||||
await client.setBreakpoint(breakpointLocation, breakpoint.options);
|
||||
|
||||
const symbols = getSymbols(getState(), source);
|
||||
const astLocation = await getASTLocation(source, symbols, location);
|
||||
|
@ -23,7 +23,7 @@ import {
|
||||
import {
|
||||
assertBreakpoint,
|
||||
createXHRBreakpoint,
|
||||
makeSourceActorLocation
|
||||
makeBreakpointLocation
|
||||
} from "../../utils/breakpoint";
|
||||
import {
|
||||
addBreakpoint,
|
||||
@ -49,19 +49,8 @@ import type {
|
||||
import { recordEvent } from "../../utils/telemetry";
|
||||
|
||||
async function removeBreakpointsPromise(client, state, breakpoint) {
|
||||
const sourceActors = getSourceActors(
|
||||
state,
|
||||
breakpoint.generatedLocation.sourceId
|
||||
);
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
breakpoint.generatedLocation
|
||||
);
|
||||
if (client.getBreakpointByLocation(sourceActorLocation)) {
|
||||
await client.removeBreakpoint(sourceActorLocation);
|
||||
}
|
||||
}
|
||||
const breakpointLocation = makeBreakpointLocation(state, breakpoint.generatedLocation);
|
||||
await client.removeBreakpoint(breakpointLocation);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -304,19 +293,8 @@ export function setBreakpointOptions(
|
||||
await dispatch(enableBreakpoint(bp));
|
||||
}
|
||||
|
||||
const sourceActors = getSourceActors(
|
||||
getState(),
|
||||
bp.generatedLocation.sourceId
|
||||
);
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
bp.generatedLocation
|
||||
);
|
||||
if (client.getBreakpointByLocation(sourceActorLocation)) {
|
||||
await client.setBreakpointOptions(sourceActorLocation, options);
|
||||
}
|
||||
}
|
||||
const breakpointLocation = makeBreakpointLocation(getState(), bp.generatedLocation);
|
||||
await client.setBreakpoint(breakpointLocation, options);
|
||||
|
||||
const newBreakpoint = { ...bp, disabled: false, options };
|
||||
|
||||
|
@ -11,7 +11,8 @@ import {
|
||||
assertBreakpoint,
|
||||
assertPendingBreakpoint,
|
||||
findScopeByName,
|
||||
makeSourceActorLocation
|
||||
makeSourceActorLocation,
|
||||
makeBreakpointLocation
|
||||
} from "../../utils/breakpoint";
|
||||
|
||||
import { getGeneratedLocation } from "../../utils/source-maps";
|
||||
@ -125,7 +126,16 @@ export async function syncBreakpointPromise(
|
||||
scopedGeneratedLocation
|
||||
);
|
||||
|
||||
const sourceActors = getSourceActors(getState(), sourceId);
|
||||
// makeBreakpointLocation requires the source to still exist, which might not
|
||||
// be the case if we navigated.
|
||||
if (!getSource(getState(), generatedSourceId)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const breakpointLocation = makeBreakpointLocation(getState(), generatedLocation);
|
||||
const scopedBreakpointLocation =
|
||||
makeBreakpointLocation(getState(), scopedGeneratedLocation);
|
||||
|
||||
let possiblePosition = true;
|
||||
if (features.columnBreakpoints && generatedLocation.column != undefined) {
|
||||
const { positions } = await dispatch(
|
||||
@ -141,19 +151,7 @@ export async function syncBreakpointPromise(
|
||||
if (possiblePosition && (pendingBreakpoint.disabled || isSameLocation)) {
|
||||
// Make sure the breakpoint is installed on all source actors.
|
||||
if (!pendingBreakpoint.disabled) {
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
generatedLocation
|
||||
);
|
||||
if (!client.getBreakpointByLocation(sourceActorLocation)) {
|
||||
await client.setBreakpoint(
|
||||
sourceActorLocation,
|
||||
pendingBreakpoint.options,
|
||||
isOriginalId(sourceId)
|
||||
);
|
||||
}
|
||||
}
|
||||
await client.setBreakpoint(breakpointLocation, pendingBreakpoint.options);
|
||||
}
|
||||
|
||||
const originalText = getTextAtPosition(source, previousLocation);
|
||||
@ -170,15 +168,7 @@ export async function syncBreakpointPromise(
|
||||
}
|
||||
|
||||
// clear server breakpoints if they exist and we have moved
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
generatedLocation
|
||||
);
|
||||
if (client.getBreakpointByLocation(sourceActorLocation)) {
|
||||
await client.removeBreakpoint(sourceActorLocation);
|
||||
}
|
||||
}
|
||||
await client.removeBreakpoint(breakpointLocation);
|
||||
|
||||
if (!possiblePosition || !scopedGeneratedLocation.line) {
|
||||
return { previousLocation, breakpoint: null };
|
||||
@ -188,18 +178,12 @@ export async function syncBreakpointPromise(
|
||||
// If we are not disabled, set the breakpoint on the server and get
|
||||
// that info so we can set it on our breakpoints.
|
||||
|
||||
for (const sourceActor of sourceActors) {
|
||||
const sourceActorLocation = makeSourceActorLocation(
|
||||
sourceActor,
|
||||
scopedGeneratedLocation
|
||||
);
|
||||
await client.setBreakpoint(
|
||||
sourceActorLocation,
|
||||
pendingBreakpoint.options,
|
||||
isOriginalId(sourceId)
|
||||
);
|
||||
if (!scopedGeneratedLocation.line) {
|
||||
return { previousLocation, breakpoint: null };
|
||||
}
|
||||
|
||||
await client.setBreakpoint(scopedGeneratedLocation, pendingBreakpoint.options);
|
||||
|
||||
const originalText = getTextAtPosition(source, scopedLocation);
|
||||
const text = getTextAtPosition(generatedSource, scopedGeneratedLocation);
|
||||
|
||||
|
@ -42,6 +42,7 @@ import {
|
||||
selectors,
|
||||
actions,
|
||||
makeOriginalSource,
|
||||
makeSource,
|
||||
waitForState
|
||||
} from "../../utils/test-head";
|
||||
|
||||
@ -128,6 +129,8 @@ describe("when adding breakpoints", () => {
|
||||
loadInitialState()
|
||||
);
|
||||
|
||||
await dispatch(actions.newSource(makeSource("foo")));
|
||||
|
||||
const csr1 = makeOriginalSource("foo");
|
||||
const csr2 = makeOriginalSource("foo2");
|
||||
|
||||
@ -178,6 +181,8 @@ describe("when changing an existing breakpoint", () => {
|
||||
const bp = generateBreakpoint("foo");
|
||||
const id = makePendingLocationId(bp.location);
|
||||
|
||||
await dispatch(actions.newSource(makeSource("foo")));
|
||||
|
||||
const csr = makeOriginalSource("foo");
|
||||
await dispatch(actions.newSource(csr));
|
||||
await dispatch(actions.loadSourceText(csr.source));
|
||||
@ -229,6 +234,8 @@ describe("initializing when pending breakpoints exist in prefs", () => {
|
||||
);
|
||||
const bar = generateBreakpoint("bar.js");
|
||||
|
||||
await dispatch(actions.newSource(makeSource("bar.js")));
|
||||
|
||||
const csr = makeOriginalSource("bar.js");
|
||||
await dispatch(actions.newSource(csr));
|
||||
await dispatch(actions.loadSourceText(csr.source));
|
||||
@ -267,6 +274,7 @@ describe("initializing with disabled pending breakpoints in prefs", () => {
|
||||
const { getState, dispatch } = store;
|
||||
const csr = makeOriginalSource("bar.js");
|
||||
|
||||
await dispatch(actions.newSource(makeSource("bar.js")));
|
||||
await dispatch(actions.newSource(csr));
|
||||
await dispatch(actions.loadSourceText(csr.source));
|
||||
|
||||
@ -297,6 +305,8 @@ describe("adding sources", () => {
|
||||
expect(selectors.getBreakpointCount(getState())).toEqual(0);
|
||||
|
||||
const csr = makeOriginalSource("bar.js");
|
||||
|
||||
await dispatch(actions.newSource(makeSource("bar.js")));
|
||||
await dispatch(actions.newSource(csr));
|
||||
await dispatch(actions.loadSourceText(csr.source));
|
||||
|
||||
@ -322,6 +332,7 @@ describe("adding sources", () => {
|
||||
|
||||
expect(selectors.getBreakpointCount(getState())).toEqual(0);
|
||||
|
||||
await dispatch(actions.newSource(makeSource("bar.js")));
|
||||
await dispatch(actions.newSource(csr));
|
||||
|
||||
await waitForState(store, state => selectors.getBreakpointCount(state) > 0);
|
||||
@ -337,12 +348,15 @@ describe("adding sources", () => {
|
||||
|
||||
const csr1 = makeOriginalSource("bar.js");
|
||||
const csr2 = makeOriginalSource("foo.js");
|
||||
await dispatch(actions.newSource(makeSource("bar.js")));
|
||||
await dispatch(actions.newSources([csr1, csr2]));
|
||||
await dispatch(actions.loadSourceText(csr1.source));
|
||||
await dispatch(actions.loadSourceText(csr2.source));
|
||||
|
||||
await waitForState(store, state => selectors.getBreakpointCount(state) > 0);
|
||||
|
||||
expect(selectors.getBreakpointCount(getState())).toEqual(1);
|
||||
// N.B. this test is kind of broken and creates different breakpoints for
|
||||
// the generated and original bar.js sources.
|
||||
expect(selectors.getBreakpointCount(getState())).toEqual(2);
|
||||
});
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ function createObjectClient(grip: Grip) {
|
||||
return DebuggerClient.createObjectClient(grip);
|
||||
}
|
||||
|
||||
export async function onConnect(connection: any, actions: Object): Object {
|
||||
export async function onConnect(connection: any, actions: Object) {
|
||||
const {
|
||||
tabConnection: { tabTarget, threadClient, debuggerClient }
|
||||
} = connection;
|
||||
@ -22,13 +22,13 @@ export async function onConnect(connection: any, actions: Object): Object {
|
||||
DebuggerClient = debuggerClient;
|
||||
|
||||
if (!tabTarget || !threadClient || !debuggerClient) {
|
||||
return { bpClients: {} };
|
||||
return;
|
||||
}
|
||||
|
||||
const supportsWasm =
|
||||
features.wasm && !!debuggerClient.mainRoot.traits.wasmBinarySource;
|
||||
|
||||
const { bpClients } = setupCommands({
|
||||
setupCommands({
|
||||
threadClient,
|
||||
tabTarget,
|
||||
debuggerClient,
|
||||
@ -69,8 +69,6 @@ export async function onConnect(connection: any, actions: Object): Object {
|
||||
if (pausedPacket) {
|
||||
clientEvents.paused(threadClient, "paused", pausedPacket);
|
||||
}
|
||||
|
||||
return { bpClients };
|
||||
}
|
||||
|
||||
export { createObjectClient, clientCommands, clientEvents };
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
import type {
|
||||
ActorId,
|
||||
BreakpointLocation,
|
||||
BreakpointOptions,
|
||||
BreakpointResult,
|
||||
EventListenerBreakpoints,
|
||||
@ -24,7 +25,6 @@ import type {
|
||||
Grip,
|
||||
ThreadClient,
|
||||
ObjectClient,
|
||||
BPClients,
|
||||
SourcesPacket
|
||||
} from "./types";
|
||||
|
||||
@ -37,12 +37,12 @@ import { supportsWorkers, updateWorkerClients } from "./workers";
|
||||
|
||||
import { features } from "../../utils/prefs";
|
||||
|
||||
let bpClients: BPClients;
|
||||
let workerClients: Object;
|
||||
let threadClient: ThreadClient;
|
||||
let tabTarget: TabTarget;
|
||||
let debuggerClient: DebuggerClient;
|
||||
let sourceActors: { [ActorId]: SourceId };
|
||||
let breakpoints: { [string]: Object };
|
||||
let supportsWasm: boolean;
|
||||
|
||||
type Dependencies = {
|
||||
@ -52,16 +52,14 @@ type Dependencies = {
|
||||
supportsWasm: boolean
|
||||
};
|
||||
|
||||
function setupCommands(dependencies: Dependencies): { bpClients: BPClients } {
|
||||
function setupCommands(dependencies: Dependencies) {
|
||||
threadClient = dependencies.threadClient;
|
||||
tabTarget = dependencies.tabTarget;
|
||||
debuggerClient = dependencies.debuggerClient;
|
||||
supportsWasm = dependencies.supportsWasm;
|
||||
bpClients = {};
|
||||
workerClients = {};
|
||||
sourceActors = {};
|
||||
|
||||
return { bpClients };
|
||||
breakpoints = {};
|
||||
}
|
||||
|
||||
function createObjectClient(grip: Grip) {
|
||||
@ -159,26 +157,6 @@ async function sourceContents({
|
||||
return { source, contentType };
|
||||
}
|
||||
|
||||
function getBreakpointByLocation(location: SourceActorLocation) {
|
||||
const id = makeBreakpointActorId(location);
|
||||
const bpClient = bpClients[id];
|
||||
|
||||
if (bpClient) {
|
||||
const { actor, url, line, column } = bpClient.location;
|
||||
return {
|
||||
id: bpClient.actor,
|
||||
options: bpClient.options,
|
||||
actualLocation: {
|
||||
line,
|
||||
column,
|
||||
sourceId: actor,
|
||||
sourceUrl: url
|
||||
}
|
||||
};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function setXHRBreakpoint(path: string, method: string) {
|
||||
return threadClient.setXHRBreakpoint(path, method);
|
||||
}
|
||||
@ -187,61 +165,34 @@ function removeXHRBreakpoint(path: string, method: string) {
|
||||
return threadClient.removeXHRBreakpoint(path, method);
|
||||
}
|
||||
|
||||
function setBreakpoint(
|
||||
location: SourceActorLocation,
|
||||
options: BreakpointOptions
|
||||
) {
|
||||
const sourceThreadClient = lookupThreadClient(location.sourceActor.thread);
|
||||
const sourceClient = sourceThreadClient.source({
|
||||
actor: location.sourceActor.actor
|
||||
});
|
||||
|
||||
return sourceClient
|
||||
.setBreakpoint({
|
||||
line: location.line,
|
||||
column: location.column,
|
||||
options,
|
||||
})
|
||||
.then(([, bpClient]) => {
|
||||
const id = makeBreakpointActorId(location);
|
||||
bpClients[id] = bpClient;
|
||||
});
|
||||
// Get the string key to use for a breakpoint location.
|
||||
// See also duplicate code in breakpoint-actor-map.js :(
|
||||
function locationKey(location) {
|
||||
const { sourceUrl, sourceId, line, column } = location;
|
||||
return `${(sourceUrl: any)}:${(sourceId: any)}:${line}:${(column: any)}`;
|
||||
}
|
||||
|
||||
function removeBreakpoint(
|
||||
location: SourceActorLocation
|
||||
): Promise<void> | ?BreakpointResult {
|
||||
try {
|
||||
const id = makeBreakpointActorId(location);
|
||||
const bpClient = bpClients[id];
|
||||
if (!bpClient) {
|
||||
console.warn("No breakpoint to delete on server");
|
||||
return Promise.resolve();
|
||||
}
|
||||
delete bpClients[id];
|
||||
return bpClient.remove();
|
||||
} catch (_error) {
|
||||
console.warn("No breakpoint to delete on server");
|
||||
function* getAllThreadClients() {
|
||||
yield threadClient;
|
||||
for (const { thread } of (Object.values(workerClients): any)) {
|
||||
yield thread;
|
||||
}
|
||||
}
|
||||
|
||||
function setBreakpointOptions(
|
||||
location: SourceActorLocation,
|
||||
async function setBreakpoint(
|
||||
location: BreakpointLocation,
|
||||
options: BreakpointOptions
|
||||
) {
|
||||
const id = makeBreakpointActorId(location);
|
||||
const bpClient = bpClients[id];
|
||||
breakpoints[locationKey(location)] = { location, options };
|
||||
for (const thread of getAllThreadClients()) {
|
||||
await thread.setBreakpoint(location, options);
|
||||
}
|
||||
}
|
||||
|
||||
if (debuggerClient.mainRoot.traits.nativeLogpoints) {
|
||||
bpClient.setOptions(options);
|
||||
} else {
|
||||
// Older server breakpoints destroy themselves when changing options.
|
||||
delete bpClients[id];
|
||||
bpClient
|
||||
.setOptions(options)
|
||||
.then(_bpClient => {
|
||||
bpClients[id] = _bpClient;
|
||||
});
|
||||
async function removeBreakpoint(location: BreakpointLocation) {
|
||||
delete breakpoints[locationKey(location)];
|
||||
for (const thread of getAllThreadClients()) {
|
||||
await thread.removeBreakpoint(location);
|
||||
}
|
||||
}
|
||||
|
||||
@ -418,18 +369,26 @@ function getSourceForActor(actor: ActorId) {
|
||||
|
||||
async function fetchWorkers(): Promise<Worker[]> {
|
||||
if (features.windowlessWorkers) {
|
||||
workerClients = await updateWorkerClients({
|
||||
const newWorkerClients = await updateWorkerClients({
|
||||
tabTarget,
|
||||
debuggerClient,
|
||||
threadClient,
|
||||
workerClients
|
||||
});
|
||||
|
||||
const workerNames = Object.getOwnPropertyNames(workerClients);
|
||||
// Fetch the sources and install breakpoints on any new workers.
|
||||
const workerNames = Object.getOwnPropertyNames(newWorkerClients);
|
||||
for (const actor of workerNames) {
|
||||
if (!workerClients[actor]) {
|
||||
const client = newWorkerClients[actor].thread;
|
||||
createSources(client);
|
||||
for (const { location, options } of (Object.values(breakpoints): any)) {
|
||||
client.setBreakpoint(location, options);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
workerNames.forEach(actor => {
|
||||
createSources(workerClients[actor].thread);
|
||||
});
|
||||
workerClients = newWorkerClients;
|
||||
|
||||
return workerNames.map(actor =>
|
||||
createWorker(actor, workerClients[actor].url)
|
||||
@ -484,13 +443,11 @@ const clientCommands = {
|
||||
breakOnNext,
|
||||
sourceContents,
|
||||
getSourceForActor,
|
||||
getBreakpointByLocation,
|
||||
getBreakpointPositions,
|
||||
setBreakpoint,
|
||||
setXHRBreakpoint,
|
||||
removeXHRBreakpoint,
|
||||
removeBreakpoint,
|
||||
setBreakpointOptions,
|
||||
evaluate,
|
||||
evaluateInFrame,
|
||||
evaluateExpressions,
|
||||
|
@ -11,6 +11,7 @@
|
||||
*/
|
||||
|
||||
import type {
|
||||
BreakpointLocation,
|
||||
BreakpointOptions,
|
||||
FrameId,
|
||||
ActorId,
|
||||
@ -327,11 +328,6 @@ export type SourceClient = {
|
||||
source: () => { source: any, contentType?: string },
|
||||
_activeThread: ThreadClient,
|
||||
actor: string,
|
||||
setBreakpoint: ({
|
||||
line: number,
|
||||
column: ?number,
|
||||
condition: ?string
|
||||
}) => Promise<BreakpointResponse>,
|
||||
getBreakpointPositionsCompressed: (range: {
|
||||
start: { line: number },
|
||||
end: { line: number }
|
||||
@ -370,6 +366,8 @@ export type ThreadClient = {
|
||||
source: ({ actor: SourceId }) => SourceClient,
|
||||
pauseGrip: (Grip | Function) => ObjectClient,
|
||||
pauseOnExceptions: (boolean, boolean) => Promise<*>,
|
||||
setBreakpoint: (BreakpointLocation, BreakpointOptions) => Promise<*>,
|
||||
removeBreakpoint: (BreakpointLocation) => Promise<*>,
|
||||
setXHRBreakpoint: (path: string, method: string) => Promise<boolean>,
|
||||
removeXHRBreakpoint: (path: string, method: string) => Promise<boolean>,
|
||||
interrupt: () => Promise<*>,
|
||||
@ -387,38 +385,6 @@ export type ThreadClient = {
|
||||
setEventListenerBreakpoints: (string[]) => void
|
||||
};
|
||||
|
||||
/**
|
||||
* BreakpointClient
|
||||
* @memberof firefox
|
||||
* @static
|
||||
*/
|
||||
export type BreakpointClient = {
|
||||
actor: ActorId,
|
||||
remove: () => void,
|
||||
location: {
|
||||
actor: string,
|
||||
url: string,
|
||||
line: number,
|
||||
column: ?number
|
||||
},
|
||||
setOptions: BreakpointOptions => Promise<BreakpointClient>,
|
||||
// request: any,
|
||||
source: SourceClient,
|
||||
options: BreakpointOptions
|
||||
};
|
||||
|
||||
export type BPClients = { [id: ActorId]: BreakpointClient };
|
||||
|
||||
export type BreakpointResponse = [
|
||||
{
|
||||
actor?: ActorId,
|
||||
from?: ActorId,
|
||||
isPending?: boolean,
|
||||
actualLocation?: ActualLocation
|
||||
},
|
||||
BreakpointClient
|
||||
];
|
||||
|
||||
export type FirefoxClientConnection = {
|
||||
getTabTarget: () => TabTarget,
|
||||
getThreadClient: () => ThreadClient,
|
||||
|
@ -29,6 +29,16 @@ function loadFromPrefs(actions: Object) {
|
||||
}
|
||||
}
|
||||
|
||||
async function syncBreakpoints() {
|
||||
const breakpoints = await asyncStore.pendingBreakpoints;
|
||||
const breakpointValues = (Object.values(breakpoints): any);
|
||||
breakpointValues.forEach(({ disabled, options, generatedLocation }) => {
|
||||
if (!disabled) {
|
||||
firefox.clientCommands.setBreakpoint(generatedLocation, options);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function syncXHRBreakpoints() {
|
||||
asyncStore.xhrBreakpoints.then(bps => {
|
||||
bps.forEach(({ path, method, disabled }) => {
|
||||
@ -83,6 +93,7 @@ export async function onConnect(
|
||||
await client.onConnect(connection, actions);
|
||||
|
||||
await loadFromPrefs(actions);
|
||||
syncBreakpoints();
|
||||
syncXHRBreakpoints();
|
||||
setupHelper({
|
||||
store,
|
||||
|
@ -90,6 +90,17 @@ export type PendingLocation = {
|
||||
+sourceUrl?: string
|
||||
};
|
||||
|
||||
// Type of location used when setting breakpoints in the server. Exactly one of
|
||||
// { sourceUrl, sourceId } must be specified. Soon this will replace
|
||||
// SourceLocation and PendingLocation, and SourceActorLocation will be removed
|
||||
// (bug 1524374).
|
||||
export type BreakpointLocation = {
|
||||
+line: number,
|
||||
+column?: number,
|
||||
+sourceUrl?: string,
|
||||
+sourceId?: SourceId
|
||||
};
|
||||
|
||||
export type ASTLocation = {|
|
||||
+name: ?string,
|
||||
+offset: PartialPosition,
|
||||
|
@ -6,7 +6,7 @@
|
||||
|
||||
import { sortBy } from "lodash";
|
||||
|
||||
import { getBreakpoint } from "../../selectors";
|
||||
import { getBreakpoint, getSource, getSourceActors } from "../../selectors";
|
||||
import { isGenerated } from "../source";
|
||||
|
||||
import assert from "../assert";
|
||||
@ -22,6 +22,7 @@ import type {
|
||||
SourceActorLocation,
|
||||
PendingLocation,
|
||||
Breakpoint,
|
||||
BreakpointLocation,
|
||||
PendingBreakpoint
|
||||
} from "../../types";
|
||||
|
||||
@ -68,6 +69,24 @@ export function makePendingLocationId(location: SourceLocation) {
|
||||
return `${sourceUrlString}:${line}:${columnString}`;
|
||||
}
|
||||
|
||||
export function makeBreakpointLocation(state: State, location: SourceLocation): BreakpointLocation {
|
||||
const source = getSource(state, location.sourceId);
|
||||
if (!source) {
|
||||
throw new Error("no source");
|
||||
}
|
||||
const breakpointLocation: any = {
|
||||
line: location.line,
|
||||
column: location.column
|
||||
};
|
||||
if (source.url) {
|
||||
breakpointLocation.sourceUrl = source.url;
|
||||
} else {
|
||||
const sourceActors = getSourceActors(state, location.sourceId);
|
||||
breakpointLocation.sourceId = sourceActors[0].actor;
|
||||
}
|
||||
return breakpointLocation;
|
||||
}
|
||||
|
||||
export function makeSourceActorLocation(
|
||||
sourceActor: SourceActor,
|
||||
location: SourceLocation
|
||||
|
@ -35,7 +35,12 @@ add_task(async function() {
|
||||
|
||||
openFirstBreakpointContextMenu(dbg);
|
||||
// select "Disable Others"
|
||||
let dispatched = waitForDispatch(dbg, "DISABLE_BREAKPOINT", 3);
|
||||
// FIXME bug 1524374 this waitForDispatch call only sees one dispatch for
|
||||
// DISABLE_BREAKPOINT even though three are triggered, due to the order in
|
||||
// which promises get resolved. The problem seems to indicate a coverage gap
|
||||
// in waitUntilService(). Workaround this by only waiting for one dispatch,
|
||||
// though this is fragile and could break again in the future.
|
||||
let dispatched = waitForDispatch(dbg, "DISABLE_BREAKPOINT", /*3*/ 1);
|
||||
selectContextMenuItem(dbg, selectors.breakpointContextMenu.disableOthers);
|
||||
await waitForState(dbg, state =>
|
||||
dbg.selectors.getBreakpointsList(state)
|
||||
|
@ -4,6 +4,13 @@
|
||||
// Tests the breakpoint gutter and making sure breakpoint icons exist
|
||||
// correctly
|
||||
|
||||
// FIXME bug 1524374 removing breakpoints in this test can cause uncaught
|
||||
// rejections and make bug 1512742 permafail.
|
||||
const { PromiseTestUtils } = scopedCuImport(
|
||||
"resource://testing-common/PromiseTestUtils.jsm"
|
||||
);
|
||||
PromiseTestUtils.whitelistRejectionsGlobally(/NS_ERROR_NOT_INITIALIZED/);
|
||||
|
||||
// Utilities for interacting with the editor
|
||||
function clickGutter(dbg, line) {
|
||||
clickElement(dbg, "gutter", line);
|
||||
|
@ -16,7 +16,7 @@ add_task(async function() {
|
||||
);
|
||||
const {threadClient, tab, toolbox} = dbg;
|
||||
|
||||
await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
|
||||
// Visit a lot of breakpoints so that we are sure we have crossed major
|
||||
// checkpoint boundaries.
|
||||
@ -39,6 +39,7 @@ add_task(async function() {
|
||||
await resumeToLine(threadClient, 21);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 10);
|
||||
|
||||
await threadClient.removeBreakpoint(bp);
|
||||
await toolbox.closeToolbox();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ add_task(async function() {
|
||||
{ waitForRecording: true });
|
||||
const {threadClient, tab, toolbox} = dbg;
|
||||
|
||||
await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
await rewindToLine(threadClient, 21);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 10);
|
||||
await checkEvaluateInTopFrameThrows(threadClient, "window.alert(3)");
|
||||
@ -23,6 +23,7 @@ add_task(async function() {
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 10);
|
||||
await checkEvaluateInTopFrame(threadClient, "testStepping2()", undefined);
|
||||
|
||||
await threadClient.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -14,18 +14,21 @@ add_task(async function() {
|
||||
const {threadClient, tab, toolbox} = dbg;
|
||||
|
||||
await threadClient.interrupt();
|
||||
await setBreakpoint(threadClient, "doc_rr_continuous.html", 19);
|
||||
const bp1 = await setBreakpoint(threadClient, "doc_rr_continuous.html", 19);
|
||||
await resumeToLine(threadClient, 19);
|
||||
await reverseStepOverToLine(threadClient, 18);
|
||||
await checkEvaluateInTopFrame(threadClient,
|
||||
"SpecialPowers.Cu.recordReplayDirective(/* AlwaysTakeTemporarySnapshots */ 3)",
|
||||
undefined);
|
||||
await stepInToLine(threadClient, 22);
|
||||
await setBreakpoint(threadClient, "doc_rr_continuous.html", 24);
|
||||
const bp2 = await setBreakpoint(threadClient, "doc_rr_continuous.html", 24);
|
||||
await resumeToLine(threadClient, 24);
|
||||
await setBreakpoint(threadClient, "doc_rr_continuous.html", 22);
|
||||
const bp3 = await setBreakpoint(threadClient, "doc_rr_continuous.html", 22);
|
||||
await rewindToLine(threadClient, 22);
|
||||
|
||||
await threadClient.removeBreakpoint(bp1);
|
||||
await threadClient.removeBreakpoint(bp2);
|
||||
await threadClient.removeBreakpoint(bp3);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ add_task(async function() {
|
||||
const dbg = await attachRecordingDebugger("doc_rr_continuous.html");
|
||||
const {threadClient, tab, toolbox} = dbg;
|
||||
|
||||
await setBreakpoint(threadClient, "doc_rr_continuous.html", 14);
|
||||
const bp = await setBreakpoint(threadClient, "doc_rr_continuous.html", 14);
|
||||
await resumeToLine(threadClient, 14);
|
||||
const value = await evaluateInTopFrame(threadClient, "number");
|
||||
await resumeToLine(threadClient, 14);
|
||||
@ -30,6 +30,7 @@ add_task(async function() {
|
||||
await rewindToLine(threadClient, 14);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", value + 2);
|
||||
|
||||
await threadClient.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -21,12 +21,13 @@ add_task(async function() {
|
||||
// Rewind to the beginning of the recording.
|
||||
await rewindToLine(threadClient, undefined);
|
||||
|
||||
await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(threadClient, "doc_rr_basic.html", 21);
|
||||
await resumeToLine(threadClient, 21);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 1);
|
||||
await resumeToLine(threadClient, 21);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 2);
|
||||
|
||||
await threadClient.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -28,12 +28,13 @@ add_task(async function() {
|
||||
// first reverse step takes us to the start of that line.
|
||||
await reverseStepOverToLine(threadClient, 19);
|
||||
await reverseStepOverToLine(threadClient, 18);
|
||||
await setBreakpoint(threadClient, "doc_rr_error.html", 12);
|
||||
const bp = await setBreakpoint(threadClient, "doc_rr_error.html", 12);
|
||||
await rewindToLine(threadClient, 12);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 4);
|
||||
await resumeToLine(threadClient, 12);
|
||||
await checkEvaluateInTopFrame(threadClient, "number", 5);
|
||||
|
||||
await threadClient.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -29,7 +29,7 @@ add_task(async function() {
|
||||
|
||||
const toolbox = await attachDebugger(replayingTab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
await rewindToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
await rewindToLine(client, 21);
|
||||
@ -37,6 +37,7 @@ add_task(async function() {
|
||||
await resumeToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(recordingTab);
|
||||
await gBrowser.removeTab(replayingTab);
|
||||
|
@ -19,7 +19,7 @@ add_task(async function() {
|
||||
|
||||
let toolbox = await attachDebugger(recordingTab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_continuous.html", 14);
|
||||
let bp = await setBreakpoint(client, "doc_rr_continuous.html", 14);
|
||||
await resumeToLine(client, 14);
|
||||
await resumeToLine(client, 14);
|
||||
await reverseStepOverToLine(client, 13);
|
||||
@ -30,6 +30,7 @@ add_task(async function() {
|
||||
ok(tabParent.saveRecording(recordingFile), "Saved recording");
|
||||
await once(Services.ppmm, "SaveRecordingFinished");
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(recordingTab);
|
||||
|
||||
@ -43,12 +44,13 @@ add_task(async function() {
|
||||
await client.interrupt();
|
||||
await checkEvaluateInTopFrame(client, "number", lastNumberValue);
|
||||
await reverseStepOverToLine(client, 13);
|
||||
await setBreakpoint(client, "doc_rr_continuous.html", 14);
|
||||
bp = await setBreakpoint(client, "doc_rr_continuous.html", 14);
|
||||
await rewindToLine(client, 14);
|
||||
await checkEvaluateInTopFrame(client, "number", lastNumberValue - 1);
|
||||
await resumeToLine(client, 14);
|
||||
await checkEvaluateInTopFrame(client, "number", lastNumberValue);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(replayingTab);
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ add_task(async function() {
|
||||
|
||||
const toolbox = await attachDebugger(tab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
await rewindToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
await reverseStepOverToLine(client, 20);
|
||||
@ -26,6 +26,7 @@ add_task(async function() {
|
||||
await stepOverToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ add_task(async function() {
|
||||
|
||||
const toolbox = await attachDebugger(tab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_basic.html", 22);
|
||||
const bp = await setBreakpoint(client, "doc_rr_basic.html", 22);
|
||||
await rewindToLine(client, 22);
|
||||
await stepInToLine(client, 25);
|
||||
await stepOverToLine(client, 26);
|
||||
@ -27,6 +27,7 @@ add_task(async function() {
|
||||
await reverseStepOutToLine(client, 26);
|
||||
await reverseStepOverToLine(client, 25);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -16,7 +16,7 @@ add_task(async function() {
|
||||
|
||||
const toolbox = await attachDebugger(tab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_continuous.html", 13);
|
||||
const bp = await setBreakpoint(client, "doc_rr_continuous.html", 13);
|
||||
await resumeToLine(client, 13);
|
||||
const value = await evaluateInTopFrame(client, "number");
|
||||
await reverseStepOverToLine(client, 12);
|
||||
@ -25,6 +25,7 @@ add_task(async function() {
|
||||
await resumeToLine(client, 13);
|
||||
await checkEvaluateInTopFrame(client, "number", value + 1);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ add_task(async function() {
|
||||
|
||||
const toolbox = await attachDebugger(tab), client = toolbox.threadClient;
|
||||
await client.interrupt();
|
||||
await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
const bp = await setBreakpoint(client, "doc_rr_basic.html", 21);
|
||||
await rewindToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
await reverseStepOverToLine(client, 20);
|
||||
@ -39,6 +39,7 @@ add_task(async function() {
|
||||
await stepOverToLine(client, 21);
|
||||
await checkEvaluateInTopFrame(client, "number", 10);
|
||||
|
||||
await client.removeBreakpoint(bp);
|
||||
await toolbox.destroy();
|
||||
await gBrowser.removeTab(tab);
|
||||
});
|
||||
|
@ -49,8 +49,9 @@ async function setBreakpoint(threadClient, expectedFile, lineno) {
|
||||
const {sources} = await threadClient.getSources();
|
||||
ok(sources.length == 1, "Got one source");
|
||||
ok(RegExp(expectedFile).test(sources[0].url), "Source is " + expectedFile);
|
||||
const sourceClient = threadClient.source(sources[0]);
|
||||
await sourceClient.setBreakpoint({ line: lineno });
|
||||
const location = { sourceUrl: sources[0].url, line: lineno };
|
||||
await threadClient.setBreakpoint(location, {});
|
||||
return location;
|
||||
}
|
||||
|
||||
function resumeThenPauseAtLineFunctionFactory(method) {
|
||||
@ -142,3 +143,8 @@ async function warpToMessage(hud, threadClient, text) {
|
||||
|
||||
return message;
|
||||
}
|
||||
|
||||
const { PromiseTestUtils } = scopedCuImport(
|
||||
"resource://testing-common/PromiseTestUtils.jsm"
|
||||
);
|
||||
PromiseTestUtils.whitelistRejectionsGlobally(/NS_ERROR_NOT_INITIALIZED/);
|
||||
|
@ -8,9 +8,6 @@
|
||||
|
||||
"use strict";
|
||||
|
||||
const { ActorClassWithSpec } = require("devtools/shared/protocol");
|
||||
const { breakpointSpec } = require("devtools/shared/specs/breakpoint");
|
||||
|
||||
/**
|
||||
* Set breakpoints on all the given entry points with the given
|
||||
* BreakpointActor as the handler.
|
||||
@ -29,31 +26,22 @@ function setBreakpointAtEntryPoints(actor, entryPoints) {
|
||||
exports.setBreakpointAtEntryPoints = setBreakpointAtEntryPoints;
|
||||
|
||||
/**
|
||||
* BreakpointActors exist for the lifetime of their containing thread and are
|
||||
* responsible for deleting breakpoints, handling breakpoint hits and
|
||||
* associating breakpoints with scripts.
|
||||
* BreakpointActors are instantiated for each breakpoint that has been installed
|
||||
* by the client. They are not true actors and do not communicate with the
|
||||
* client directly, but encapsulate the DebuggerScript locations where the
|
||||
* breakpoint is installed.
|
||||
*/
|
||||
const BreakpointActor = ActorClassWithSpec(breakpointSpec, {
|
||||
/**
|
||||
* Create a Breakpoint actor.
|
||||
*
|
||||
* @param ThreadActor threadActor
|
||||
* The parent thread actor that contains this breakpoint.
|
||||
* @param GeneratedLocation generatedLocation
|
||||
* The generated location of the breakpoint.
|
||||
*/
|
||||
initialize: function(threadActor, generatedLocation) {
|
||||
// A map from Debugger.Script instances to the offsets which the breakpoint
|
||||
// has been set for in that script.
|
||||
this.scripts = new Map();
|
||||
function BreakpointActor(threadActor, location) {
|
||||
// A map from Debugger.Script instances to the offsets which the breakpoint
|
||||
// has been set for in that script.
|
||||
this.scripts = new Map();
|
||||
|
||||
this.threadActor = threadActor;
|
||||
this.generatedLocation = generatedLocation;
|
||||
this.options = null;
|
||||
this.isPending = true;
|
||||
},
|
||||
this.threadActor = threadActor;
|
||||
this.location = location;
|
||||
this.options = null;
|
||||
}
|
||||
|
||||
// Called when new breakpoint options are received from the client.
|
||||
BreakpointActor.prototype = {
|
||||
setOptions(options) {
|
||||
for (const [script, offsets] of this.scripts) {
|
||||
this._updateOptionsForScript(script, offsets, this.options, options);
|
||||
@ -85,7 +73,6 @@ const BreakpointActor = ActorClassWithSpec(breakpointSpec, {
|
||||
script.setBreakpoint(offset, this);
|
||||
}
|
||||
|
||||
this.isPending = false;
|
||||
this._updateOptionsForScript(script, offsets, null, this.options);
|
||||
},
|
||||
|
||||
@ -241,18 +228,13 @@ const BreakpointActor = ActorClassWithSpec(breakpointSpec, {
|
||||
return this.threadActor._pauseAndRespond(frame, reason);
|
||||
},
|
||||
|
||||
/**
|
||||
* Handle a protocol request to remove this breakpoint.
|
||||
*/
|
||||
delete: function() {
|
||||
// Remove from the breakpoint store.
|
||||
if (this.generatedLocation) {
|
||||
this.threadActor.breakpointActorMap.deleteActor(this.generatedLocation);
|
||||
}
|
||||
this.threadActor.breakpointActorMap.deleteActor(this.location);
|
||||
this.threadActor.threadLifetimePool.removeActor(this);
|
||||
// Remove the actual breakpoint from the associated scripts.
|
||||
this.removeScripts();
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
exports.BreakpointActor = BreakpointActor;
|
||||
|
@ -7,8 +7,7 @@
|
||||
"use strict";
|
||||
|
||||
const { Ci } = require("chrome");
|
||||
const { BreakpointActor, setBreakpointAtEntryPoints } = require("devtools/server/actors/breakpoint");
|
||||
const { GeneratedLocation } = require("devtools/server/actors/common");
|
||||
const { setBreakpointAtEntryPoints } = require("devtools/server/actors/breakpoint");
|
||||
const { createValueGrip } = require("devtools/server/actors/object/utils");
|
||||
const { ActorClassWithSpec } = require("devtools/shared/protocol");
|
||||
const DevToolsUtils = require("devtools/shared/DevToolsUtils");
|
||||
@ -461,61 +460,6 @@ const SourceActor = ActorClassWithSpec(sourceSpec, {
|
||||
this.pausePoints = uncompressed;
|
||||
},
|
||||
|
||||
/**
|
||||
* Handle a request to set a breakpoint.
|
||||
*
|
||||
* @param Number line
|
||||
* Line to break on.
|
||||
* @param Number column
|
||||
* Column to break on.
|
||||
* @param Object options
|
||||
* Any options for the breakpoint.
|
||||
*
|
||||
* @returns Promise
|
||||
* A promise that resolves to a JSON object representing the
|
||||
* response.
|
||||
*/
|
||||
setBreakpoint: function(line, column, options) {
|
||||
const location = new GeneratedLocation(this, line, column);
|
||||
const actor = this._getOrCreateBreakpointActor(
|
||||
location,
|
||||
options
|
||||
);
|
||||
|
||||
return {
|
||||
actor: actor.actorID,
|
||||
isPending: actor.isPending,
|
||||
};
|
||||
},
|
||||
|
||||
/**
|
||||
* Get or create a BreakpointActor for the given location in the generated
|
||||
* source, and ensure it is set as a breakpoint handler on all scripts that
|
||||
* match the given location.
|
||||
*
|
||||
* @param GeneratedLocation generatedLocation
|
||||
* A GeneratedLocation representing the location of the breakpoint in
|
||||
* the generated source.
|
||||
* @param Object options
|
||||
* Any options for the breakpoint.
|
||||
*
|
||||
* @returns BreakpointActor
|
||||
* A BreakpointActor representing the breakpoint.
|
||||
*/
|
||||
_getOrCreateBreakpointActor: function(generatedLocation, options) {
|
||||
let actor = this.breakpointActorMap.getActor(generatedLocation);
|
||||
if (!actor) {
|
||||
actor = new BreakpointActor(this.threadActor, generatedLocation);
|
||||
this.threadActor.threadLifetimePool.addActor(actor);
|
||||
this.breakpointActorMap.setActor(generatedLocation, actor);
|
||||
}
|
||||
|
||||
actor.setOptions(options);
|
||||
|
||||
this._setBreakpoint(actor);
|
||||
return actor;
|
||||
},
|
||||
|
||||
/*
|
||||
* Ensure the given BreakpointActor is set as a breakpoint handler on all
|
||||
* scripts that match its location in the generated source.
|
||||
@ -525,31 +469,21 @@ const SourceActor = ActorClassWithSpec(sourceSpec, {
|
||||
*
|
||||
* @returns A Promise that resolves to the given BreakpointActor.
|
||||
*/
|
||||
_setBreakpoint: function(actor) {
|
||||
const { generatedLocation } = actor;
|
||||
|
||||
const {
|
||||
generatedSourceActor,
|
||||
generatedLine,
|
||||
generatedColumn,
|
||||
generatedLastColumn,
|
||||
} = generatedLocation;
|
||||
applyBreakpoint: function(actor) {
|
||||
const { line, column } = actor.location;
|
||||
|
||||
// Find all scripts that match the given source actor and line
|
||||
// number.
|
||||
let scripts = generatedSourceActor._findDebuggeeScripts(
|
||||
{ line: generatedLine }
|
||||
);
|
||||
|
||||
let scripts = this._findDebuggeeScripts({ line });
|
||||
scripts = scripts.filter((script) => !actor.hasScript(script));
|
||||
|
||||
// Find all entry points that correspond to the given location.
|
||||
const entryPoints = [];
|
||||
if (generatedColumn === undefined) {
|
||||
if (column === undefined) {
|
||||
// This is a line breakpoint, so we are interested in all offsets
|
||||
// that correspond to the given line number.
|
||||
for (const script of scripts) {
|
||||
const offsets = script.getLineOffsets(generatedLine);
|
||||
const offsets = script.getLineOffsets(line);
|
||||
if (offsets.length > 0) {
|
||||
entryPoints.push({ script, offsets });
|
||||
}
|
||||
@ -561,15 +495,15 @@ const SourceActor = ActorClassWithSpec(sourceSpec, {
|
||||
[
|
||||
script,
|
||||
script.getAllColumnOffsets()
|
||||
.filter(({ lineNumber }) => lineNumber === generatedLine),
|
||||
.filter(({ lineNumber }) => lineNumber === line),
|
||||
]
|
||||
);
|
||||
|
||||
// This is a column breakpoint, so we are interested in all column
|
||||
// offsets that correspond to the given line *and* column number.
|
||||
for (const [script, columnToOffsetMap] of columnToOffsetMaps) {
|
||||
for (const { columnNumber: column, offset } of columnToOffsetMap) {
|
||||
if (column >= generatedColumn && column <= generatedLastColumn) {
|
||||
for (const { columnNumber, offset } of columnToOffsetMap) {
|
||||
if (columnNumber >= column && columnNumber <= column + 1) {
|
||||
entryPoints.push({ script, offsets: [offset] });
|
||||
}
|
||||
}
|
||||
@ -584,8 +518,8 @@ const SourceActor = ActorClassWithSpec(sourceSpec, {
|
||||
// of caution by handling it here.
|
||||
const closestScripts = findClosestScriptBySource(
|
||||
columnToOffsetMaps.map(pair => pair[0]),
|
||||
generatedLine,
|
||||
generatedColumn,
|
||||
line,
|
||||
column,
|
||||
);
|
||||
|
||||
const columnToOffsetLookup = new Map(columnToOffsetMaps);
|
||||
@ -596,11 +530,11 @@ const SourceActor = ActorClassWithSpec(sourceSpec, {
|
||||
const firstColumnOffset = columnToOffsetMap[0];
|
||||
const lastColumnOffset = columnToOffsetMap[columnToOffsetMap.length - 1];
|
||||
|
||||
if (generatedColumn < firstColumnOffset.columnNumber) {
|
||||
if (column < firstColumnOffset.columnNumber) {
|
||||
entryPoints.push({ script, offsets: [firstColumnOffset.offset] });
|
||||
}
|
||||
|
||||
if (generatedColumn > lastColumnOffset.columnNumber) {
|
||||
if (column > lastColumnOffset.columnNumber) {
|
||||
entryPoints.push({ script, offsets: [lastColumnOffset.offset] });
|
||||
}
|
||||
}
|
||||
|
@ -18,7 +18,6 @@ const { threadSpec } = require("devtools/shared/specs/script");
|
||||
|
||||
loader.lazyRequireGetter(this, "findCssSelector", "devtools/shared/inspector/css-logic", true);
|
||||
loader.lazyRequireGetter(this, "EnvironmentActor", "devtools/server/actors/environment", true);
|
||||
loader.lazyRequireGetter(this, "SourceActorStore", "devtools/server/actors/utils/source-actor-store", true);
|
||||
loader.lazyRequireGetter(this, "BreakpointActorMap", "devtools/server/actors/utils/breakpoint-actor-map", true);
|
||||
loader.lazyRequireGetter(this, "PauseScopedObjectActor", "devtools/server/actors/pause-scoped", true);
|
||||
loader.lazyRequireGetter(this, "EventLoopStack", "devtools/server/actors/utils/event-loop", true);
|
||||
@ -66,8 +65,7 @@ const ThreadActor = ActorClassWithSpec(threadSpec, {
|
||||
autoBlackBox: false,
|
||||
};
|
||||
|
||||
this.breakpointActorMap = new BreakpointActorMap();
|
||||
this.sourceActorStore = new SourceActorStore();
|
||||
this.breakpointActorMap = new BreakpointActorMap(this);
|
||||
|
||||
this._debuggerSourcesSeen = null;
|
||||
|
||||
@ -152,6 +150,10 @@ const ThreadActor = ActorClassWithSpec(threadSpec, {
|
||||
return this._parent.sources;
|
||||
},
|
||||
|
||||
get breakpoints() {
|
||||
return this._parent.breakpoints;
|
||||
},
|
||||
|
||||
get youngestFrame() {
|
||||
if (this.state != "paused") {
|
||||
return null;
|
||||
@ -209,11 +211,6 @@ const ThreadActor = ActorClassWithSpec(threadSpec, {
|
||||
this.onResume();
|
||||
}
|
||||
|
||||
// Blow away our source actor ID store because those IDs are only
|
||||
// valid for this connection. This is ok because we never keep
|
||||
// things like breakpoints across connections.
|
||||
this._sourceActorStore = null;
|
||||
|
||||
this._xhrBreakpoints = [];
|
||||
this._updateNetworkObserver();
|
||||
|
||||
@ -316,6 +313,24 @@ const ThreadActor = ActorClassWithSpec(threadSpec, {
|
||||
({ path, method }) => path === p && method === m);
|
||||
},
|
||||
|
||||
setBreakpoint(location, options) {
|
||||
const actor = this.breakpointActorMap.getOrCreateBreakpointActor(location);
|
||||
actor.setOptions(options);
|
||||
|
||||
const sourceActor = location.sourceUrl
|
||||
? this.sources.getSourceActorByURL(location.sourceUrl)
|
||||
: this.sources.getSourceActorById(location.sourceId);
|
||||
|
||||
if (sourceActor) {
|
||||
sourceActor.applyBreakpoint(actor);
|
||||
}
|
||||
},
|
||||
|
||||
removeBreakpoint(location) {
|
||||
const actor = this.breakpointActorMap.getOrCreateBreakpointActor(location);
|
||||
actor.delete();
|
||||
},
|
||||
|
||||
removeXHRBreakpoint: function(path, method) {
|
||||
const index = this._findXHRBreakpointIndex(path, method);
|
||||
|
||||
@ -1786,30 +1801,17 @@ const ThreadActor = ActorClassWithSpec(threadSpec, {
|
||||
sourceActor = this.sources.createSourceActor(source);
|
||||
}
|
||||
|
||||
const bpActors = [...this.breakpointActorMap.findActors()]
|
||||
.filter((actor) => {
|
||||
const bpSource = actor.generatedLocation.generatedSourceActor;
|
||||
return bpSource.source ? bpSource.source === source : bpSource.url === source.url;
|
||||
});
|
||||
|
||||
// Bug 1225160: If addSource is called in response to a new script
|
||||
// notification, and this notification was triggered by loading a JSM from
|
||||
// chrome code, calling unsafeSynchronize could cause a debuggee timer to
|
||||
// fire. If this causes the JSM to be loaded a second time, the browser
|
||||
// will crash, because loading JSMS is not reentrant, and the first load
|
||||
// has not completed yet.
|
||||
//
|
||||
// The root of the problem is that unsafeSynchronize can cause debuggee
|
||||
// code to run. Unfortunately, fixing that is prohibitively difficult. The
|
||||
// best we can do at the moment is disable source maps for the browser
|
||||
// debugger, and carefully avoid the use of unsafeSynchronize in this
|
||||
// function when source maps are disabled.
|
||||
for (const actor of bpActors) {
|
||||
actor.generatedLocation.generatedSourceActor._setBreakpoint(actor);
|
||||
if (this._onLoadBreakpointURLs.has(source.url)) {
|
||||
this.setBreakpoint({ sourceUrl: source.url, line: 1 }, {});
|
||||
}
|
||||
|
||||
if (this._onLoadBreakpointURLs.has(source.url)) {
|
||||
sourceActor.setBreakpoint(1);
|
||||
const bpActors = this.breakpointActorMap.findActors()
|
||||
.filter((actor) => {
|
||||
return actor.location.sourceUrl && actor.location.sourceUrl == source.url;
|
||||
});
|
||||
|
||||
for (const actor of bpActors) {
|
||||
sourceActor.applyBreakpoint(actor);
|
||||
}
|
||||
|
||||
this._debuggerSourcesSeen.add(source);
|
||||
|
@ -117,14 +117,7 @@ TabSources.prototype = {
|
||||
contentType: contentType,
|
||||
});
|
||||
|
||||
const sourceActorStore = this._thread.sourceActorStore;
|
||||
const id = sourceActorStore.getReusableActorId(source, originalUrl);
|
||||
if (id) {
|
||||
actor.actorID = id;
|
||||
}
|
||||
|
||||
this._thread.threadLifetimePool.addActor(actor);
|
||||
sourceActorStore.setReusableActorId(source, originalUrl, actor.actorID);
|
||||
|
||||
if (this._autoBlackBox &&
|
||||
!this.neverAutoBlackBoxSources.has(actor.url) &&
|
||||
@ -182,8 +175,16 @@ TabSources.prototype = {
|
||||
return this._htmlDocumentSourceActors[url];
|
||||
}
|
||||
}
|
||||
return null;
|
||||
},
|
||||
|
||||
throw new Error("getSourceActorByURL: could not find source for " + url);
|
||||
getSourceActorById(actorId) {
|
||||
for (const [, actor] of this._sourceActors) {
|
||||
if (actor.actorID == actorId) {
|
||||
return actor;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -6,169 +6,59 @@
|
||||
|
||||
"use strict";
|
||||
|
||||
const { GeneratedLocation } = require("devtools/server/actors/common");
|
||||
const { BreakpointActor } = require("devtools/server/actors/breakpoint");
|
||||
|
||||
/**
|
||||
* A BreakpointActorMap is a map from locations to instances of BreakpointActor.
|
||||
*/
|
||||
function BreakpointActorMap() {
|
||||
this._size = 0;
|
||||
function BreakpointActorMap(threadActor) {
|
||||
this._threadActor = threadActor;
|
||||
this._actors = {};
|
||||
}
|
||||
|
||||
BreakpointActorMap.prototype = {
|
||||
/**
|
||||
* Return the number of BreakpointActors in this BreakpointActorMap.
|
||||
*
|
||||
* @returns Number
|
||||
* The number of BreakpointActor in this BreakpointActorMap.
|
||||
*/
|
||||
get size() {
|
||||
return this._size;
|
||||
// Get the key in the _actors table for a given breakpoint location.
|
||||
// See also duplicate code in commands.js :(
|
||||
_locationKey(location) {
|
||||
const { sourceUrl, sourceId, line, column } = location;
|
||||
return `${sourceUrl}:${sourceId}:${line}:${column}`;
|
||||
},
|
||||
|
||||
/**
|
||||
* Generate all BreakpointActors that match the given location in
|
||||
* this BreakpointActorMap.
|
||||
*
|
||||
* @param GeneratedLocation location
|
||||
* The location for which matching BreakpointActors should be generated.
|
||||
* Return all BreakpointActors in this BreakpointActorMap.
|
||||
*/
|
||||
findActors: function* (location = new GeneratedLocation()) {
|
||||
// Fast shortcut for when we know we won't find any actors. Surprisingly
|
||||
// enough, this speeds up refreshing when there are no breakpoints set by
|
||||
// about 2x!
|
||||
if (this.size === 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
function* findKeys(obj, key) {
|
||||
if (key !== undefined) {
|
||||
if (key in obj) {
|
||||
yield key;
|
||||
}
|
||||
} else {
|
||||
for (key of Object.keys(obj)) {
|
||||
yield key;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const query = {
|
||||
sourceActorID: location.generatedSourceActor
|
||||
? location.generatedSourceActor.actorID
|
||||
: undefined,
|
||||
line: location.generatedLine,
|
||||
};
|
||||
|
||||
// If location contains a line, assume we are searching for a whole line
|
||||
// breakpoint, and set begin/endColumn accordingly. Otherwise, we are
|
||||
// searching for all breakpoints, so begin/endColumn should be left unset.
|
||||
if (location.generatedLine) {
|
||||
query.beginColumn = location.generatedColumn ? location.generatedColumn : 0;
|
||||
query.endColumn = location.generatedColumn
|
||||
? location.generatedColumn + 1
|
||||
: Infinity;
|
||||
} else {
|
||||
query.beginColumn = location.generatedColumn ? query.generatedColumn : undefined;
|
||||
query.endColumn = location.generatedColumn ? query.generatedColumn + 1 : undefined;
|
||||
}
|
||||
|
||||
for (const sourceActorID of findKeys(this._actors, query.sourceActorID)) {
|
||||
const actor = this._actors[sourceActorID];
|
||||
for (const line of findKeys(actor, query.line)) {
|
||||
for (const beginColumn of findKeys(actor[line], query.beginColumn)) {
|
||||
for (const endColumn of findKeys(actor[line][beginColumn],
|
||||
query.endColumn)) {
|
||||
yield actor[line][beginColumn][endColumn];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
findActors() {
|
||||
return Object.values(this._actors);
|
||||
},
|
||||
|
||||
/**
|
||||
* Return the BreakpointActor at the given location in this
|
||||
* BreakpointActorMap.
|
||||
*
|
||||
* @param GeneratedLocation location
|
||||
* @param BreakpointLocation location
|
||||
* The location for which the BreakpointActor should be returned.
|
||||
*
|
||||
* @returns BreakpointActor actor
|
||||
* The BreakpointActor at the given location.
|
||||
*/
|
||||
getActor: function(generatedLocation) {
|
||||
for (const actor of this.findActors(generatedLocation)) {
|
||||
return actor;
|
||||
getOrCreateBreakpointActor(location) {
|
||||
const key = this._locationKey(location);
|
||||
if (!this._actors[key]) {
|
||||
this._actors[key] = new BreakpointActor(this._threadActor, location);
|
||||
}
|
||||
|
||||
return null;
|
||||
},
|
||||
|
||||
/**
|
||||
* Set the given BreakpointActor to the given location in this
|
||||
* BreakpointActorMap.
|
||||
*
|
||||
* @param GeneratedLocation location
|
||||
* The location to which the given BreakpointActor should be set.
|
||||
*
|
||||
* @param BreakpointActor actor
|
||||
* The BreakpointActor to be set to the given location.
|
||||
*/
|
||||
setActor: function(location, actor) {
|
||||
const { generatedSourceActor, generatedLine, generatedColumn } = location;
|
||||
|
||||
const sourceActorID = generatedSourceActor.actorID;
|
||||
const line = generatedLine;
|
||||
const beginColumn = generatedColumn ? generatedColumn : 0;
|
||||
const endColumn = generatedColumn ? generatedColumn + 1 : Infinity;
|
||||
|
||||
if (!this._actors[sourceActorID]) {
|
||||
this._actors[sourceActorID] = [];
|
||||
}
|
||||
if (!this._actors[sourceActorID][line]) {
|
||||
this._actors[sourceActorID][line] = [];
|
||||
}
|
||||
if (!this._actors[sourceActorID][line][beginColumn]) {
|
||||
this._actors[sourceActorID][line][beginColumn] = [];
|
||||
}
|
||||
if (!this._actors[sourceActorID][line][beginColumn][endColumn]) {
|
||||
++this._size;
|
||||
}
|
||||
this._actors[sourceActorID][line][beginColumn][endColumn] = actor;
|
||||
return this._actors[key];
|
||||
},
|
||||
|
||||
/**
|
||||
* Delete the BreakpointActor from the given location in this
|
||||
* BreakpointActorMap.
|
||||
*
|
||||
* @param GeneratedLocation location
|
||||
* @param BreakpointLocation location
|
||||
* The location from which the BreakpointActor should be deleted.
|
||||
*/
|
||||
deleteActor: function(location) {
|
||||
const { generatedSourceActor, generatedLine, generatedColumn } = location;
|
||||
|
||||
const sourceActorID = generatedSourceActor.actorID;
|
||||
const line = generatedLine;
|
||||
const beginColumn = generatedColumn ? generatedColumn : 0;
|
||||
const endColumn = generatedColumn ? generatedColumn + 1 : Infinity;
|
||||
|
||||
if (this._actors[sourceActorID]) {
|
||||
if (this._actors[sourceActorID][line]) {
|
||||
if (this._actors[sourceActorID][line][beginColumn]) {
|
||||
if (this._actors[sourceActorID][line][beginColumn][endColumn]) {
|
||||
--this._size;
|
||||
}
|
||||
delete this._actors[sourceActorID][line][beginColumn][endColumn];
|
||||
if (Object.keys(this._actors[sourceActorID][line][beginColumn]).length === 0) {
|
||||
delete this._actors[sourceActorID][line][beginColumn];
|
||||
}
|
||||
}
|
||||
if (Object.keys(this._actors[sourceActorID][line]).length === 0) {
|
||||
delete this._actors[sourceActorID][line];
|
||||
}
|
||||
}
|
||||
}
|
||||
deleteActor(location) {
|
||||
const key = this._locationKey(location);
|
||||
delete this._actors[key];
|
||||
},
|
||||
};
|
||||
|
||||
|
@ -19,7 +19,6 @@ DevToolsModules(
|
||||
'function-call.js',
|
||||
'make-debugger.js',
|
||||
'shapes-utils.js',
|
||||
'source-actor-store.js',
|
||||
'stack.js',
|
||||
'TabSources.js',
|
||||
'track-change-emitter.js',
|
||||
|
@ -1,57 +0,0 @@
|
||||
/* -*- indent-tabs-mode: nil; js-indent-level: 2; js-indent-level: 2 -*- */
|
||||
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
loader.lazyRequireGetter(this, "getSourceURL", "devtools/server/actors/source", true);
|
||||
|
||||
/**
|
||||
* Keeps track of persistent sources across reloads and ties different
|
||||
* source instances to the same actor id so that things like
|
||||
* breakpoints survive reloads. ThreadSources uses this to force the
|
||||
* same actorID on a SourceActor.
|
||||
*/
|
||||
function SourceActorStore() {
|
||||
// source identifier --> actor id
|
||||
this._sourceActorIds = Object.create(null);
|
||||
}
|
||||
|
||||
SourceActorStore.prototype = {
|
||||
/**
|
||||
* Lookup an existing actor id that represents this source, if available.
|
||||
*/
|
||||
getReusableActorId: function(source, originalUrl) {
|
||||
const url = this.getUniqueKey(source, originalUrl);
|
||||
if (url && url in this._sourceActorIds) {
|
||||
return this._sourceActorIds[url];
|
||||
}
|
||||
return null;
|
||||
},
|
||||
|
||||
/**
|
||||
* Update a source with an actorID.
|
||||
*/
|
||||
setReusableActorId: function(source, originalUrl, actorID) {
|
||||
const url = this.getUniqueKey(source, originalUrl);
|
||||
if (url) {
|
||||
this._sourceActorIds[url] = actorID;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Make a unique URL from a source that identifies it across reloads.
|
||||
*/
|
||||
getUniqueKey: function(source, originalUrl) {
|
||||
if (originalUrl) {
|
||||
// Original source from a sourcemap.
|
||||
return originalUrl;
|
||||
}
|
||||
|
||||
return getSourceURL(source);
|
||||
},
|
||||
};
|
||||
|
||||
exports.SourceActorStore = SourceActorStore;
|
@ -249,9 +249,9 @@ function waitForProperty(dbg, property) {
|
||||
});
|
||||
}
|
||||
|
||||
function setBreakpoint(sourceClient, location) {
|
||||
function setBreakpoint(threadClient, location) {
|
||||
dump("Setting breakpoint.\n");
|
||||
return sourceClient.setBreakpoint(location);
|
||||
return threadClient.setBreakpoint(location, {});
|
||||
}
|
||||
|
||||
function getPrototypeAndProperties(objClient) {
|
||||
|
@ -36,7 +36,7 @@ const testBlackBox = async function() {
|
||||
packet.frame.where.actor
|
||||
);
|
||||
|
||||
await setBreakpoint(bpSource, { line: 2 });
|
||||
await setBreakpoint(gThreadClient, { sourceUrl: bpSource.url, line: 2 });
|
||||
await resume(gThreadClient);
|
||||
|
||||
let sourceForm = await getSourceForm(gThreadClient, BLACK_BOXED_URL);
|
||||
|
@ -43,11 +43,8 @@ function test_black_box() {
|
||||
|
||||
function runWithSource(packet) {
|
||||
const source = gThreadClient.source(packet.source);
|
||||
source.setBreakpoint({
|
||||
line: 2,
|
||||
}).then(function() {
|
||||
gThreadClient.resume(test_black_box_breakpoint);
|
||||
});
|
||||
gThreadClient.setBreakpoint({ sourceUrl: source.url, line: 2 }, {});
|
||||
gThreadClient.resume(test_black_box_breakpoint);
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -11,7 +11,6 @@
|
||||
var gDebuggee;
|
||||
var gClient;
|
||||
var gThreadClient;
|
||||
var gBpClient;
|
||||
|
||||
function run_test() {
|
||||
initTestDebuggerServer();
|
||||
@ -33,8 +32,7 @@ const SOURCE_URL = "http://example.com/source.js";
|
||||
function test_black_box() {
|
||||
gClient.addOneTimeListener("paused", async function(event, packet) {
|
||||
const source = await getSourceById(gThreadClient, packet.frame.where.actor);
|
||||
const [, bpClient] = await source.setBreakpoint({ line: 4 });
|
||||
gBpClient = bpClient;
|
||||
gThreadClient.setBreakpoint({ sourceUrl: source.url, line: 4 }, {});
|
||||
await gThreadClient.resume();
|
||||
test_black_box_dbg_statement();
|
||||
});
|
||||
@ -79,7 +77,9 @@ function test_black_box_dbg_statement() {
|
||||
Assert.equal(packet.why.type, "breakpoint",
|
||||
"We should pass over the debugger statement.");
|
||||
|
||||
await gBpClient.remove();
|
||||
const source = await getSourceById(gThreadClient, packet.frame.where.actor);
|
||||
gThreadClient.removeBreakpoint({ sourceUrl: source.url, line: 4 }, {});
|
||||
|
||||
await gThreadClient.resume();
|
||||
await test_unblack_box_dbg_statement(sourceClient);
|
||||
});
|
||||
|
@ -40,9 +40,8 @@ function test_black_box() {
|
||||
|
||||
function runWithSource(packet) {
|
||||
const source = gThreadClient.source(packet.source);
|
||||
source.setBreakpoint({
|
||||
line: 2,
|
||||
}).then(test_black_box_paused);
|
||||
gThreadClient.setBreakpoint({ sourceUrl: source.url, line: 2 }, {});
|
||||
test_black_box_paused();
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -31,8 +31,8 @@ function run_test() {
|
||||
const { sources } = await getSources(threadClient);
|
||||
const sourceClient = threadClient.source(sources[0]);
|
||||
|
||||
await setBreakpoint(sourceClient, { line: 7 });
|
||||
await setBreakpoint(sourceClient, { line: 11 });
|
||||
await setBreakpoint(threadClient, { sourceUrl: sourceClient.url, line: 7 });
|
||||
await setBreakpoint(threadClient, { sourceUrl: sourceClient.url, line: 11 });
|
||||
|
||||
// 1. lets blackbox function a, and assert that we pause in b
|
||||
const range = {start: { line: 6, column: 0 }, end: { line: 8, colum: 1 }};
|
||||
|
@ -17,9 +17,9 @@ add_task(threadClientTest(async ({ threadClient, debuggee }) => {
|
||||
packet.frame.where.actor
|
||||
);
|
||||
|
||||
const location = { line: debuggee.line0 + 3 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 3 };
|
||||
|
||||
const [, bpClient] = await source.setBreakpoint(location);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
await threadClient.resume();
|
||||
packet = await waitForPause(threadClient);
|
||||
@ -29,13 +29,11 @@ add_task(threadClientTest(async ({ threadClient, debuggee }) => {
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
|
||||
info("Check that the breakpoint worked.");
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
|
||||
await bpClient.remove();
|
||||
await threadClient.resume();
|
||||
})();
|
||||
|
||||
|
@ -11,11 +11,11 @@
|
||||
add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
return new Promise((resolve) => {
|
||||
threadClient.addOneTimeListener("paused", async function(event, packet) {
|
||||
const location = { line: debuggee.line0 + 3 };
|
||||
const source = await getSourceById(
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 3 };
|
||||
|
||||
threadClient.resume();
|
||||
|
||||
@ -25,15 +25,8 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
Assert.equal(packet.why.type, "interrupted");
|
||||
});
|
||||
|
||||
source.setBreakpoint(location).then(function() {
|
||||
executeSoon(resolve);
|
||||
}, function(response) {
|
||||
// Eval scripts don't stick around long enough for the breakpoint to be set,
|
||||
// so just make sure we got the expected response from the actor.
|
||||
Assert.notEqual(response.error, "noScript");
|
||||
|
||||
executeSoon(resolve);
|
||||
});
|
||||
threadClient.setBreakpoint(location, {});
|
||||
executeSoon(resolve);
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -15,32 +15,27 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 3 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 3 };
|
||||
|
||||
source.setBreakpoint(location).then(function([response, bpClient]) {
|
||||
// actualLocation is not returned when breakpoints don't skip forward.
|
||||
Assert.equal(response.actualLocation, undefined);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
// Remove the breakpoint.
|
||||
threadClient.removeBreakpoint(location);
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -16,35 +16,33 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 2 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 2 };
|
||||
|
||||
source.setBreakpoint(location).then(function([response, bpClient]) {
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, undefined);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, undefined);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
done = true;
|
||||
threadClient.addOneTimeListener("paused",
|
||||
function(event, packet) {
|
||||
// Remove the breakpoint.
|
||||
threadClient.removeBreakpoint(location);
|
||||
done = true;
|
||||
threadClient.addOneTimeListener("paused",
|
||||
function(event, packet) {
|
||||
// The breakpoint should not be hit again.
|
||||
threadClient.resume(function() {
|
||||
Assert.ok(false);
|
||||
});
|
||||
});
|
||||
threadClient.resume();
|
||||
});
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume(function() {
|
||||
Assert.ok(false);
|
||||
});
|
||||
});
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -16,40 +16,36 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 3 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 3 };
|
||||
|
||||
source.setBreakpoint(location).then(function([response, bpClient]) {
|
||||
// actualLocation is not returned when breakpoints don't skip forward.
|
||||
Assert.equal(response.actualLocation, undefined);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.i, 0);
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.i, 0);
|
||||
Assert.equal(debuggee.i, 1);
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.i, 1);
|
||||
// Remove the breakpoint.
|
||||
threadClient.removeBreakpoint(location);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit again.
|
||||
threadClient.resume();
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
|
||||
// Continue until the breakpoint is hit again.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -16,41 +16,37 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 2 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 2 };
|
||||
|
||||
source.setBreakpoint(location).then(function([response, bpClient]) {
|
||||
// actualLocation is not returned when breakpoints don't skip forward.
|
||||
Assert.equal(response.actualLocation, undefined);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, undefined);
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a, undefined);
|
||||
Assert.equal(debuggee.a.b, 1);
|
||||
Assert.equal(debuggee.res, undefined);
|
||||
|
||||
threadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
// Check that the breakpoint worked.
|
||||
Assert.equal(debuggee.a.b, 1);
|
||||
Assert.equal(debuggee.res, undefined);
|
||||
// Remove the breakpoint.
|
||||
threadClient.removeBreakpoint(location);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit again.
|
||||
threadClient.resume();
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
|
||||
// Continue until the breakpoint is hit again.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -16,65 +16,67 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 2 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 2 };
|
||||
|
||||
source.setBreakpoint(location).then(async function([response, bpClient]) {
|
||||
const testCallbacks = [
|
||||
function(packet) {
|
||||
// Check that the stepping worked.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 5);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Entered the foo function call frame.
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// At the end of the foo function call frame.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the breakpoint wasn't the reason for this pause, but
|
||||
// that the frame is about to be popped while stepping.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.why.frameFinished.return.type, "undefined");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 6);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.poppedFrames.length, 1);
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 7);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
];
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
for (const callback of testCallbacks) {
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepIn();
|
||||
const packet = await waiter;
|
||||
callback(packet);
|
||||
}
|
||||
const testCallbacks = [
|
||||
function(packet) {
|
||||
// Check that the stepping worked.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 5);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Entered the foo function call frame.
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// At the end of the foo function call frame.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the breakpoint wasn't the reason for this pause, but
|
||||
// that the frame is about to be popped while stepping.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.why.frameFinished.return.type, "undefined");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 6);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.poppedFrames.length, 1);
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 7);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
];
|
||||
|
||||
// Remove the breakpoint and finish.
|
||||
for (const callback of testCallbacks) {
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepIn();
|
||||
await waiter;
|
||||
bpClient.remove(() => threadClient.resume(resolve));
|
||||
});
|
||||
const packet = await waiter;
|
||||
callback(packet);
|
||||
}
|
||||
|
||||
// Remove the breakpoint and finish.
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepIn();
|
||||
await waiter;
|
||||
threadClient.removeBreakpoint(location);
|
||||
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -16,63 +16,63 @@ add_task(threadClientTest(({ threadClient, debuggee }) => {
|
||||
threadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = { line: debuggee.line0 + 2 };
|
||||
const location = { sourceUrl: source.url, line: debuggee.line0 + 2 };
|
||||
|
||||
source.setBreakpoint(location).then(async function([response, bpClient]) {
|
||||
const testCallbacks = [
|
||||
function(packet) {
|
||||
// Check that the stepping worked.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 5);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Reached the breakpoint.
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.notEqual(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Stepped to the closing brace of the function.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// The frame is about to be popped while stepping.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.why.frameFinished.return.type, "undefined");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 6);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.poppedFrames.length, 1);
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 7);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
];
|
||||
threadClient.setBreakpoint(location, {});
|
||||
const testCallbacks = [
|
||||
function(packet) {
|
||||
// Check that the stepping worked.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 5);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Reached the breakpoint.
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.notEqual(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// Stepped to the closing brace of the function.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
function(packet) {
|
||||
// The frame is about to be popped while stepping.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 3);
|
||||
Assert.notEqual(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.why.frameFinished.return.type, "undefined");
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(debuggee.a, 1);
|
||||
Assert.equal(debuggee.b, undefined);
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 6);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
Assert.equal(packet.poppedFrames.length, 1);
|
||||
},
|
||||
function(packet) {
|
||||
// Check that the debugger statement wasn't the reason for this pause.
|
||||
Assert.equal(packet.frame.where.line, debuggee.line0 + 7);
|
||||
Assert.notEqual(packet.why.type, "debuggerStatement");
|
||||
Assert.equal(packet.why.type, "resumeLimit");
|
||||
},
|
||||
];
|
||||
|
||||
for (const callback of testCallbacks) {
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepOver();
|
||||
const packet = await waiter;
|
||||
callback(packet);
|
||||
}
|
||||
|
||||
// Remove the breakpoint and finish.
|
||||
for (const callback of testCallbacks) {
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepOver();
|
||||
await waiter;
|
||||
bpClient.remove(() => threadClient.resume(resolve));
|
||||
});
|
||||
const packet = await waiter;
|
||||
callback(packet);
|
||||
}
|
||||
|
||||
// Remove the breakpoint and finish.
|
||||
const waiter = waitForPause(threadClient);
|
||||
threadClient.stepOver();
|
||||
await waiter;
|
||||
threadClient.removeBreakpoint(location);
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -17,37 +17,36 @@ add_task(threadClientTest(({ threadClient, debuggee, client }) => {
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = {
|
||||
sourceUrl: source.url,
|
||||
line: debuggee.line0 + 1,
|
||||
column: 55,
|
||||
};
|
||||
let timesBreakpointHit = 0;
|
||||
|
||||
source.setBreakpoint(location).then(function([response, bpClient]) {
|
||||
threadClient.addListener("paused", function onPaused(event, packet) {
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.frame.where.column, location.column);
|
||||
threadClient.setBreakpoint(location, {});
|
||||
|
||||
Assert.equal(debuggee.acc, timesBreakpointHit);
|
||||
Assert.equal(packet.frame.environment.bindings.variables.i.value,
|
||||
timesBreakpointHit);
|
||||
threadClient.addListener("paused", function onPaused(event, packet) {
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
Assert.equal(packet.frame.where.column, location.column);
|
||||
|
||||
if (++timesBreakpointHit === 3) {
|
||||
threadClient.removeListener("paused", onPaused);
|
||||
bpClient.remove(function(response) {
|
||||
threadClient.resume(resolve);
|
||||
});
|
||||
} else {
|
||||
threadClient.resume();
|
||||
}
|
||||
});
|
||||
Assert.equal(debuggee.acc, timesBreakpointHit);
|
||||
Assert.equal(packet.frame.environment.bindings.variables.i.value,
|
||||
timesBreakpointHit);
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
if (++timesBreakpointHit === 3) {
|
||||
threadClient.removeListener("paused", onPaused);
|
||||
threadClient.removeBreakpoint(location);
|
||||
threadClient.resume(resolve);
|
||||
} else {
|
||||
threadClient.resume();
|
||||
}
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
threadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -51,9 +51,8 @@ function setBreakpoint(packet, threadClient, client) {
|
||||
);
|
||||
client.addOneTimeListener("resumed", resolve);
|
||||
|
||||
source.setBreakpoint({ line: 3 }).then(() => {
|
||||
threadClient.resume();
|
||||
});
|
||||
threadClient.setBreakpoint({ sourceUrl: source.url, line: 3 }, {});
|
||||
threadClient.resume();
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -26,17 +26,11 @@ function setUpCode(debuggee) {
|
||||
}
|
||||
|
||||
add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const source = await getSource(threadClient, URL);
|
||||
const [response ] = await setBreakpoint(source, {line: 2});
|
||||
ok(!response.error);
|
||||
|
||||
const actor = response.actor;
|
||||
ok(actor);
|
||||
setBreakpoint(threadClient, { sourceUrl: URL, line: 2});
|
||||
|
||||
await executeOnNextTickAndWaitForPause(() => setUpCode(debuggee), client);
|
||||
await resume(threadClient);
|
||||
|
||||
const packet = await executeOnNextTickAndWaitForPause(debuggee.test, client);
|
||||
equal(packet.why.type, "breakpoint");
|
||||
notEqual(packet.why.actors.indexOf(actor), -1);
|
||||
}));
|
||||
|
@ -34,13 +34,7 @@ const testBreakpoint = async function(threadResponse, targetFront,
|
||||
// Set a breakpoint in the test source.
|
||||
|
||||
const source = await getSource(threadClient, "test.js");
|
||||
const [response ] = await setBreakpoint(source, {
|
||||
line: 3,
|
||||
});
|
||||
ok(!response.error, "Shouldn't get an error setting the BP.");
|
||||
ok(!response.actualLocation,
|
||||
"Shouldn't get an actualLocation, the location we provided was good.");
|
||||
const bpActor = response.actor;
|
||||
setBreakpoint(threadClient, { sourceUrl: source.url, line: 3 });
|
||||
|
||||
await resume(threadClient);
|
||||
|
||||
@ -57,8 +51,6 @@ const testBreakpoint = async function(threadResponse, targetFront,
|
||||
gClient);
|
||||
equal(bpPause1.why.type, "breakpoint",
|
||||
"Should pause because of hitting our breakpoint (not debugger statement).");
|
||||
equal(bpPause1.why.actors[0], bpActor,
|
||||
"And the breakpoint actor should be correct.");
|
||||
const dbgStmtPause1 = await executeOnNextTickAndWaitForPause(() => resume(threadClient),
|
||||
gClient);
|
||||
equal(dbgStmtPause1.why.type, "debuggerStatement",
|
||||
@ -72,8 +64,6 @@ const testBreakpoint = async function(threadResponse, targetFront,
|
||||
gClient);
|
||||
equal(bpPause2.why.type, "breakpoint",
|
||||
"Should pause because of hitting our breakpoint (not debugger statement).");
|
||||
equal(bpPause2.why.actors[0], bpActor,
|
||||
"And the breakpoint actor should be correct.");
|
||||
const dbgStmtPause2 = await executeOnNextTickAndWaitForPause(() => resume(threadClient),
|
||||
gClient);
|
||||
equal(dbgStmtPause2.why.type, "debuggerStatement",
|
||||
|
@ -22,17 +22,16 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
packet.frame.where.actor
|
||||
);
|
||||
const location = {
|
||||
sourceUrl: source.url,
|
||||
line: debuggee.line0 + 8,
|
||||
};
|
||||
|
||||
const [res, bpClient] = await setBreakpoint(source, location);
|
||||
ok(!res.error);
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
await resume(threadClient);
|
||||
packet = await waitForPause(client);
|
||||
Assert.equal(packet.type, "paused");
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.why.actors[0], bpClient.actor);
|
||||
Assert.equal(packet.frame.where.actor, source.actor);
|
||||
Assert.equal(packet.frame.where.line, location.line);
|
||||
|
||||
|
@ -34,28 +34,26 @@ function test_simple_breakpoint() {
|
||||
gThreadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
source.setBreakpoint({
|
||||
line: 3,
|
||||
options: { condition: "a === 1" },
|
||||
}).then(function([response, bpClient]) {
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
Assert.equal(hitBreakpoint, false);
|
||||
hitBreakpoint = true;
|
||||
const location = { sourceUrl: source.url, line: 3 };
|
||||
gThreadClient.setBreakpoint(location, { condition: "a === 1" });
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
Assert.equal(hitBreakpoint, false);
|
||||
hitBreakpoint = true;
|
||||
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.frame.where.line, 3);
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.frame.where.line, 3);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
});
|
||||
// Remove the breakpoint.
|
||||
gThreadClient.removeBreakpoint(location);
|
||||
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -32,29 +32,25 @@ function test_simple_breakpoint() {
|
||||
gThreadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
await source.setBreakpoint({
|
||||
line: 3,
|
||||
options: { condition: "a === 2" },
|
||||
});
|
||||
source.setBreakpoint({
|
||||
line: 4,
|
||||
options: { condition: "a === 1" },
|
||||
}).then(function([response, bpClient]) {
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.frame.where.line, 4);
|
||||
const location1 = { sourceUrl: source.url, line: 3 };
|
||||
gThreadClient.setBreakpoint(location1, { condition: "a === 2" });
|
||||
const location2 = { sourceUrl: source.url, line: 4 };
|
||||
gThreadClient.setBreakpoint(location2, { condition: "a === 1" });
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpoint");
|
||||
Assert.equal(packet.frame.where.line, 4);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
});
|
||||
// Remove the breakpoint.
|
||||
gThreadClient.removeBreakpoint(location2);
|
||||
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -32,25 +32,23 @@ function test_simple_breakpoint() {
|
||||
gThreadClient,
|
||||
packet.frame.where.actor
|
||||
);
|
||||
source.setBreakpoint({
|
||||
line: 3,
|
||||
options: { condition: "throw new Error()" },
|
||||
}).then(function([response, bpClient]) {
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpointConditionThrown");
|
||||
Assert.equal(packet.frame.where.line, 3);
|
||||
const location = { sourceUrl: source.url, line: 3 };
|
||||
gThreadClient.setBreakpoint(location, { condition: "throw new Error()" });
|
||||
gThreadClient.addOneTimeListener("paused", function(event, packet) {
|
||||
// Check the return value.
|
||||
Assert.equal(packet.why.type, "breakpointConditionThrown");
|
||||
Assert.equal(packet.frame.where.line, 3);
|
||||
|
||||
// Remove the breakpoint.
|
||||
bpClient.remove(function(response) {
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
});
|
||||
// Remove the breakpoint.
|
||||
gThreadClient.removeBreakpoint(location);
|
||||
|
||||
gThreadClient.resume(function() {
|
||||
finishClient(gClient);
|
||||
});
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
// Continue until the breakpoint is hit.
|
||||
gThreadClient.resume();
|
||||
});
|
||||
|
||||
/* eslint-disable */
|
||||
|
@ -34,10 +34,10 @@ function test_simple_breakpoint() {
|
||||
);
|
||||
|
||||
// Set a logpoint which should invoke console.log.
|
||||
await source.setBreakpoint({
|
||||
gThreadClient.setBreakpoint({
|
||||
sourceUrl: source.url,
|
||||
line: 4,
|
||||
options: { logValue: "a" },
|
||||
});
|
||||
}, { logValue: "a" });
|
||||
|
||||
// Execute the rest of the code.
|
||||
gThreadClient.resume();
|
||||
|
@ -34,10 +34,10 @@ function test_simple_breakpoint() {
|
||||
);
|
||||
|
||||
// Set a logpoint which should invoke console.log.
|
||||
await source.setBreakpoint({
|
||||
gThreadClient.setBreakpoint({
|
||||
sourceUrl: source.url,
|
||||
line: 5,
|
||||
options: { logValue: "a", condition: "a === 5" },
|
||||
});
|
||||
}, { logValue: "a", condition: "a === 5" });
|
||||
|
||||
// Execute the rest of the code.
|
||||
gThreadClient.resume();
|
||||
|
@ -6,18 +6,11 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const promise = waitForNewSource(threadClient, SOURCE_URL);
|
||||
loadSubScript(SOURCE_URL, debuggee);
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 4, column: 2 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(
|
||||
sourceClient,
|
||||
location
|
||||
);
|
||||
const location = { sourceUrl: source.url, line: 4, column: 2 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
|
||||
@ -25,7 +18,6 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
|
||||
const frame = packet.frame;
|
||||
Assert.equal(frame.where.actor, source.actor);
|
||||
|
@ -6,20 +6,13 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const promise = waitForNewSource(threadClient, SOURCE_URL);
|
||||
loadSubScript(SOURCE_URL, debuggee);
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
// Pause inside of the nested function so we can make sure that we don't
|
||||
// add any other breakpoints at other places on this line.
|
||||
const location = { line: 3, column: 47 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(
|
||||
sourceClient,
|
||||
location
|
||||
);
|
||||
const location = { sourceUrl: source.url, line: 3, column: 47 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
|
||||
@ -27,7 +20,6 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
|
@ -6,18 +6,11 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const promise = waitForNewSource(threadClient, SOURCE_URL);
|
||||
loadSubScript(SOURCE_URL, debuggee);
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 4, column: 42 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(
|
||||
sourceClient,
|
||||
location
|
||||
);
|
||||
const location = { sourceUrl: source.url, line: 4, column: 42 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
|
||||
@ -25,7 +18,6 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
|
@ -6,20 +6,13 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const promise = waitForNewSource(threadClient, SOURCE_URL);
|
||||
loadSubScript(SOURCE_URL, debuggee);
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
// Pause inside of the nested function so we can make sure that we don't
|
||||
// add any other breakpoints at other places on this line.
|
||||
const location = { line: 3, column: 81 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(
|
||||
sourceClient,
|
||||
location
|
||||
);
|
||||
const location = { sourceUrl: source.url, line: 3, column: 81 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
|
||||
@ -27,7 +20,6 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
|
@ -8,14 +8,11 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client, targetFront }
|
||||
Cu.forceGC(); Cu.forceGC(); Cu.forceGC();
|
||||
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 6, column: 17 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: source.url, line: 6, column: 17 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
reload(targetFront).then(function() {
|
||||
loadSubScriptWithOptions(SOURCE_URL, {target: debuggee, ignoreCache: true});
|
||||
});
|
||||
@ -24,10 +21,8 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client, targetFront }
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
Assert.equal(where.line, location.line);
|
||||
Assert.equal(where.column, location.column);
|
||||
const variables = frame.environment.bindings.variables;
|
||||
|
@ -6,21 +6,17 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const promise = waitForNewSource(threadClient, SOURCE_URL);
|
||||
loadSubScript(SOURCE_URL, debuggee);
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 4, column: 17 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: source.url, line: 4, column: 17 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
Assert.equal(packet.type, "paused");
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
|
@ -8,14 +8,11 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client, targetFront }
|
||||
Cu.forceGC(); Cu.forceGC(); Cu.forceGC();
|
||||
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 7 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: source.url, line: 7 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
reload(targetFront).then(function() {
|
||||
loadSubScriptWithOptions(SOURCE_URL, {target: debuggee, ignoreCache: true});
|
||||
});
|
||||
@ -24,10 +21,8 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client, targetFront }
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
Assert.equal(where.line, location.line);
|
||||
const variables = frame.environment.bindings.variables;
|
||||
Assert.equal(variables.a.value, 1);
|
||||
|
@ -8,19 +8,16 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 4 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: sourceClient.url, line: 4 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
let packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
Assert.equal(packet.type, "paused");
|
||||
let why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
let frame = packet.frame;
|
||||
let where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
@ -36,7 +33,6 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
frame = packet.frame;
|
||||
where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
|
@ -8,19 +8,16 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 4 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: sourceClient.url, line: 4 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
Assert.equal(packet.type, "paused");
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
|
@ -8,19 +8,16 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
const { source } = await promise;
|
||||
const sourceClient = threadClient.source(source);
|
||||
|
||||
const location = { line: 5 };
|
||||
let [packet, breakpointClient] = await setBreakpoint(sourceClient, location);
|
||||
Assert.ok(!packet.isPending);
|
||||
Assert.equal(false, "actualLocation" in packet);
|
||||
const location = { sourceUrl: sourceClient.url, line: 5 };
|
||||
setBreakpoint(threadClient, location);
|
||||
|
||||
packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
const packet = await executeOnNextTickAndWaitForPause(function() {
|
||||
Cu.evalInSandbox("f()", debuggee);
|
||||
}, client);
|
||||
Assert.equal(packet.type, "paused");
|
||||
const why = packet.why;
|
||||
Assert.equal(why.type, "breakpoint");
|
||||
Assert.equal(why.actors.length, 1);
|
||||
Assert.equal(why.actors[0], breakpointClient.actor);
|
||||
const frame = packet.frame;
|
||||
const where = frame.where;
|
||||
Assert.equal(where.actor, source.actor);
|
||||
|
@ -18,7 +18,7 @@ add_task(threadClientTest(async ({ threadClient, debuggee, client }) => {
|
||||
threadClient,
|
||||
dbgStmt.frame.where.actor
|
||||
);
|
||||
await source.setBreakpoint({ line: 7 });
|
||||
await threadClient.setBreakpoint({ sourceUrl: source.url, line: 7 }, {});
|
||||
|
||||
dumpn("Step in to innerFunction");
|
||||
const step1 = await stepIn(client, threadClient);
|
||||
|
@ -128,8 +128,10 @@ skip-if = true # breakpoint sliding is not supported bug 1525685
|
||||
[test_breakpoint-13.js]
|
||||
[test_breakpoint-14.js]
|
||||
[test_breakpoint-15.js]
|
||||
skip-if = true # tests for breakpoint actors are obsolete bug 1524374
|
||||
[test_breakpoint-16.js]
|
||||
[test_breakpoint-17.js]
|
||||
skip-if = true # tests for breakpoint actors are obsolete bug 1524374
|
||||
[test_breakpoint-18.js]
|
||||
[test_breakpoint-19.js]
|
||||
skip-if = true
|
||||
@ -209,6 +211,7 @@ skip-if = true # breakpoint sliding is not supported bug 1525685
|
||||
[test_source-02.js]
|
||||
[test_wasm_source-01.js]
|
||||
[test_breakpoint-actor-map.js]
|
||||
skip-if = true # tests for breakpoint actors are obsolete bug 1524374
|
||||
[test_unsafeDereference.js]
|
||||
[test_add_actors.js]
|
||||
[test_ignore_caught_exceptions.js]
|
||||
|
@ -1,100 +0,0 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
const promise = require("devtools/shared/deprecated-sync-thenables");
|
||||
|
||||
const eventSource = require("devtools/shared/client/event-source");
|
||||
const {arg, DebuggerClient} = require("devtools/shared/client/debugger-client");
|
||||
|
||||
/**
|
||||
* Breakpoint clients are used to remove breakpoints that are no longer used.
|
||||
*
|
||||
* @param client DebuggerClient
|
||||
* The debugger client parent.
|
||||
* @param sourceClient SourceClient
|
||||
* The source where this breakpoint exists
|
||||
* @param actor string
|
||||
* The actor ID for this breakpoint.
|
||||
* @param location object
|
||||
* The location of the breakpoint. This is an object with two properties:
|
||||
* url and line.
|
||||
* @param options object
|
||||
* Any options associated with the breakpoint
|
||||
*/
|
||||
function BreakpointClient(client, sourceClient, actor, location, options) {
|
||||
this._client = client;
|
||||
this._actor = actor;
|
||||
this.location = location;
|
||||
this.location.actor = sourceClient.actor;
|
||||
this.location.url = sourceClient.url;
|
||||
this.source = sourceClient;
|
||||
this.request = this._client.request;
|
||||
this.options = options;
|
||||
}
|
||||
|
||||
BreakpointClient.prototype = {
|
||||
|
||||
_actor: null,
|
||||
get actor() {
|
||||
return this._actor;
|
||||
},
|
||||
get _transport() {
|
||||
return this._client._transport;
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove the breakpoint from the server.
|
||||
*/
|
||||
remove: DebuggerClient.requester({
|
||||
type: "delete",
|
||||
}),
|
||||
|
||||
// Send a setOptions request to newer servers.
|
||||
setOptionsRequester: DebuggerClient.requester({
|
||||
type: "setOptions",
|
||||
options: arg(0),
|
||||
}, {
|
||||
before(packet) {
|
||||
this.options = packet.options;
|
||||
return packet;
|
||||
},
|
||||
}),
|
||||
|
||||
/**
|
||||
* Set any options for this breakpoint.
|
||||
*/
|
||||
setOptions: function(options) {
|
||||
if (this._client.mainRoot.traits.nativeLogpoints) {
|
||||
return this.setOptionsRequester(options).then(() => this);
|
||||
}
|
||||
// Older servers need to reinstall breakpoints when the condition changes.
|
||||
const deferred = promise.defer();
|
||||
|
||||
const info = {
|
||||
line: this.location.line,
|
||||
column: this.location.column,
|
||||
options,
|
||||
};
|
||||
|
||||
// Remove the current breakpoint and add a new one with the specified
|
||||
// information.
|
||||
this.remove(response => {
|
||||
if (response && response.error) {
|
||||
deferred.reject(response);
|
||||
return;
|
||||
}
|
||||
|
||||
deferred.resolve(this.source.setBreakpoint(info).then(([, newBreakpoint]) => {
|
||||
return newBreakpoint;
|
||||
}));
|
||||
});
|
||||
return deferred;
|
||||
},
|
||||
};
|
||||
|
||||
eventSource(BreakpointClient.prototype);
|
||||
|
||||
module.exports = BreakpointClient;
|
@ -6,7 +6,6 @@
|
||||
|
||||
DevToolsModules(
|
||||
'array-buffer-client.js',
|
||||
'breakpoint-client.js',
|
||||
'connection-manager.js',
|
||||
'constants.js',
|
||||
'debugger-client.js',
|
||||
|
@ -5,7 +5,6 @@
|
||||
"use strict";
|
||||
|
||||
const {arg, DebuggerClient} = require("devtools/shared/client/debugger-client");
|
||||
loader.lazyRequireGetter(this, "BreakpointClient", "devtools/shared/client/breakpoint-client");
|
||||
|
||||
const noop = () => {};
|
||||
|
||||
@ -149,87 +148,6 @@ SourceClient.prototype = {
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* Request to set a breakpoint in the specified location.
|
||||
*
|
||||
* @param object location
|
||||
* The location and options of the breakpoint in
|
||||
* the form of { line[, column, options] }.
|
||||
*/
|
||||
setBreakpoint: function({ line, column, options }) {
|
||||
// A helper function that sets the breakpoint.
|
||||
const doSetBreakpoint = callback => {
|
||||
const location = {
|
||||
line,
|
||||
column,
|
||||
};
|
||||
|
||||
const packet = {
|
||||
to: this.actor,
|
||||
type: "setBreakpoint",
|
||||
location,
|
||||
options,
|
||||
};
|
||||
|
||||
// Older servers only support conditions, not a more general options
|
||||
// object. Transform the packet to support the older format.
|
||||
if (options && !this._client.mainRoot.traits.nativeLogpoints) {
|
||||
delete packet.options;
|
||||
if (options.logValue) {
|
||||
// Emulate log points by setting a condition with a call to console.log,
|
||||
// which always returns false so the server will never pause.
|
||||
packet.condition = `console.log(${options.logValue})`;
|
||||
} else {
|
||||
packet.condition = options.condition;
|
||||
}
|
||||
}
|
||||
|
||||
return this._client.request(packet).then(response => {
|
||||
// Ignoring errors, since the user may be setting a breakpoint in a
|
||||
// dead script that will reappear on a page reload.
|
||||
let bpClient;
|
||||
if (response.actor) {
|
||||
bpClient = new BreakpointClient(
|
||||
this._client,
|
||||
this,
|
||||
response.actor,
|
||||
location,
|
||||
options
|
||||
);
|
||||
}
|
||||
if (callback) {
|
||||
callback();
|
||||
}
|
||||
return [response, bpClient];
|
||||
});
|
||||
};
|
||||
|
||||
// With async sourcemap processing removed from the server, it is not
|
||||
// necessary for clients to pause the debuggee before adding breakpoints.
|
||||
if (this._client.mainRoot.traits.breakpointWhileRunning) {
|
||||
return doSetBreakpoint();
|
||||
}
|
||||
|
||||
// If the debuggee is paused, just set the breakpoint.
|
||||
if (this._activeThread.paused) {
|
||||
return doSetBreakpoint();
|
||||
}
|
||||
// Otherwise, force a pause in order to set the breakpoint.
|
||||
return this._activeThread.interrupt().then(response => {
|
||||
if (response.error) {
|
||||
// Can't set the breakpoint if pausing failed.
|
||||
return response;
|
||||
}
|
||||
|
||||
const { type, why } = response;
|
||||
const cleanUp = type == "paused" && why.type == "interrupted"
|
||||
? () => this._activeThread.resume()
|
||||
: noop;
|
||||
|
||||
return doSetBreakpoint(cleanUp);
|
||||
});
|
||||
},
|
||||
|
||||
setPausePoints: function(pausePoints) {
|
||||
const packet = {
|
||||
to: this._form.actor,
|
||||
|
@ -663,6 +663,17 @@ ThreadClient.prototype = {
|
||||
return this._lastPausePacket;
|
||||
},
|
||||
|
||||
setBreakpoint: DebuggerClient.requester({
|
||||
type: "setBreakpoint",
|
||||
location: arg(0),
|
||||
options: arg(1),
|
||||
}),
|
||||
|
||||
removeBreakpoint: DebuggerClient.requester({
|
||||
type: "removeBreakpoint",
|
||||
location: arg(0),
|
||||
}),
|
||||
|
||||
/**
|
||||
* Requests to set XHR breakpoint
|
||||
* @param string path
|
||||
|
@ -1,22 +0,0 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
"use strict";
|
||||
|
||||
const {Arg, generateActorSpec} = require("devtools/shared/protocol");
|
||||
|
||||
const breakpointSpec = generateActorSpec({
|
||||
typeName: "breakpoint",
|
||||
|
||||
methods: {
|
||||
delete: {},
|
||||
|
||||
setOptions: {
|
||||
request: {
|
||||
options: Arg(0, "nullable:json"),
|
||||
},
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
exports.breakpointSpec = breakpointSpec;
|
@ -42,12 +42,6 @@ const Types = exports.__TypesForTests = [
|
||||
spec: "devtools/shared/specs/animation",
|
||||
front: "devtools/shared/fronts/animation",
|
||||
},
|
||||
/* breakpoint has old fashion client and no front */
|
||||
{
|
||||
types: ["breakpoint"],
|
||||
spec: "devtools/shared/specs/breakpoint",
|
||||
front: null,
|
||||
},
|
||||
{
|
||||
types: ["frame-snapshot", "canvas"],
|
||||
spec: "devtools/shared/specs/canvas",
|
||||
|
@ -14,7 +14,6 @@ DevToolsModules(
|
||||
'accessibility.js',
|
||||
'actor-registry.js',
|
||||
'animation.js',
|
||||
'breakpoint.js',
|
||||
'canvas.js',
|
||||
'changes.js',
|
||||
'css-properties.js',
|
||||
|
@ -9,6 +9,17 @@ const threadSpec = generateActorSpec({
|
||||
typeName: "context",
|
||||
|
||||
methods: {
|
||||
setBreakpoint: {
|
||||
request: {
|
||||
location: Arg(0, "json"),
|
||||
options: Arg(1, "json"),
|
||||
},
|
||||
},
|
||||
removeBreakpoint: {
|
||||
request: {
|
||||
location: Arg(0, "json"),
|
||||
},
|
||||
},
|
||||
setXHRBreakpoint: {
|
||||
request: {
|
||||
path: Arg(0, "string"),
|
||||
|
@ -55,16 +55,6 @@ const sourceSpec = generateActorSpec({
|
||||
unblackbox: {
|
||||
request: { range: Arg(0, "nullable:json") },
|
||||
},
|
||||
setBreakpoint: {
|
||||
request: {
|
||||
location: {
|
||||
line: Arg(0, "number"),
|
||||
column: Arg(1, "nullable:number"),
|
||||
},
|
||||
options: Arg(2, "nullable:json"),
|
||||
},
|
||||
response: RetVal("json"),
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
|
@ -37,7 +37,7 @@ skip-if = verify
|
||||
[browser_thumbnails_bug818225.js]
|
||||
skip-if = (verify && debug && (os == 'linux'))
|
||||
[browser_thumbnails_capture.js]
|
||||
skip-if = (os == "mac" && !debug) || (os == 'win') # bug 1314039 # Bug 1345418
|
||||
skip-if = true # bug 1314039 # Bug 1345418
|
||||
[browser_thumbnails_expiration.js]
|
||||
[browser_thumbnails_privacy.js]
|
||||
[browser_thumbnails_redirect.js]
|
||||
|
Loading…
Reference in New Issue
Block a user