using System.Collections.Generic;
using MLAPI.Collections;
using MLAPI.Configuration;
using MLAPI.Transports;
using UnityEngine;
namespace MLAPI.Profiling
{
///
/// NetworkProfiler for profiling network traffic
///
public static class NetworkProfiler
{
///
/// The ticks that has been recorded
///
public static FixedQueue Ticks { get; private set; }
///
/// Whether or not the profiler is recording data
///
public static bool IsRunning { get; private set; }
private static int s_TickHistory = 1024;
private static int s_EventIdCounter = 0;
private static ProfilerTick s_CurrentTick;
///
/// Starts recording data for the Profiler
///
/// The amount of ticks to keep in memory
public static void Start(int historyLength)
{
if (IsRunning) return;
s_EventIdCounter = 0;
Ticks = new FixedQueue(historyLength);
s_TickHistory = historyLength;
s_CurrentTick = null;
IsRunning = true;
}
///
/// Stops recording data
///
public static void Stop()
{
Ticks = null; //leave to GC
s_CurrentTick = null; //leave to GC
IsRunning = false;
}
///
/// Stops recording data and fills the buffer with the recorded ticks and returns the length;
///
/// The buffer to fill with the ticks
/// The number of ticks recorded
public static int Stop(ref ProfilerTick[] tickBuffer)
{
if (!IsRunning) return 0;
int iteration = Ticks.Count > tickBuffer.Length ? tickBuffer.Length : Ticks.Count;
for (int i = 0; i < iteration; i++) tickBuffer[i] = Ticks[i];
Ticks = null; //leave to GC
s_CurrentTick = null; //leave to GC
IsRunning = false;
return iteration;
}
///
/// Stops recording data and fills the buffer with the recorded ticks and returns the length;
///
/// The buffer to fill with the ticks
/// The number of ticks recorded
public static int Stop(ref List tickBuffer)
{
if (!IsRunning) return 0;
int iteration = Ticks.Count > tickBuffer.Count ? tickBuffer.Count : Ticks.Count;
for (int i = 0; i < iteration; i++) tickBuffer[i] = Ticks[i];
Ticks = null; //leave to GC
s_CurrentTick = null; //leave to GC
IsRunning = false;
return iteration;
}
internal static void StartTick(TickType type)
{
if (!IsRunning) return;
if (Ticks.Count == s_TickHistory)
{
Ticks.Dequeue();
}
var tick = new ProfilerTick()
{
Type = type,
Frame = Time.frameCount,
EventId = s_EventIdCounter
};
s_EventIdCounter++;
Ticks.Enqueue(tick);
s_CurrentTick = tick;
}
internal static void EndTick()
{
if (!IsRunning) return;
if (s_CurrentTick == null) return;
s_CurrentTick = null;
}
internal static void StartEvent(TickType eventType, uint bytes, NetworkChannel networkChannel, byte messageType)
{
if (!IsRunning) return;
if (s_CurrentTick == null) return;
string messageName = messageType < NetworkConstants.MESSAGE_NAMES.Length ? NetworkConstants.MESSAGE_NAMES[messageType] : "INVALID_MESSAGE_TYPE";
string channelName = networkChannel.ToString();
s_CurrentTick.StartEvent(eventType, bytes, channelName, messageName);
}
internal static void StartEvent(TickType eventType, uint bytes, NetworkChannel networkChannel, string messageName)
{
if (!IsRunning) return;
if (s_CurrentTick == null) return;
string channelName = networkChannel.ToString();
s_CurrentTick.StartEvent(eventType, bytes, channelName, messageName);
}
internal static void EndEvent()
{
if (!IsRunning) return;
if (s_CurrentTick == null) return;
s_CurrentTick.EndEvent();
}
}
}