systrace: fix a bug with userland thread states

This change fixes an issue where userland threads would not display the
color-coded thread state above their call traces.  It also adds config.pyc to
the .gitignore file.

Change-Id: Ic9135310880a9a805722b0707bc37336c026a7d6
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..bdc160b
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+config.pyc
diff --git a/script.js b/script.js
index c7380b8..18def3d 100644
--- a/script.js
+++ b/script.js
@@ -53,24 +53,24 @@
 importEvents:function(){this.importCpuData();this.alignClocks()&&this.buildPerThreadCpuSlicesFromCpuState()},finalizeImport:function(){},buildPerThreadCpuSlicesFromCpuState:function(){for(var a in this.cpuStates_)for(var b=this.cpuStates_[a].cpu,d=0;d<b.slices.length;d++){var c=b.slices[d],f=this.threadsByLinuxPid[c.args.tid];f&&(f.tempCpuSlices||(f.tempCpuSlices=[]),c.index=d,f.tempCpuSlices.push(c))}var e=tracing.getColorIdByName("running"),h=tracing.getColorIdByName("runnable"),g=tracing.getColorIdByName("sleeping"),
 o=tracing.getColorIdByName("iowait");this.model_.getAllThreads().forEach(function(a){if(a.tempCpuSlices){var b=a.tempCpuSlices;delete a.tempCpuSlices;b.sort(function(a,b){var d=a.start-b.start;return 0==d?a.index-b.index:d});var d=[];if(b.length){var c=b[0];d.push(new tracing.TimelineSlice("Running",e,c.start,{},c.duration))}for(c=1;c<b.length;c++){var f=b[c-1],m=b[c],i=m.start-f.end;if("S"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Sleeping",g,f.end,{},i));else if("R"==f.args.stateWhenDescheduled||
 "R+"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Runnable",h,f.end,{},i));else if("D"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Uninterruptible Sleep",o,f.end,{},i));else if("T"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("__TASK_STOPPED",o,f.end,{},i));else if("t"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("debug",o,f.end,{},i));else if("Z"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Zombie",o,f.end,{},
-i));else if("X"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Exit Dead",o,f.end,{},i));else if("x"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Task Dead",o,f.end,{},i));else if("W"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("WakeKill",o,f.end,{},i));else if("D|W"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Uninterruptable Sleep | WakeKill",o,f.end,{},i));else throw"Unrecognized state: "+f.args.stateWhenDescheduled;d.push(new tracing.TimelineSlice("Running",
+i));else if("X"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Exit Dead",o,f.end,{},i));else if("x"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Task Dead",o,f.end,{},i));else if("W"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("WakeKill",o,f.end,{},i));else if("D|W"==f.args.stateWhenDescheduled)d.push(new tracing.TimelineSlice("Uninterruptible Sleep | WakeKill",o,f.end,{},i));else throw"Unrecognized state: "+f.args.stateWhenDescheduled;d.push(new tracing.TimelineSlice("Running",
 e,m.start,{},m.duration))}a.cpuSlices=d}})},alignClocks:function(){if(0==this.clockSyncRecords_.length){if(!this.isAdditionalImport_)return;this.abortImport();return!1}var a=this.clockSyncRecords_[0];if(0==a.parentTS||a.parentTS==a.perfTS)return!0;var a=a.parentTS-a.perfTS,b;for(b in this.cpuStates_){for(var d=this.cpuStates_[b].cpu,c=0;c<d.slices.length;c++){var f=d.slices[c];f.start+=a;f.duration=f.duration}for(var e in d.counters){c=d.counters[e];for(f=0;f<c.timestamps.length;f++)c.timestamps[f]+=
 a}}for(var h in this.kernelThreadStates_){b=this.kernelThreadStates_[h].thread;for(c=0;c<b.subRows[0].length;c++)b.subRows[0][c].start+=a}return!0},abortImport:function(){if(this.pushedEventsToThreads)throw"Cannot abort, have alrady pushedCpuDataToThreads.";for(var a in this.cpuStates_)delete this.model_.cpus[a];for(var b in this.kernelThreadStates_){a=this.kernelThreadStates_[b].thread;var d=a.parent;delete d.threads[a.tid];delete this.model_.processes[d.pid]}this.model_.importErrors.push("Cannot import kernel trace without a clock sync.")},
 markPidRunnable:function(){},importError:function(a){this.model_.importErrors.push("Line "+(this.lineNumber+1)+": "+a)},malformedEvent:function(a){this.importError("Malformed "+a+" event")},openSlice:function(a,b,d){a.openSliceTS=d;a.openSlice=b},closeSlice:function(a,b,d){a.openSlice&&(b=new tracing.TimelineSlice(a.openSlice,tracing.getStringColorId(a.openSlice),a.openSliceTS,d,b-a.openSliceTS),a.thread.subRows[0].push(b),a.openSlice=void 0)},getThreadState:function(a){return this.threadStateByKPID_[this.parsePid(a)]},
-getOrCreateThreadState:function(a,b){var d=this.parsePid(a),c=this.threadStateByKPID_[d];c||(c=new e,c.threadName=this.parseThreadName(a),c.tid=d,c.pid=b,c.thread=this.model_.getOrCreateProcess(b).getOrCreateThread(d),c.thread.name||(c.thread.name=c.threadName),this.threadStateByKPID_[d]=c);return c},processBegin:function(a,b,d,c){a=this.getOrCreateThreadState(a,c);c=tracing.getStringColorId(b);b=new tracing.TimelineThreadSlice(b,c,d,null);a.openSlices.push(b)},processEnd:function(a,b){var d=this.getThreadState(a);
-if(d&&0!=d.openSlices.length){var c=d.openSlices.pop();c.duration=b-c.start;d.thread.getSubrow(d.openSlices.length).push(c);d.openSlices.length&&d.openSlices[d.openSlices.length-1].subSlices.push(c)}},autoCloseOpenSlices:function(){this.model_.updateBounds();var a=[],b;for(b in this.threadStateByKPID_)for(var d=this.threadStateByKPID_[b],c=0;c<d.openSlices.length;c++){var f=d.openSlices[c];a.push(f.start);for(var e=0;e<f.subSlices.length;e++){var h=f.subSlices[e];a.push(h.start);h.duration&&a.push(h.end)}}a=
-this.model_.maxTimestamp?Math.max(this.model_.maxTimestamp,Math.max.apply(Math,a)):Math.max.apply(Math,a);for(b in this.threadStateByKPID_)for(d=this.threadStateByKPID_[b];0<d.openSlices.length;)f=d.openSlices.pop(),f.duration=a-f.start,f.didNotFinish=!0,d.thread.getSubrow(d.openSlices.length).push(f),d.openSlices.length&&d.openSlices[d.openSlices.length-1].subSlices.push(f)},processCounter:function(a,b,d,c){a=this.model_.getOrCreateProcess(c).getOrCreateCounter("",a);0==a.numSeries&&(a.seriesNames.push("state"),
-a.seriesColors.push(tracing.getStringColorId(a.name+".state")));a.timestamps.push(b);a.samples.push(d)},importCpuData:function(){this.lines_=this.events_.split("\n");for(this.lineNumber=0;this.lineNumber<this.lines_.length;++this.lineNumber){var a=this.lines_[this.lineNumber];if(!(/^#/.exec(a)||0==a.length)){var b=f.exec(a);if(b){var a=b[1],d=b[2],c=b[4],e=b[5],b=b[6],h=this.eventDefinitions[e];if(h){var g;if(h.format){if(g=h.format.exec(b),!g){this.malformedEvent(e);continue}}else g={};g.timestamp=
-1E3*parseFloat(c);g.name=e;g.info=b;g.taskId=a;g.cpuState=this.getOrCreateCpuState(parseInt(d));h.handler&&h.handler(this,g)}else console.log("unknown event "+e)}else this.importError("Unrecognized line: "+a)}}},eventDefinitions:{sched_switch:{format:RegExp("prev_comm=(.+) prev_pid=(\\d+) prev_prio=(\\d+) prev_state=(\\S+) ==> next_comm=(.+) next_pid=(\\d+) next_prio=(\\d+)"),handler:function(a,b){var d=b[4],c=b[5],f=parseInt(b[6]),e=parseInt(b[7]);b.cpuState.switchRunningLinuxPid(a,d,b.timestamp,
-f,c,e)}},sched_wakeup:{format:/comm=(.+) pid=(\d+) prio=(\d+) success=(\d+) target_cpu=(\d+)/,handler:function(a,b){var d=b[1],c=parseInt(b[2]),f=parseInt(b[3]);a.markPidRunnable(b.timestamp,c,d,f)}},power_start:{format:/type=(\d+) state=(\d) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[3]),d=a.getOrCreateCpuState(d);if("1"==b[1]){d=d.cpu.getOrCreateCounter("","C-State");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));var c=parseInt(b[2]);
-d.timestamps.push(b.timestamp);d.samples.push(c)}else a.importError("Don't understand power_start events of type "+b[1])}},power_frequency:{format:/type=(\d+) state=(\d+) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[3]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","Power Frequency");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));var c=parseInt(b[2]);d.timestamps.push(b.timestamp);d.samples.push(c)}},cpu_frequency:{format:/state=(\d+) cpu_id=(\d)+/,
-handler:function(a,b){var d=parseInt(b[2]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","Clock Frequency");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));var c=parseInt(b[1]);d.timestamps.push(b.timestamp);d.samples.push(c)}},cpu_idle:{format:/state=(\d+) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[2]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","C-State");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name)));
-var c=parseInt(b[1]);4294967295!=c?d.samples.push(c):d.samples.push(0);d.timestamps.push(b.timestamp)}},workqueue_execute_start:{format:/work struct (.+): function (\S+)/,handler:function(a,b){var d=a.getOrCreateKernelThread(b.taskId);a.openSlice(d,b[2],b.timestamp)}},workqueue_execute_end:{format:/work struct (.+)/,handler:function(a,b){var d=a.getOrCreateKernelThread(b.taskId);a.closeSlice(d,b.timestamp,{})}},workqueue_queue_work:{},workqueue_activate_work:{},ext4_sync_file_enter:{format:/dev (\d+,\d+) ino (\d+) parent (\d+) datasync (\d+)/,
-handler:function(a,b){var d=a.getOrCreateKernelThread("ext4:"+b.taskId);a.openSlice(d,1==b[4]?"fdatasync":"fsync",b.timestamp)}},ext4_sync_file_exit:{format:/dev (\d+,\d+) ino (\d+) ret (\d+)/,handler:function(a,b){var d=a.getOrCreateKernelThread("ext4:"+b.taskId);a.closeSlice(d,b.timestamp,{dev:b[1]})}},block_rq_issue:{format:/(\d+,\d+) (F)?([DWRN])(F)?(A)?(S)?(M)? .*/,handler:function(a,b){var d=a.getOrCreateKernelThread("block:"+b.taskId),c;switch(b[3]){case "D":c="discard";break;case "W":c="write";
-break;case "R":c="read";break;case "N":c="none";break;default:c="unknown"}b[2]&&(c+=" flush");"F"==b[4]&&(c+=" fua");"A"==b[5]&&(c+=" ahead");"S"==b[6]&&(c+=" sync");"M"==b[7]&&(c+=" meta");a.openSlice(d,c,b.timestamp)}},block_rq_complete:{format:/(\d+,\d+).*/,handler:function(a,b){var d=a.getOrCreateKernelThread("block:"+b.taskId);a.closeSlice(d,b.timestamp,{dev:b[1]})}},i915_gem_object_pwrite:{format:/obj=(.+), offset=(\d+), len=(\d+)/,handler:function(a,b){var d=b[1],c=parseInt(b[2]),f=parseInt(b[3]),
-e=a.getOrCreateKernelThread("i915_gem",0,1);a.openSlice(e,"pwrite:"+d,b.timestamp);a.closeSlice(e,b.timestamp,{obj:d,offset:c,len:f})}},i915_flip_request:{format:/plane=(\d+), obj=(.+)/,handler:function(a,b){var d=parseInt(b[1]),c=b[2],f=a.getOrCreateKernelThread("i915_flip",0,2);a.openSlice(f,"flip:"+c+"/"+d,b.timestamp)}},i915_flip_complete:{format:/plane=(\d+), obj=(.+)/,handler:function(a,b){var d=parseInt(b[1]),c=b[2],f=a.getOrCreateKernelThread("i915_flip",0,2);a.closeSlice(f,b.timestamp,{obj:c,
-plane:d})}},tracing_mark_write:{handler:function(a,b){var d=h.exec(b.info);if(d)a.clockSyncRecords_.push({perfTS:b.timestamp,parentTS:1E3*d[1]});else switch(d=b.info.split("|"),d[0]){case "B":var c=parseInt(d[1]),f=d[2];a.processBegin(b.taskId,f,b.timestamp,c);break;case "E":a.processEnd(b.taskId,b.timestamp);break;case "C":c=parseInt(d[1]);f=d[2];d=parseInt(d[3]);a.processCounter(f,b.timestamp,d,c);break;default:a.malformedEvent(b.name)}}}}};c.prototype.eventDefinitions["0"]=c.prototype.eventDefinitions.tracing_mark_write;
-TestExports.eventDefinitions=c.prototype.eventDefinitions;tracing.TimelineModel.registerImporter(c);return{LinuxPerfImporter:c,_LinuxPerfImporterTestExports:TestExports}});cr.define("tracing",function(){function g(){this.openSlices=[]}function e(c,f){this.model_=c;"string"===typeof f||f instanceof String?("["==f[0]&&(n=f.length,"]"!=f[n-1]&&"\n"!=f[n-1]?f+="]":"]"!=f[n-2]&&"\n"==f[n-1]?f+="]":"]"!=f[n-3]&&("\r"==f[n-2]&&"\n"==f[n-1])&&(f+="]")),this.events_=JSON.parse(f)):this.events_=f;this.events_.traceEvents&&(this.events_=this.events_.traceEvents);this.threadStateByPTID_={};this.allAsyncEvents_=[]}e.canImport=function(c){return"string"===typeof c||c instanceof String?
+getOrCreateThreadState:function(a,b){var d=this.parsePid(a),c=this.threadStateByKPID_[d];c||(c=new e,c.threadName=this.parseThreadName(a),c.tid=d,c.pid=b,c.thread=this.model_.getOrCreateProcess(b).getOrCreateThread(d),this.threadsByLinuxPid[d]=c.thread,c.thread.name||(c.thread.name=c.threadName),this.threadStateByKPID_[d]=c);return c},processBegin:function(a,b,d,c){a=this.getOrCreateThreadState(a,c);c=tracing.getStringColorId(b);b=new tracing.TimelineThreadSlice(b,c,d,null);a.openSlices.push(b)},
+processEnd:function(a,b){var d=this.getThreadState(a);if(d&&0!=d.openSlices.length){var c=d.openSlices.pop();c.duration=b-c.start;d.thread.getSubrow(d.openSlices.length).push(c);d.openSlices.length&&d.openSlices[d.openSlices.length-1].subSlices.push(c)}},autoCloseOpenSlices:function(){this.model_.updateBounds();var a=[],b;for(b in this.threadStateByKPID_)for(var d=this.threadStateByKPID_[b],c=0;c<d.openSlices.length;c++){var f=d.openSlices[c];a.push(f.start);for(var e=0;e<f.subSlices.length;e++){var h=
+f.subSlices[e];a.push(h.start);h.duration&&a.push(h.end)}}a=this.model_.maxTimestamp?Math.max(this.model_.maxTimestamp,Math.max.apply(Math,a)):Math.max.apply(Math,a);for(b in this.threadStateByKPID_)for(d=this.threadStateByKPID_[b];0<d.openSlices.length;)f=d.openSlices.pop(),f.duration=a-f.start,f.didNotFinish=!0,d.thread.getSubrow(d.openSlices.length).push(f),d.openSlices.length&&d.openSlices[d.openSlices.length-1].subSlices.push(f)},processCounter:function(a,b,d,c){a=this.model_.getOrCreateProcess(c).getOrCreateCounter("",
+a);0==a.numSeries&&(a.seriesNames.push("state"),a.seriesColors.push(tracing.getStringColorId(a.name+".state")));a.timestamps.push(b);a.samples.push(d)},importCpuData:function(){this.lines_=this.events_.split("\n");for(this.lineNumber=0;this.lineNumber<this.lines_.length;++this.lineNumber){var a=this.lines_[this.lineNumber];if(!(/^#/.exec(a)||0==a.length)){var b=f.exec(a);if(b){var a=b[1],d=b[2],c=b[4],e=b[5],b=b[6],h=this.eventDefinitions[e];if(h){var g;if(h.format){if(g=h.format.exec(b),!g){this.malformedEvent(e);
+continue}}else g={};g.timestamp=1E3*parseFloat(c);g.name=e;g.info=b;g.taskId=a;g.cpuState=this.getOrCreateCpuState(parseInt(d));h.handler&&h.handler(this,g)}else console.log("unknown event "+e)}else this.importError("Unrecognized line: "+a)}}},eventDefinitions:{sched_switch:{format:RegExp("prev_comm=(.+) prev_pid=(\\d+) prev_prio=(\\d+) prev_state=(\\S+) ==> next_comm=(.+) next_pid=(\\d+) next_prio=(\\d+)"),handler:function(a,b){var d=b[4],c=b[5],f=parseInt(b[6]),e=parseInt(b[7]);b.cpuState.switchRunningLinuxPid(a,
+d,b.timestamp,f,c,e)}},sched_wakeup:{format:/comm=(.+) pid=(\d+) prio=(\d+) success=(\d+) target_cpu=(\d+)/,handler:function(a,b){var d=b[1],c=parseInt(b[2]),f=parseInt(b[3]);a.markPidRunnable(b.timestamp,c,d,f)}},power_start:{format:/type=(\d+) state=(\d) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[3]),d=a.getOrCreateCpuState(d);if("1"==b[1]){d=d.cpu.getOrCreateCounter("","C-State");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));
+var c=parseInt(b[2]);d.timestamps.push(b.timestamp);d.samples.push(c)}else a.importError("Don't understand power_start events of type "+b[1])}},power_frequency:{format:/type=(\d+) state=(\d+) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[3]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","Power Frequency");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));var c=parseInt(b[2]);d.timestamps.push(b.timestamp);d.samples.push(c)}},
+cpu_frequency:{format:/state=(\d+) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[2]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","Clock Frequency");0==d.numSeries&&(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name+".state")));var c=parseInt(b[1]);d.timestamps.push(b.timestamp);d.samples.push(c)}},cpu_idle:{format:/state=(\d+) cpu_id=(\d)+/,handler:function(a,b){var d=parseInt(b[2]),d=a.getOrCreateCpuState(d).cpu.getOrCreateCounter("","C-State");0==d.numSeries&&
+(d.seriesNames.push("state"),d.seriesColors.push(tracing.getStringColorId(d.name)));var c=parseInt(b[1]);4294967295!=c?d.samples.push(c):d.samples.push(0);d.timestamps.push(b.timestamp)}},workqueue_execute_start:{format:/work struct (.+): function (\S+)/,handler:function(a,b){var d=a.getOrCreateKernelThread(b.taskId);a.openSlice(d,b[2],b.timestamp)}},workqueue_execute_end:{format:/work struct (.+)/,handler:function(a,b){var d=a.getOrCreateKernelThread(b.taskId);a.closeSlice(d,b.timestamp,{})}},workqueue_queue_work:{},
+workqueue_activate_work:{},ext4_sync_file_enter:{format:/dev (\d+,\d+) ino (\d+) parent (\d+) datasync (\d+)/,handler:function(a,b){var d=a.getOrCreateKernelThread("ext4:"+b.taskId);a.openSlice(d,1==b[4]?"fdatasync":"fsync",b.timestamp)}},ext4_sync_file_exit:{format:/dev (\d+,\d+) ino (\d+) ret (\d+)/,handler:function(a,b){var d=a.getOrCreateKernelThread("ext4:"+b.taskId);a.closeSlice(d,b.timestamp,{dev:b[1]})}},block_rq_issue:{format:/(\d+,\d+) (F)?([DWRN])(F)?(A)?(S)?(M)? .*/,handler:function(a,
+b){var d=a.getOrCreateKernelThread("block:"+b.taskId),c;switch(b[3]){case "D":c="discard";break;case "W":c="write";break;case "R":c="read";break;case "N":c="none";break;default:c="unknown"}b[2]&&(c+=" flush");"F"==b[4]&&(c+=" fua");"A"==b[5]&&(c+=" ahead");"S"==b[6]&&(c+=" sync");"M"==b[7]&&(c+=" meta");a.openSlice(d,c,b.timestamp)}},block_rq_complete:{format:/(\d+,\d+).*/,handler:function(a,b){var d=a.getOrCreateKernelThread("block:"+b.taskId);a.closeSlice(d,b.timestamp,{dev:b[1]})}},i915_gem_object_pwrite:{format:/obj=(.+), offset=(\d+), len=(\d+)/,
+handler:function(a,b){var d=b[1],c=parseInt(b[2]),f=parseInt(b[3]),e=a.getOrCreateKernelThread("i915_gem",0,1);a.openSlice(e,"pwrite:"+d,b.timestamp);a.closeSlice(e,b.timestamp,{obj:d,offset:c,len:f})}},i915_flip_request:{format:/plane=(\d+), obj=(.+)/,handler:function(a,b){var d=parseInt(b[1]),c=b[2],f=a.getOrCreateKernelThread("i915_flip",0,2);a.openSlice(f,"flip:"+c+"/"+d,b.timestamp)}},i915_flip_complete:{format:/plane=(\d+), obj=(.+)/,handler:function(a,b){var d=parseInt(b[1]),c=b[2],f=a.getOrCreateKernelThread("i915_flip",
+0,2);a.closeSlice(f,b.timestamp,{obj:c,plane:d})}},tracing_mark_write:{handler:function(a,b){var d=h.exec(b.info);if(d)a.clockSyncRecords_.push({perfTS:b.timestamp,parentTS:1E3*d[1]});else switch(d=b.info.split("|"),d[0]){case "B":var c=parseInt(d[1]),f=d[2];a.processBegin(b.taskId,f,b.timestamp,c);break;case "E":a.processEnd(b.taskId,b.timestamp);break;case "C":c=parseInt(d[1]);f=d[2];d=parseInt(d[3]);a.processCounter(f,b.timestamp,d,c);break;default:a.malformedEvent(b.name)}}}}};c.prototype.eventDefinitions["0"]=
+c.prototype.eventDefinitions.tracing_mark_write;TestExports.eventDefinitions=c.prototype.eventDefinitions;tracing.TimelineModel.registerImporter(c);return{LinuxPerfImporter:c,_LinuxPerfImporterTestExports:TestExports}});cr.define("tracing",function(){function g(){this.openSlices=[]}function e(c,f){this.model_=c;"string"===typeof f||f instanceof String?("["==f[0]&&(n=f.length,"]"!=f[n-1]&&"\n"!=f[n-1]?f+="]":"]"!=f[n-2]&&"\n"==f[n-1]?f+="]":"]"!=f[n-3]&&("\r"==f[n-2]&&"\n"==f[n-1])&&(f+="]")),this.events_=JSON.parse(f)):this.events_=f;this.events_.traceEvents&&(this.events_=this.events_.traceEvents);this.threadStateByPTID_={};this.allAsyncEvents_=[]}e.canImport=function(c){return"string"===typeof c||c instanceof String?
 "{"==c[0]||"["==c[0]:c instanceof Array&&c.length&&c[0].ph?!0:c.traceEvents?c.traceEvents instanceof Array&&c.traceEvents[0].ph:!1};e.prototype={__proto__:Object.prototype,processBeginEvent:function(c,f,e){var a=tracing.getStringColorId(e.name),c={index:c,slice:new tracing.TimelineThreadSlice(e.name,a,e.ts/1E3,e.args)};e.uts&&(c.slice.startInUserTime=e.uts/1E3);"0"===e.args["ui-nest"]?this.model_.importErrors.push("ui-nest no longer supported."):f.openSlices.push(c)},processEndEvent:function(c,f){if("0"===
 f.args["ui-nest"])this.model_.importErrors.push("ui-nest no longer supported.");else if(0!=c.openSlices.length){var e=c.openSlices.pop().slice;e.duration=f.ts/1E3-e.start;f.uts&&(e.durationInUserTime=f.uts/1E3-e.startInUserTime);for(var a in f.args)e.args[a]=f.args[a];this.model_.getOrCreateProcess(f.pid).getOrCreateThread(f.tid).getSubrow(c.openSlices.length).push(e);c.openSlices.length&&c.openSlices[c.openSlices.length-1].slice.subSlices.push(e)}},processAsyncEvent:function(c,f,e){c=this.model_.getOrCreateProcess(e.pid).getOrCreateThread(e.tid);
 this.allAsyncEvents_.push({event:e,thread:c})},autoCloseOpenSlices:function(){this.model_.updateBounds();var c=[],f;for(f in this.threadStateByPTID_)for(var e=this.threadStateByPTID_[f],a=0;a<e.openSlices.length;a++){var b=e.openSlices[a];c.push(b.slice.start);for(var d=0;d<b.slice.subSlices.length;d++){var g=b.slice.subSlices[d];c.push(g.start);g.duration&&c.push(g.end)}}c=this.model_.maxTimestamp?Math.max(this.model_.maxTimestamp,Math.max.apply(Math,c)):Math.max.apply(Math,c);for(f in this.threadStateByPTID_)for(e=
diff --git a/src/tracing/linux_perf_importer.js b/src/tracing/linux_perf_importer.js
index bb137a8..b0688fa 100644
--- a/src/tracing/linux_perf_importer.js
+++ b/src/tracing/linux_perf_importer.js
@@ -304,7 +304,7 @@
                 prevSlice.end, {}, midDuration));
           } else if (prevSlice.args.stateWhenDescheduled == 'D|W') {
             slices.push(new tracing.TimelineSlice(
-              'Uninterruptable Sleep | WakeKill', ioWaitId,
+              'Uninterruptible Sleep | WakeKill', ioWaitId,
               prevSlice.end, {}, midDuration));
           } else {
             throw 'Unrecognized state: ' + prevSlice.args.stateWhenDescheduled;
@@ -448,6 +448,7 @@
         state.pid = pid;
         state.thread = this.model_.getOrCreateProcess(pid).
             getOrCreateThread(kpid);
+        this.threadsByLinuxPid[kpid] = state.thread;
         if (!state.thread.name) {
           state.thread.name = state.threadName;
         }