// Copyright (c) 2012 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. 'use strict'; /** * @fileoverview Provides the ProcessBase class. */ base.require('base.guid'); base.require('base.range'); base.require('tracing.trace_model.counter'); base.require('tracing.trace_model.object_collection'); base.require('tracing.trace_model.thread'); base.require('tracing.trace_model_settings'); base.exportTo('tracing.trace_model', function() { var Thread = tracing.trace_model.Thread; var Counter = tracing.trace_model.Counter; /** * The ProcessBase is an partial base class, upon which Kernel * and Process are built. * * @constructor */ function ProcessBase(model) { if (!model) throw new Error('Must provide a model'); this.guid_ = base.GUID.allocate(); this.model = model; this.threads = {}; this.counters = {}; this.objects = new tracing.trace_model.ObjectCollection(this); this.bounds = new base.Range(); this.sortIndex = 0; this.ephemeralSettings = {}; }; ProcessBase.compare = function(x, y) { return x.sortIndex - y.sortIndex; }; ProcessBase.prototype = { /* * @return {Number} A globally unique identifier for this counter. */ get guid() { return this.guid_; }, /** * Gets the number of threads in this process. */ get numThreads() { var n = 0; for (var p in this.threads) { n++; } return n; }, toJSON: function() { var obj = new Object(); var keys = Object.keys(this); for (var i = 0; i < keys.length; i++) { var key = keys[i]; if (typeof this[key] == 'function') continue; if (key == 'model') continue; obj[key] = this[key]; } return obj; }, /** * Shifts all the timestamps inside this process forward by the amount * specified. */ shiftTimestampsForward: function(amount) { for (var tid in this.threads) this.threads[tid].shiftTimestampsForward(amount); for (var id in this.counters) this.counters[id].shiftTimestampsForward(amount); this.objects.shiftTimestampsForward(amount); }, /** * Closes any open slices. */ autoCloseOpenSlices: function(opt_maxTimestamp) { for (var tid in this.threads) { var thread = this.threads[tid]; thread.autoCloseOpenSlices(opt_maxTimestamp); } }, autoDeleteObjects: function(maxTimestamp) { this.objects.autoDeleteObjects(maxTimestamp); }, /** * Called by the model after finalizing imports, * but before joining refs. */ preInitializeObjects: function() { this.objects.preInitializeAllObjects(); }, /** * Called by the model after joining refs. */ initializeObjects: function() { this.objects.initializeAllObjects(); }, /** * Merge slices from the kernel with those from userland for each thread. */ mergeKernelWithUserland: function() { for (var tid in this.threads) { var thread = this.threads[tid]; thread.mergeKernelWithUserland(); } }, updateBounds: function() { this.bounds.reset(); for (var tid in this.threads) { this.threads[tid].updateBounds(); this.bounds.addRange(this.threads[tid].bounds); } for (var id in this.counters) { this.counters[id].updateBounds(); this.bounds.addRange(this.counters[id].bounds); } this.objects.updateBounds(); this.bounds.addRange(this.objects.bounds); }, addCategoriesToDict: function(categoriesDict) { for (var tid in this.threads) this.threads[tid].addCategoriesToDict(categoriesDict); for (var id in this.counters) categoriesDict[this.counters[id].category] = true; this.objects.addCategoriesToDict(categoriesDict); }, /** * @param {String} The name of the thread to find. * @return {Array} An array of all the matched threads. */ findAllThreadsNamed: function(name) { var namedThreads = []; for (var tid in this.threads) { var thread = this.threads[tid]; if (thread.name == name) namedThreads.push(thread); } return namedThreads; }, /** * Removes threads from the process that are fully empty. */ pruneEmptyContainers: function() { var threadsToKeep = {}; for (var tid in this.threads) { var thread = this.threads[tid]; if (!thread.isEmpty) threadsToKeep[tid] = thread; } this.threads = threadsToKeep; }, /** * @return {TimlineThread} The thread identified by tid on this process, * creating it if it doesn't exist. */ getOrCreateThread: function(tid) { if (!this.threads[tid]) this.threads[tid] = new Thread(this, tid); return this.threads[tid]; }, /** * @return {TimlineCounter} The counter on this process named 'name', * creating it if it doesn't exist. */ getOrCreateCounter: function(cat, name) { var id = cat + '.' + name; if (!this.counters[id]) this.counters[id] = new Counter(this, id, cat, name); return this.counters[id]; }, getSettingsKey: function() { throw new Error('Not implemented'); } }; return { ProcessBase: ProcessBase }; });