| /* |
| * Copyright (C) 2011 Google Inc. All rights reserved. |
| * |
| * Redistribution and use in source and binary forms, with or without |
| * modification, are permitted provided that the following conditions are |
| * met: |
| * |
| * * Redistributions of source code must retain the above copyright |
| * notice, this list of conditions and the following disclaimer. |
| * * Redistributions in binary form must reproduce the above |
| * copyright notice, this list of conditions and the following disclaimer |
| * in the documentation and/or other materials provided with the |
| * distribution. |
| * * Neither the name of Google Inc. nor the names of its |
| * contributors may be used to endorse or promote products derived from |
| * this software without specific prior written permission. |
| * |
| * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
| * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
| * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
| * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
| * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
| * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
| * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
| * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
| * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
| * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| */ |
| |
| /** |
| * @constructor |
| * @extends {WebInspector.Object} |
| * @param {WebInspector.Setting} breakpointStorage |
| * @param {WebInspector.DebuggerModel} debuggerModel |
| * @param {WebInspector.Workspace} workspace |
| */ |
| WebInspector.BreakpointManager = function(breakpointStorage, debuggerModel, workspace) |
| { |
| this._storage = new WebInspector.BreakpointManager.Storage(this, breakpointStorage); |
| this._debuggerModel = debuggerModel; |
| this._workspace = workspace; |
| |
| this._breakpointForDebuggerId = {}; |
| this._breakpointsForUISourceCode = new Map(); |
| this._breakpointsForPrimaryUISourceCode = new Map(); |
| this._sourceFilesWithRestoredBreakpoints = {}; |
| |
| this._debuggerModel.addEventListener(WebInspector.DebuggerModel.Events.BreakpointResolved, this._breakpointResolved, this); |
| this._workspace.addEventListener(WebInspector.Workspace.Events.ProjectWillReset, this._projectWillReset, this); |
| this._workspace.addEventListener(WebInspector.Workspace.Events.UISourceCodeAdded, this._uiSourceCodeAdded, this); |
| this._workspace.addEventListener(WebInspector.Workspace.Events.UISourceCodeRemoved, this._uiSourceCodeRemoved, this); |
| } |
| |
| WebInspector.BreakpointManager.Events = { |
| BreakpointAdded: "breakpoint-added", |
| BreakpointRemoved: "breakpoint-removed" |
| } |
| |
| WebInspector.BreakpointManager._sourceFileId = function(uiSourceCode) |
| { |
| if (!uiSourceCode.url) |
| return ""; |
| var deobfuscatedPrefix = uiSourceCode.formatted() ? "deobfuscated:" : ""; |
| return deobfuscatedPrefix + uiSourceCode.uri(); |
| } |
| |
| /** |
| * @param {string} sourceFileId |
| * @param {number} lineNumber |
| * @return {string} |
| */ |
| WebInspector.BreakpointManager._breakpointStorageId = function(sourceFileId, lineNumber) |
| { |
| if (!sourceFileId) |
| return ""; |
| return sourceFileId + ":" + lineNumber; |
| } |
| |
| WebInspector.BreakpointManager.prototype = { |
| /** |
| * @param {string} sourceFileId |
| */ |
| _provisionalBreakpointsForSourceFileId: function(sourceFileId) |
| { |
| var result = new StringMap(); |
| for (var debuggerId in this._breakpointForDebuggerId) { |
| var breakpoint = this._breakpointForDebuggerId[debuggerId]; |
| if (breakpoint._sourceFileId === sourceFileId) |
| result.put(breakpoint._breakpointStorageId(), breakpoint); |
| } |
| return result; |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| */ |
| _restoreBreakpoints: function(uiSourceCode) |
| { |
| var sourceFileId = WebInspector.BreakpointManager._sourceFileId(uiSourceCode); |
| if (!sourceFileId || this._sourceFilesWithRestoredBreakpoints[sourceFileId]) |
| return; |
| this._sourceFilesWithRestoredBreakpoints[sourceFileId] = true; |
| |
| this._storage.mute(); |
| var breakpointItems = this._storage.breakpointItems(uiSourceCode); |
| var provisionalBreakpoints = this._provisionalBreakpointsForSourceFileId(sourceFileId); |
| for (var i = 0; i < breakpointItems.length; ++i) { |
| var breakpointItem = breakpointItems[i]; |
| var itemStorageId = WebInspector.BreakpointManager._breakpointStorageId(breakpointItem.sourceFileId, breakpointItem.lineNumber); |
| var provisionalBreakpoint = provisionalBreakpoints.get(itemStorageId); |
| if (provisionalBreakpoint) { |
| if (!this._breakpointsForPrimaryUISourceCode.get(uiSourceCode)) |
| this._breakpointsForPrimaryUISourceCode.put(uiSourceCode, []); |
| this._breakpointsForPrimaryUISourceCode.get(uiSourceCode).push(provisionalBreakpoint); |
| provisionalBreakpoint._updateInDebugger(); |
| } else { |
| this._innerSetBreakpoint(uiSourceCode, breakpointItem.lineNumber, breakpointItem.condition, breakpointItem.enabled); |
| } |
| } |
| this._storage.unmute(); |
| }, |
| |
| /** |
| * @param {WebInspector.Event} event |
| */ |
| _uiSourceCodeAdded: function(event) |
| { |
| var uiSourceCode = /** @type {WebInspector.UISourceCode} */ (event.data); |
| this._restoreBreakpoints(uiSourceCode); |
| if (uiSourceCode.contentType() === WebInspector.resourceTypes.Script || uiSourceCode.contentType() === WebInspector.resourceTypes.Document) { |
| uiSourceCode.addEventListener(WebInspector.UISourceCode.Events.SourceMappingChanged, this._uiSourceCodeMappingChanged, this); |
| uiSourceCode.addEventListener(WebInspector.UISourceCode.Events.FormattedChanged, this._uiSourceCodeFormatted, this); |
| } |
| }, |
| |
| /** |
| * @param {WebInspector.Event} event |
| */ |
| _uiSourceCodeFormatted: function(event) |
| { |
| var uiSourceCode = /** @type {WebInspector.UISourceCode} */ (event.target); |
| this._restoreBreakpoints(uiSourceCode); |
| }, |
| |
| /** |
| * @param {WebInspector.Event} event |
| */ |
| _uiSourceCodeRemoved: function(event) |
| { |
| var uiSourceCode = /** @type {WebInspector.UISourceCode} */ (event.data); |
| this._removeUISourceCode(uiSourceCode); |
| }, |
| |
| /** |
| * @param {WebInspector.Event} event |
| */ |
| _uiSourceCodeMappingChanged: function(event) |
| { |
| var uiSourceCode = /** @type {WebInspector.UISourceCode} */ (event.target); |
| var breakpoints = this._breakpointsForPrimaryUISourceCode.get(uiSourceCode) || []; |
| for (var i = 0; i < breakpoints.length; ++i) |
| breakpoints[i]._updateInDebugger(); |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| */ |
| _removeUISourceCode: function(uiSourceCode) |
| { |
| var breakpoints = this._breakpointsForPrimaryUISourceCode.get(uiSourceCode) || []; |
| for (var i = 0; i < breakpoints.length; ++i) |
| breakpoints[i]._resetLocations(); |
| var sourceFileId = WebInspector.BreakpointManager._sourceFileId(uiSourceCode); |
| delete this._sourceFilesWithRestoredBreakpoints[sourceFileId]; |
| uiSourceCode.removeEventListener(WebInspector.UISourceCode.Events.FormattedChanged, this._uiSourceCodeFormatted, this); |
| uiSourceCode.removeEventListener(WebInspector.UISourceCode.Events.SourceMappingChanged, this._uiSourceCodeMappingChanged, this); |
| this._breakpointsForPrimaryUISourceCode.remove(uiSourceCode); |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @param {number} lineNumber |
| * @param {string} condition |
| * @param {boolean} enabled |
| * @return {WebInspector.BreakpointManager.Breakpoint} |
| */ |
| setBreakpoint: function(uiSourceCode, lineNumber, condition, enabled) |
| { |
| this._debuggerModel.setBreakpointsActive(true); |
| return this._innerSetBreakpoint(uiSourceCode, lineNumber, condition, enabled); |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @param {number} lineNumber |
| * @param {string} condition |
| * @param {boolean} enabled |
| * @return {WebInspector.BreakpointManager.Breakpoint} |
| */ |
| _innerSetBreakpoint: function(uiSourceCode, lineNumber, condition, enabled) |
| { |
| var breakpoint = this.findBreakpoint(uiSourceCode, lineNumber); |
| if (breakpoint) { |
| breakpoint._updateBreakpoint(condition, enabled); |
| return breakpoint; |
| } |
| var projectId = uiSourceCode.project().id(); |
| var path = uiSourceCode.path(); |
| var sourceFileId = WebInspector.BreakpointManager._sourceFileId(uiSourceCode); |
| breakpoint = new WebInspector.BreakpointManager.Breakpoint(this, projectId, path, sourceFileId, lineNumber, condition, enabled); |
| if (!this._breakpointsForPrimaryUISourceCode.get(uiSourceCode)) |
| this._breakpointsForPrimaryUISourceCode.put(uiSourceCode, []); |
| this._breakpointsForPrimaryUISourceCode.get(uiSourceCode).push(breakpoint); |
| return breakpoint; |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @param {number} lineNumber |
| * @return {?WebInspector.BreakpointManager.Breakpoint} |
| */ |
| findBreakpoint: function(uiSourceCode, lineNumber) |
| { |
| var breakpoints = this._breakpointsForUISourceCode.get(uiSourceCode); |
| var lineBreakpoints = breakpoints ? breakpoints[lineNumber] : null; |
| return lineBreakpoints ? lineBreakpoints[0] : null; |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @return {Array.<WebInspector.BreakpointManager.Breakpoint>} |
| */ |
| breakpointsForUISourceCode: function(uiSourceCode) |
| { |
| var breakpoints = this._breakpointsForUISourceCode.get(uiSourceCode); |
| var allLineBreakpoints = breakpoints ? Object.values(breakpoints) : []; |
| var result = []; |
| for (var i = 0; i < allLineBreakpoints.length; ++i) |
| result = result.concat(allLineBreakpoints[i]); |
| return result; |
| }, |
| |
| /** |
| * @return {Array.<WebInspector.BreakpointManager.Breakpoint>} |
| */ |
| allBreakpoints: function() |
| { |
| var result = []; |
| var uiSourceCodes = this._breakpointsForUISourceCode.keys(); |
| for (var i = 0; i < uiSourceCodes.length; ++i) |
| result = result.concat(this.breakpointsForUISourceCode(uiSourceCodes[i])); |
| return result; |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @return {Array.<{breakpoint: WebInspector.BreakpointManager.Breakpoint, uiLocation: WebInspector.UILocation}>} |
| */ |
| breakpointLocationsForUISourceCode: function(uiSourceCode) |
| { |
| var breakpoints = this._breakpointsForUISourceCode.get(uiSourceCode); |
| var breakpointLines = breakpoints ? Object.keys(breakpoints) : []; |
| var result = []; |
| for (var i = 0; i < breakpointLines.length; ++i) { |
| var lineNumber = parseInt(breakpointLines[i], 10); |
| if (isNaN(lineNumber)) |
| continue; |
| var lineBreakpoints = breakpoints[lineNumber]; |
| for (var j = 0; j < lineBreakpoints.length; ++j) { |
| var breakpoint = lineBreakpoints[j]; |
| var uiLocation = new WebInspector.UILocation(uiSourceCode, lineNumber, 0); |
| result.push({breakpoint: breakpoint, uiLocation: uiLocation}); |
| } |
| } |
| return result; |
| }, |
| |
| /** |
| * @return {Array.<{breakpoint: WebInspector.BreakpointManager.Breakpoint, uiLocation: WebInspector.UILocation}>} |
| */ |
| allBreakpointLocations: function() |
| { |
| var result = []; |
| var uiSourceCodes = this._breakpointsForUISourceCode.keys(); |
| for (var i = 0; i < uiSourceCodes.length; ++i) |
| result = result.concat(this.breakpointLocationsForUISourceCode(uiSourceCodes[i])); |
| return result; |
| }, |
| |
| /** |
| * @param {boolean} toggleState |
| */ |
| toggleAllBreakpoints: function(toggleState) |
| { |
| var breakpoints = this.allBreakpoints(); |
| for (var i = 0; i < breakpoints.length; ++i) |
| breakpoints[i].setEnabled(toggleState); |
| }, |
| |
| removeAllBreakpoints: function() |
| { |
| var breakpoints = this.allBreakpoints(); |
| for (var i = 0; i < breakpoints.length; ++i) |
| breakpoints[i].remove(); |
| }, |
| |
| removeProvisionalBreakpoints: function() |
| { |
| for (var debuggerId in this._breakpointForDebuggerId) |
| this._debuggerModel.removeBreakpoint(debuggerId); |
| }, |
| |
| _projectWillReset: function(event) |
| { |
| var project = /** @type {WebInspector.Project} */ (event.data); |
| var uiSourceCodes = project.uiSourceCodes(); |
| for (var i = 0; i < uiSourceCodes.length; ++i) |
| this._removeUISourceCode(uiSourceCodes[i]); |
| }, |
| |
| _breakpointResolved: function(event) |
| { |
| var breakpointId = /** @type {DebuggerAgent.BreakpointId} */ (event.data.breakpointId); |
| var location = /** @type {WebInspector.DebuggerModel.Location} */ (event.data.location); |
| var breakpoint = this._breakpointForDebuggerId[breakpointId]; |
| if (!breakpoint) |
| return; |
| breakpoint._addResolvedLocation(location); |
| }, |
| |
| /** |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| * @param {boolean} removeFromStorage |
| */ |
| _removeBreakpoint: function(breakpoint, removeFromStorage) |
| { |
| var uiSourceCode = breakpoint.uiSourceCode(); |
| var breakpoints = uiSourceCode ? this._breakpointsForPrimaryUISourceCode.get(uiSourceCode) || [] : []; |
| var index = breakpoints.indexOf(breakpoint); |
| if (index > -1) |
| breakpoints.splice(index, 1); |
| console.assert(!breakpoint._debuggerId) |
| if (removeFromStorage) |
| this._storage._removeBreakpoint(breakpoint); |
| }, |
| |
| /** |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| * @param {WebInspector.UILocation} uiLocation |
| */ |
| _uiLocationAdded: function(breakpoint, uiLocation) |
| { |
| var breakpoints = this._breakpointsForUISourceCode.get(uiLocation.uiSourceCode); |
| if (!breakpoints) { |
| breakpoints = {}; |
| this._breakpointsForUISourceCode.put(uiLocation.uiSourceCode, breakpoints); |
| } |
| |
| var lineBreakpoints = breakpoints[uiLocation.lineNumber]; |
| if (!lineBreakpoints) { |
| lineBreakpoints = []; |
| breakpoints[uiLocation.lineNumber] = lineBreakpoints; |
| } |
| |
| lineBreakpoints.push(breakpoint); |
| this.dispatchEventToListeners(WebInspector.BreakpointManager.Events.BreakpointAdded, {breakpoint: breakpoint, uiLocation: uiLocation}); |
| }, |
| |
| /** |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| * @param {WebInspector.UILocation} uiLocation |
| */ |
| _uiLocationRemoved: function(breakpoint, uiLocation) |
| { |
| var breakpoints = this._breakpointsForUISourceCode.get(uiLocation.uiSourceCode); |
| if (!breakpoints) |
| return; |
| |
| var lineBreakpoints = breakpoints[uiLocation.lineNumber]; |
| if (!lineBreakpoints) |
| return; |
| |
| lineBreakpoints.remove(breakpoint); |
| if (!lineBreakpoints.length) |
| delete breakpoints[uiLocation.lineNumber]; |
| if (Object.keys(breakpoints).length === 0) |
| this._breakpointsForUISourceCode.remove(uiLocation.uiSourceCode); |
| this.dispatchEventToListeners(WebInspector.BreakpointManager.Events.BreakpointRemoved, {breakpoint: breakpoint, uiLocation: uiLocation}); |
| }, |
| |
| __proto__: WebInspector.Object.prototype |
| } |
| |
| /** |
| * @constructor |
| * @param {WebInspector.BreakpointManager} breakpointManager |
| * @param {string} projectId |
| * @param {string} path |
| * @param {string} sourceFileId |
| * @param {number} lineNumber |
| * @param {string} condition |
| * @param {boolean} enabled |
| */ |
| WebInspector.BreakpointManager.Breakpoint = function(breakpointManager, projectId, path, sourceFileId, lineNumber, condition, enabled) |
| { |
| this._breakpointManager = breakpointManager; |
| this._projectId = projectId; |
| this._path = path; |
| this._lineNumber = lineNumber; |
| this._sourceFileId = sourceFileId; |
| /** @type {Array.<WebInspector.Script.Location>} */ |
| this._liveLocations = []; |
| /** @type {!Object.<string, WebInspector.UILocation>} */ |
| this._uiLocations = {}; |
| |
| // Force breakpoint update. |
| /** @type {string} */ this._condition; |
| /** @type {boolean} */ this._enabled; |
| this._updateBreakpoint(condition, enabled); |
| } |
| |
| WebInspector.BreakpointManager.Breakpoint.prototype = { |
| /** |
| * @return {string} |
| */ |
| projectId: function() |
| { |
| return this._projectId; |
| }, |
| |
| /** |
| * @return {string} |
| */ |
| path: function() |
| { |
| return this._path; |
| }, |
| |
| /** |
| * @return {number} |
| */ |
| lineNumber: function() |
| { |
| return this._lineNumber; |
| }, |
| |
| /** |
| * @return {WebInspector.UISourceCode} |
| */ |
| uiSourceCode: function() |
| { |
| return this._breakpointManager._workspace.uiSourceCode(this._projectId, this._path); |
| }, |
| |
| /** |
| * @param {WebInspector.DebuggerModel.Location} location |
| */ |
| _addResolvedLocation: function(location) |
| { |
| this._liveLocations.push(this._breakpointManager._debuggerModel.createLiveLocation(location, this._locationUpdated.bind(this, location))); |
| }, |
| |
| /** |
| * @param {WebInspector.DebuggerModel.Location} location |
| * @param {WebInspector.UILocation} uiLocation |
| */ |
| _locationUpdated: function(location, uiLocation) |
| { |
| var stringifiedLocation = location.scriptId + ":" + location.lineNumber + ":" + location.columnNumber; |
| var oldUILocation = /** @type {WebInspector.UILocation} */ (this._uiLocations[stringifiedLocation]); |
| if (oldUILocation) |
| this._breakpointManager._uiLocationRemoved(this, oldUILocation); |
| if (this._uiLocations[""]) { |
| var defaultLocation = this._uiLocations[""]; |
| delete this._uiLocations[""]; |
| this._breakpointManager._uiLocationRemoved(this, defaultLocation); |
| } |
| this._uiLocations[stringifiedLocation] = uiLocation; |
| this._breakpointManager._uiLocationAdded(this, uiLocation); |
| }, |
| |
| /** |
| * @return {boolean} |
| */ |
| enabled: function() |
| { |
| return this._enabled; |
| }, |
| |
| /** |
| * @param {boolean} enabled |
| */ |
| setEnabled: function(enabled) |
| { |
| this._updateBreakpoint(this._condition, enabled); |
| }, |
| |
| /** |
| * @return {string} |
| */ |
| condition: function() |
| { |
| return this._condition; |
| }, |
| |
| /** |
| * @param {string} condition |
| */ |
| setCondition: function(condition) |
| { |
| this._updateBreakpoint(condition, this._enabled); |
| }, |
| |
| /** |
| * @param {string} condition |
| * @param {boolean} enabled |
| */ |
| _updateBreakpoint: function(condition, enabled) |
| { |
| if (this._enabled === enabled && this._condition === condition) |
| return; |
| this._removeFromDebugger(); |
| this._enabled = enabled; |
| this._condition = condition; |
| this._breakpointManager._storage._updateBreakpoint(this); |
| this._fakeBreakpointAtPrimaryLocation(); |
| this._updateInDebugger(); |
| }, |
| |
| _updateInDebugger: function() |
| { |
| var uiSourceCode = this.uiSourceCode(); |
| if (!uiSourceCode || !uiSourceCode.hasSourceMapping()) |
| return; |
| var scriptFile = uiSourceCode && uiSourceCode.scriptFile(); |
| if (this._enabled && !(scriptFile && scriptFile.hasDivergedFromVM())) |
| this._setInDebugger(); |
| }, |
| |
| /** |
| * @param {boolean=} keepInStorage |
| */ |
| remove: function(keepInStorage) |
| { |
| var removeFromStorage = !keepInStorage; |
| this._resetLocations(); |
| this._removeFromDebugger(); |
| this._breakpointManager._removeBreakpoint(this, removeFromStorage); |
| }, |
| |
| _setInDebugger: function() |
| { |
| this._removeFromDebugger(); |
| var uiSourceCode = this._breakpointManager._workspace.uiSourceCode(this._projectId, this._path); |
| if (!uiSourceCode) |
| return; |
| var rawLocation = uiSourceCode.uiLocationToRawLocation(this._lineNumber, 0); |
| var debuggerModelLocation = /** @type {WebInspector.DebuggerModel.Location} */ (rawLocation); |
| if (debuggerModelLocation) |
| this._breakpointManager._debuggerModel.setBreakpointByScriptLocation(debuggerModelLocation, this._condition, this._didSetBreakpointInDebugger.bind(this)); |
| else if (uiSourceCode.url) |
| this._breakpointManager._debuggerModel.setBreakpointByURL(uiSourceCode.url, this._lineNumber, 0, this._condition, this._didSetBreakpointInDebugger.bind(this)); |
| }, |
| |
| /** |
| * @this {WebInspector.BreakpointManager.Breakpoint} |
| * @param {?DebuggerAgent.BreakpointId} breakpointId |
| * @param {Array.<WebInspector.DebuggerModel.Location>} locations |
| */ |
| _didSetBreakpointInDebugger: function(breakpointId, locations) |
| { |
| if (!breakpointId) { |
| this._resetLocations(); |
| this._breakpointManager._removeBreakpoint(this, false); |
| return; |
| } |
| |
| this._debuggerId = breakpointId; |
| this._breakpointManager._breakpointForDebuggerId[breakpointId] = this; |
| |
| if (!locations.length) { |
| this._fakeBreakpointAtPrimaryLocation(); |
| return; |
| } |
| |
| this._resetLocations(); |
| for (var i = 0; i < locations.length; ++i) { |
| var script = this._breakpointManager._debuggerModel.scriptForId(locations[i].scriptId); |
| var uiLocation = script.rawLocationToUILocation(locations[i].lineNumber, locations[i].columnNumber); |
| if (this._breakpointManager.findBreakpoint(uiLocation.uiSourceCode, uiLocation.lineNumber)) { |
| // location clash |
| this.remove(); |
| return; |
| } |
| } |
| |
| for (var i = 0; i < locations.length; ++i) |
| this._addResolvedLocation(locations[i]); |
| }, |
| |
| _removeFromDebugger: function() |
| { |
| if (!this._debuggerId) |
| return; |
| this._breakpointManager._debuggerModel.removeBreakpoint(this._debuggerId); |
| delete this._breakpointManager._breakpointForDebuggerId[this._debuggerId]; |
| delete this._debuggerId; |
| }, |
| |
| _resetLocations: function() |
| { |
| for (var stringifiedLocation in this._uiLocations) |
| this._breakpointManager._uiLocationRemoved(this, this._uiLocations[stringifiedLocation]); |
| |
| for (var i = 0; i < this._liveLocations.length; ++i) |
| this._liveLocations[i].dispose(); |
| this._liveLocations = []; |
| |
| this._uiLocations = {}; |
| }, |
| |
| /** |
| * @return {string} |
| */ |
| _breakpointStorageId: function() |
| { |
| return WebInspector.BreakpointManager._breakpointStorageId(this._sourceFileId, this._lineNumber); |
| }, |
| |
| _fakeBreakpointAtPrimaryLocation: function() |
| { |
| this._resetLocations(); |
| var uiSourceCode = this._breakpointManager._workspace.uiSourceCode(this._projectId, this._path); |
| if (!uiSourceCode) |
| return; |
| var uiLocation = new WebInspector.UILocation(uiSourceCode, this._lineNumber, 0); |
| this._uiLocations[""] = uiLocation; |
| this._breakpointManager._uiLocationAdded(this, uiLocation); |
| } |
| } |
| |
| /** |
| * @constructor |
| * @param {WebInspector.BreakpointManager} breakpointManager |
| * @param {WebInspector.Setting} setting |
| */ |
| WebInspector.BreakpointManager.Storage = function(breakpointManager, setting) |
| { |
| this._breakpointManager = breakpointManager; |
| this._setting = setting; |
| var breakpoints = this._setting.get(); |
| /** @type {Object.<string,WebInspector.BreakpointManager.Storage.Item>} */ |
| this._breakpoints = {}; |
| for (var i = 0; i < breakpoints.length; ++i) { |
| var breakpoint = /** @type {WebInspector.BreakpointManager.Storage.Item} */ (breakpoints[i]); |
| this._breakpoints[breakpoint.sourceFileId + ":" + breakpoint.lineNumber] = breakpoint; |
| } |
| } |
| |
| WebInspector.BreakpointManager.Storage.prototype = { |
| mute: function() |
| { |
| this._muted = true; |
| }, |
| |
| unmute: function() |
| { |
| delete this._muted; |
| }, |
| |
| /** |
| * @param {WebInspector.UISourceCode} uiSourceCode |
| * @return {Array.<WebInspector.BreakpointManager.Storage.Item>} |
| */ |
| breakpointItems: function(uiSourceCode) |
| { |
| var result = []; |
| var sourceFileId = WebInspector.BreakpointManager._sourceFileId(uiSourceCode); |
| for (var id in this._breakpoints) { |
| var breakpoint = this._breakpoints[id]; |
| if (breakpoint.sourceFileId === sourceFileId) |
| result.push(breakpoint); |
| } |
| return result; |
| }, |
| |
| /** |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| */ |
| _updateBreakpoint: function(breakpoint) |
| { |
| if (this._muted || !breakpoint._breakpointStorageId()) |
| return; |
| this._breakpoints[breakpoint._breakpointStorageId()] = new WebInspector.BreakpointManager.Storage.Item(breakpoint); |
| this._save(); |
| }, |
| |
| /** |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| */ |
| _removeBreakpoint: function(breakpoint) |
| { |
| if (this._muted) |
| return; |
| delete this._breakpoints[breakpoint._breakpointStorageId()]; |
| this._save(); |
| }, |
| |
| _save: function() |
| { |
| var breakpointsArray = []; |
| for (var id in this._breakpoints) |
| breakpointsArray.push(this._breakpoints[id]); |
| this._setting.set(breakpointsArray); |
| } |
| } |
| |
| /** |
| * @constructor |
| * @param {WebInspector.BreakpointManager.Breakpoint} breakpoint |
| */ |
| WebInspector.BreakpointManager.Storage.Item = function(breakpoint) |
| { |
| this.sourceFileId = breakpoint._sourceFileId; |
| this.lineNumber = breakpoint.lineNumber(); |
| this.condition = breakpoint.condition(); |
| this.enabled = breakpoint.enabled(); |
| } |
| |
| /** @type {WebInspector.BreakpointManager} */ |
| WebInspector.breakpointManager = null; |