Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
6150f26
[DebuggerV2] Flesh out graph execution data display
caisq Apr 16, 2020
d7dd9c5
Flesh out scrolling effect; Improve CSS
caisq Apr 17, 2020
4b31ddb
Add unit tests for selectors
caisq Apr 17, 2020
20daabf
Add unit tests for reducers
caisq Apr 17, 2020
5eb5e10
Adjust CSS
caisq Apr 17, 2020
d1ef4ab
Add unit tests for effect
caisq Apr 17, 2020
4df718f
Add container tests
caisq Apr 17, 2020
964c20c
Fix loading spinner css
caisq Apr 17, 2020
9e37e35
Revert extraneous change
caisq Apr 17, 2020
ab58b65
Tweak some comments
caisq Apr 17, 2020
8893db2
[DebuggerV2] Add tensor-debug info to GraphExecutionComponent
caisq Apr 20, 2020
1d7b8d2
Merge branch 'master' into dbg2-graph-exec-1c
caisq Apr 21, 2020
a6d5e56
WIP: Add debug_tensor_value.ts
caisq Apr 22, 2020
14613da
Add logic and tests for FULL_TENSOR and FULL_HEALTH; doc string
caisq Apr 22, 2020
64282ad
Add undefined filling for shape
caisq Apr 22, 2020
02c8e32
Refactoring into DebugTensorValueComponent
caisq Apr 22, 2020
df83903
Refactor DebugTensorValueComponent into separate folder
caisq Apr 22, 2020
3820d93
Adjust breakdown component CSS
caisq Apr 22, 2020
ccbc314
Add DebugTensorShapeComponent
caisq Apr 22, 2020
1e90a8e
Add DebugTensorHasInfOrNaNComponent
caisq Apr 22, 2020
4f2bcdc
Switch ExecutionDataComponent to using DebugTensorValueCompoennt
caisq Apr 22, 2020
7f71cbb
Adding unit tests for debug-tensor-value components
caisq Apr 22, 2020
606f80f
Add more unit tests for debug-tensor-value components
caisq Apr 23, 2020
c4ab22c
Add more unit tests
caisq Apr 23, 2020
0dc3281
Fix typos
caisq Apr 23, 2020
8634808
Fix more typos
caisq Apr 23, 2020
0873c95
Address Stephan's comments
caisq Apr 24, 2020
a67a8f5
Address 2nd round of comments
caisq Apr 27, 2020
b33d934
Remove cruft
caisq Apr 27, 2020
b6ce533
Add missing BUILD dependency
caisq Apr 27, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ tf_ng_web_test_suite(
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/effects:debugger_effects_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/store:debugger_store_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/views/alerts:alerts_container_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/views/debug_tensor_value:debug_tensor_value_component_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/views/graph_executions:graph_executions_container_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/views/source_code:source_code_container_test_lib",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/views/source_code:source_code_test_lib",
Expand Down

Large diffs are not rendered by default.

13 changes: 13 additions & 0 deletions tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/store/BUILD
Original file line number Diff line number Diff line change
Expand Up @@ -31,15 +31,28 @@ ng_module(
],
)

ng_module(
name = "debug_tensor_value",
srcs = [
"debug_tensor_value.ts",
],
deps = [
":types",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin:tf_types",
],
)

tf_ts_library(
name = "debugger_store_test_lib",
testonly = True,
srcs = [
"debug_tensor_value_test.ts",
"debugger_reducers_test.ts",
"debugger_selectors_test.ts",
],
tsconfig = "//:tsconfig-test",
deps = [
":debug_tensor_value",
":store",
":types",
"//tensorboard/plugins/debugger_v2/tf_debugger_v2_plugin/actions",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,213 @@
/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
==============================================================================*/

import {DTYPE_ENUM_TO_NAME} from '../tf_dtypes';
import {DebugTensorValue, TensorDebugMode} from './debugger_types';

export interface RawDebugTensorValue {
tensorDebugMode: TensorDebugMode;
array: null | number[];
}

export interface RawDebugTensorValueNoTensor extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.NO_TENSOR;
array: null;
}

export interface RawDebugTensorValueCurtHealth extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.CURT_HEALTH;
array: [
number, // Tensor ID.
number // 0-1 indicator for the presence of inf/nan.
];
}

export interface RawDebugTensorValueConciseHealth extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.CURT_HEALTH;
array: [
number, // Tensor ID.
number, // Element count (size).
number, // -inf count.
number, // +inf count.
number // nan count.
];
}

export interface RawDebugTensorValueShape extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.SHAPE;
array: [
number, // Tensor ID.
number, // DType enum value.
number, // Rank.
number, // Size.
number, // Shape truncated at head to a maximum length of 6.
number,
number,
number,
number,
number
];
}

export interface RawDebugTensorValueFullHealth extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.FULL_HEALTH;
array: [
number, // Tensor ID.
number, // Device ID.
number, // DType enum value.
number, // Rank.
number, // Size.
number, // -inf count.
number, // +inf count.
number, // nan count.
number, // -finite count.
number, // zero count.
number // +finite count.
];
}

export interface RawDebugTensorValueFullTensor extends RawDebugTensorValue {
tensorDebugMode: TensorDebugMode.FULL_HEALTH;
array: null;
}

/**
* Parse a number array that represents debugging summary of an instrumented
* tensor value.
*
* @param tensorDebugMode and the array of number that represents various
* aspect of the instrumented tensor. The semantics of the numbers are
* determined by `tensorDebugMode`.
* @returns A DebugTensorValue object with the same information as
* carried by `array`, but represented in a more explicit fashion.
* For numbers that represent breakdown of numeric values by type
* (e.g., counts of -inf, +inf and nan), the corresponding fields
* in the returned object will be defined only if the count is non-zero.
*/
export function parseDebugTensorValue(
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high level question: I find this rather tedious. What happens if we just have hard dependency on jspb or OSS equivalent?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a little tedious. But this is the only place where this logic needs to exist in tensorboard. The background is that for efficiency, DebugNumericsSummaryV2 ops return a fixed-size 1D tensor for all instrumented tensors. The advantages of this format is that

  1. It is smaller in size compared to other options such as a proto or serialized proto
  2. All of such small tensors can be potentially stacked and transferred over device boundaries as a whole in future performance optimizations.

As such, the 1D vector must have a contract in what each number means (given the TensorDebugMode). This function here knows and carries out this contract.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am not too convinced about the performance argument. Protobuf, sure, may not be as efficient at representing such values as what you did here but it surely is closer to this than, say, JSON (jspb encodes values as array of arrays; it does not transfer binaries).

I am still okay with this because jspb dependency (closure version) on FE is quite not pleasant.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ack.

raw: RawDebugTensorValue
): DebugTensorValue {
const {tensorDebugMode, array} = raw;
switch (tensorDebugMode) {
case TensorDebugMode.NO_TENSOR: {
if (array !== null) {
throw new Error(
'Unexpectedly received non-null debug-tensor-value array ' +
'under NO_TENSOR mode'
);
}
return {};
}
case TensorDebugMode.CURT_HEALTH: {
if (array === null || array.length !== 2) {
throw new Error(
`Under CURT_HEALTH mode, expected debug-tensor-value array ` +
`to have length 2, but got ${JSON.stringify(array)}`
);
}
return {
hasInfOrNaN: Boolean(array[1]),
};
}
case TensorDebugMode.CONCISE_HEALTH: {
if (array === null || array.length !== 5) {
throw new Error(
`Under CONCISE_HEALTH mode, expected debug-tensor-value array ` +
`to have length 5, but got ${JSON.stringify(array)}`
);
}
const value: DebugTensorValue = {
size: array[1],
};
if (array[2] > 0) {
value.numNegativeInfs = array[2];
}
if (array[3] > 0) {
value.numPositiveInfs = array[3];
}
if (array[4] > 0) {
value.numNaNs = array[4];
}
return value;
}
case TensorDebugMode.SHAPE: {
if (array === null || array.length !== 10) {
throw new Error(
`Under SHAPE mode, expected debug-tensor-value array ` +
`to have length 10, but got ${JSON.stringify(array)}`
);
}
const rank = array[2];
let shape: number[] = array.slice(4, Math.min(4 + rank, array.length));
if (shape.length < rank) {
// The SHAPE mode truncates the shape at head.
shape = new Array<number>(rank - shape.length).concat(shape);
}
return {
dtype: DTYPE_ENUM_TO_NAME[array[1]],
rank,
size: array[3],
shape,
};
}
case TensorDebugMode.FULL_HEALTH: {
if (array === null || array.length !== 11) {
throw new Error(
`Under FULL_HEALTH mode, expected debug-tensor-value array ` +
`to have length 11, but got ${JSON.stringify(array)}`
);
}
const rank = array[3];
const value: DebugTensorValue = {
dtype: DTYPE_ENUM_TO_NAME[array[2]],
rank,
size: array[4],
};
if (array[5] > 0) {
value.numNegativeInfs = array[5];
}
if (array[6] > 0) {
value.numPositiveInfs = array[6];
}
if (array[7] > 0) {
value.numNaNs = array[7];
}
if (array[8] > 0) {
value.numNegativeFinites = array[8];
}
if (array[9] > 0) {
value.numZeros = array[9];
}
if (array[10] > 0) {
value.numPositiveFinites = array[10];
}
return value;
}
case TensorDebugMode.FULL_TENSOR: {
// Under FULL_TENSOR mode, the full tensor value is supplied via
// separate means. No summary values are provided for the tensor value.
if (array !== null) {
throw new Error(
'Unexpectedly received non-null debug-tensor-value array ' +
'under FULL_TENSOR mode'
);
}
return {};
}
default: {
throw new Error(`Unrecognized tensorDebugMode: ${tensorDebugMode}`);
}
}
}
Loading