// Copyright 2019 The MediaPipe Authors.
//
// 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.

syntax = "proto2";

package mediapipe;

import "mediapipe/framework/calculator.proto";

option java_package = "com.google.mediapipe.proto";
option java_outer_classname = "CalculatorProfileProto";

// Stores the profiling information.
//
// It is the responsibility of the user of this message to make sure the 'total'
// field and the interval information (num, size and count) are in a valid
// state and all get updated together.
//
// Each interval of the histogram is closed on the lower range and open on the
// higher end. An example histogram with interval_size=1000 and num_interval=3
// will have the following intervals:
// - First interval = [0, 1000)
// - Second interval = [1000, 2000)
// - Third interval = [2000, +inf)
//
// IMPORTANT: If You add any new field, update CalculatorProfiler::Reset()
// accordingly.
message TimeHistogram {
  // Total time (in microseconds).
  optional int64 total = 1 [default = 0];

  // Size of the runtimes histogram intervals (in microseconds) to generate the
  // histogram of the Process() time. The last interval extends to +inf.
  optional int64 interval_size_usec = 2 [default = 1000000 /* 1 sec */];

  // Number of intervals to generate the histogram of the Process() runtime.
  optional int64 num_intervals = 3 [default = 1];

  // Number of calls in each interval.
  repeated int64 count = 4;
}

// Stores the profiling information of a stream.
message StreamProfile {
  // Stream name.
  optional string name = 1;

  // If true, than this is a back edge input stream and won't be profiled.
  optional bool back_edge = 2 [default = false];

  // Total and histogram of the time that this stream took.
  optional TimeHistogram latency = 3;
}

// Stores the profiling information for a calculator node.
// All the times are in microseconds.
message CalculatorProfile {
  // The calculator name.
  optional string name = 1;

  // Total time the calculator spent on Open (in microseconds).
  optional int64 open_runtime = 2 [default = 0];

  // Total time the calculator spent on Close (in microseconds).
  optional int64 close_runtime = 3 [default = 0];

  // Total and histogram of the time that the calculator spent on the Process()
  // (in microseconds).
  optional TimeHistogram process_runtime = 4;

  // Total and histogram of the time that the input latency, ie. difference
  // between input timestamp and process call time.
  // (in microseconds).
  optional TimeHistogram process_input_latency = 5;

  // Total and histogram of the time that the output latency, ie. difference
  // between input timestamp and process finished time.
  optional TimeHistogram process_output_latency = 6;

  // Total and histogram of the time that input streams of this calculator took.
  repeated StreamProfile input_stream_profiles = 7;
}

// Latency timing for recent mediapipe packets.
message GraphTrace {
  // The timing for one packet across one packet stream.
  message StreamTrace {
    // The time at which the packet entered the stream.
    optional int64 start_time = 1;

    // The time at which the packet exited the stream.
    optional int64 finish_time = 2;

    // The identifying timetamp of the packet.
    optional int64 packet_timestamp = 3;

    // The index of the stream in the stream_name list.
    optional int32 stream_id = 4;

    // The address of the packet contents.
    optional int64 packet_id = 5 [deprecated = true];

    // Data describing the event, such as the packet contents.
    optional int64 event_data = 6;
  }

  // The kind of event recorded.
  enum EventType {
    UNKNOWN = 0;
    OPEN = 1;
    PROCESS = 2;
    CLOSE = 3;
    NOT_READY = 4;
    READY_FOR_PROCESS = 5;
    READY_FOR_CLOSE = 6;
    THROTTLED = 7;
    UNTHROTTLED = 8;
    CPU_TASK_USER = 9;
    CPU_TASK_SYSTEM = 10;
    GPU_TASK = 11;
    DSP_TASK = 12;
    TPU_TASK = 13;
    GPU_CALIBRATION = 14;
    PACKET_QUEUED = 15;
    GPU_TASK_INVOKE = 16;
    TPU_TASK_INVOKE = 17;
    CPU_TASK_INVOKE = 18;
  }
  //  //depot/mediapipe/framework/mediapipe_profiling.h:profiler_census_tags,
  //  //depot/mediapipe/framework/profiler/trace_buffer.h:event_type_list,
  // )

  // The timing for one packet set being processed at one caclulator node.
  message CalculatorTrace {
    // The index of the calculator node in the calculator_name list.
    optional int32 node_id = 1;

    // The input timestamp during Open, Process, or Close.
    optional int64 input_timestamp = 2;

    // The kind of event, 1=Open, 2=Process, 3=Close, etc.
    optional EventType event_type = 3;

    // The time at which the packets entered the caclulator node.
    optional int64 start_time = 4;

    // The time at which the packets exited the caclulator node.
    optional int64 finish_time = 5;

    // The timing data for each input packet.
    repeated StreamTrace input_trace = 6;

    // The identifying timetamp and stream_id for each output packet.
    repeated StreamTrace output_trace = 7;

    // An identifier for the current process thread.
    optional int32 thread_id = 8;
  }

  // The time represented as 0 in the trace.
  optional int64 base_time = 1;

  // The timestamp represented as 0 in the trace.
  optional int64 base_timestamp = 2;

  // The list of calculator node names indexed by node id.
  repeated string calculator_name = 3;

  // The list of stream names indexed by stream id.
  repeated string stream_name = 4;

  // Recent packet timing informtion about each calculator node and stream.
  repeated CalculatorTrace calculator_trace = 5;
}

// Latency events and summaries for recent mediapipe packets.
message GraphProfile {
  // Recent packet timing informtion about each calculator node and stream.
  repeated GraphTrace graph_trace = 1;

  // Aggregated latency information about each calculator node.
  repeated CalculatorProfile calculator_profiles = 2;

  // The canonicalized calculator graph that is traced.
  optional CalculatorGraphConfig config = 3;
}
