using System;
using System.Runtime.InteropServices;

namespace QC.QMSLPhone;

public class LogLTEAntCorrelation : LogMessage
{
	[StructLayout(LayoutKind.Sequential, Pack = 1, Size = 20)]
	public struct LogLTEAntCorrelationType
	{
		public uint verServSubframeFrameRes;

		public int rssiRx0;

		public int rssiRx1;

		public int rssiCombined;

		public uint resNumRecords;
	}

	[StructLayout(LayoutKind.Sequential, Pack = 1, Size = 12)]
	public struct LogLTEAntCorrelationRecordType
	{
		public uint txAntRes;

		public int antCorrReal;

		public int antCorrImag;
	}

	private const int lteAntCorrSize = 20;

	private const int lteAntCorrRecordSize = 12;

	private const int maxlteAntCorrRecords = 4;

	public LogLTEAntCorrelationType LTEAntCorr;

	public LogLTEAntCorrelationRecordType[] LTEAntCorrRecord = new LogLTEAntCorrelationRecordType[4];

	private GCHandle pinnedPacket;

	private IntPtr p;

	private IntPtr pLTEAntCorr;

	private IntPtr pLTEAntCorrRecords;

	public LogLTEAntCorrelation(LogMessage msgVal)
		: base(msgVal.msgID, msgVal.message, displayRawVal: false)
	{
		message = msgVal.message;
		pinnedPacket = GCHandle.Alloc(message, GCHandleType.Pinned);
		p = pinnedPacket.AddrOfPinnedObject();
		pLTEAntCorr = new IntPtr(p.ToInt64() + 16);
		pLTEAntCorrRecords = new IntPtr(pLTEAntCorr.ToInt64() + 20);
		LTEAntCorr = (LogLTEAntCorrelationType)Marshal.PtrToStructure(pLTEAntCorr, typeof(LogLTEAntCorrelationType));
		int numRecords = getNumRecords();
		for (int i = 0; i < numRecords; i++)
		{
			IntPtr ptr = new IntPtr(pLTEAntCorrRecords.ToInt64() + i * 12);
			ref LogLTEAntCorrelationRecordType reference = ref LTEAntCorrRecord[i];
			reference = (LogLTEAntCorrelationRecordType)Marshal.PtrToStructure(ptr, typeof(LogLTEAntCorrelationRecordType));
		}
	}

	public int getNumRecords()
	{
		return Convert.ToInt16(LTEAntCorr.resNumRecords >> 30);
	}

	public double getRssi(int antenna)
	{
		double value = ((antenna != 0) ? (Convert.ToDouble(LTEAntCorr.rssiRx1) / Convert.ToDouble(Math.Pow(2.0, 24.0))) : (Convert.ToDouble(LTEAntCorr.rssiRx0) / Convert.ToDouble(Math.Pow(2.0, 24.0))));
		return Math.Round(value, 2);
	}

	public double getPhase()
	{
		double num = 0.0;
		double num2 = Convert.ToDouble(LTEAntCorrRecord[0].antCorrReal);
		double num3 = Convert.ToDouble(LTEAntCorrRecord[0].antCorrImag);
		if (num2 == 0.0)
		{
			num = ((!(num3 >= 0.0)) ? 4.71238898038469 : (Math.PI / 2.0));
		}
		else
		{
			num = Math.Atan(Math.Abs(num3) / Math.Abs(num2));
			if (num2 < 0.0 && num3 >= 0.0)
			{
				num = Math.PI - num;
			}
			else if (num2 < 0.0 && num3 < 0.0)
			{
				num = Math.PI + num;
			}
			else if (num2 > 0.0 && num3 < 0.0)
			{
				num = Math.PI * 2.0 - num;
			}
		}
		return num;
	}

	public int getAntCorrReal()
	{
		return LTEAntCorrRecord[0].antCorrReal;
	}

	public int getAntCorrImag()
	{
		return LTEAntCorrRecord[0].antCorrImag;
	}
}
