/* SPDX-License-Identifier: LGPL-2.1-only OR BSD-3-Clause */
/******************************************************************************
 *
 * This file is provided under a dual license.  When you use or
 * distribute this software, you may choose to be licensed under
 * version 2.1 of the GNU Lesser General Public License
 * ("LGPLv2.1 License") or BSD License.
 *
 * LGPLv2.1 License
 *
 * Copyright(C) 2019 MediaTek Inc.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of version 2.1 of the GNU Lesser General Public
 * License as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
 * See https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html for more
 * details.
 *
 * BSD LICENSE
 *
 * Copyright(C) 2019 MediaTek Inc.
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 *  * Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *  * Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *  * Neither the name of the copyright holder nor the names of its
 *    contributors may be used to endorse or promote products derived
 *    from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 *****************************************************************************/

/*-----------------------------------------------------------------------------
 *
 * $Author: wenming.wu $
 * $Date  $
 * $RCSfile: drv_hdmi.h,v $
 * $Revision: #3 $
 *
 *---------------------------------------------------------------------------*/
#ifndef _DRV_MHL_H_
#define _DRV_MHL_H_

#include "drv_mhlcom.h"
#include "hw_pdwnc.h"

#define EMSC_BLOCK_MAX_LENGTH 256
#define MHL_RCP_KEYCODE_NUM 0x80
#define MHL_RBP_KEYCODE_NUM 0x80

#define MHL3_TIMER_PERIOD  10     // ms
#define MHL_MSC_MAX_REPLY_DELAY 500/10 //ms

#define MHL_DEV_STATE 	     0x00
#define MHL_MHL_VERSION      0x32
#define MHL_DEV_CAT          0x91//why?
#define MHL_ADOPTER_ID_H     0x01
#define MHL_ADOPTER_ID_L     0x43
#define MHL_VID_LINK_MODE    0x7F
#define MHL_AUD_LINK_MODE    0x03
#define MHL_VIDEO_TYPE       0x8F
#define MHL_LOG_DEV_MAP      0x41
#define MHL_BANDWIDTH        0x0f
#define MHL_FEATURE_FLAG  	 0x7f
#define MHL_DEVICE_ID_H      0x00
#define MHL_DEVICE_ID_L      0x01
#define MHL_SCRATCH_PAD_SIZE 0x10
#define MHL_INT_STAT_SIZE    0x33
#define MHL_RESEVED          0x00

#define MHL_EXTDEVCAP_0_ECBUS_S_075       (1<<0)
#define MHL_EXTDEVCAP_0_ECBUS_S_8BIT	  (1<<1)
#define MHL_EXTDEVCAP_0_ECBUS_S_12BIT     (1<<2)
#define MHL_EXTDEVCAP_0_ECBUS_D_150	      (1<<4)
#define MHL_EXTDEVCAP_0_ECBUS_D_8BIT      (1<<5)

#define MHL_EXTDEVCAP_1_TMDS_150          (1<<0)
#define MHL_EXTDEVCAP_1_TMDS_300	      (1<<1)
#define MHL_EXTDEVCAP_1_TMDS_600          (1<<2)

#define MHL_EXTDEVCAP_2_DEV_HOST          (1<<0)
#define MHL_EXTDEVCAP_2_DEV_DEVICE	      (1<<1)
#define MHL_EXTDEVCAP_2_DEV_CHARGER       (1<<2)
#define MHL_EXTDEVCAP_2_HID_HOST	      (1<<3)
#define MHL_EXTDEVCAP_2_HID_DEVICE        (1<<4)

#define MHL_EXTDEVCAP_3_LD_PHONE          (1<<0)

//RAP
#define MHL_RAP_CMD_POLL          0x00  // Poll
#define MHL_RAP_CMD_CONTENTON     0x10    // change to content-on state
#define MHL_RAP_CMD_CONTENTOFF    0x11     // change to content-off state
#define MHL_RAP_CMD_MODE_DOWN     0x20
#define MHL_RAP_CMD_MODE_UP       0x21

#define MHL_RAPK_NOERROR            0x00 // Poll
#define MHL_RAPK_UNRECOGNIZED_CODE  0x01    // unrecognized action code RAP action code
#define MHL_RAPK_UNSUPPORTED        0x02     // unsupport RAP Action code
#define MHL_RAPK_BUSY               0x03     // responder is busy


#define ECBUS_SPEED (MHL_EXTDEVCAP_0_ECBUS_S_075 | MHL_EXTDEVCAP_0_ECBUS_S_8BIT)
#define TMDS_SPEED  (MHL_EXTDEVCAP_1_TMDS_150 | MHL_EXTDEVCAP_1_TMDS_300 | MHL_EXTDEVCAP_1_TMDS_600)
#define ECBUS_DEV_ROLES (MHL_EXTDEVCAP_2_DEV_HOST | MHL_EXTDEVCAP_2_DEV_DEVICE | MHL_EXTDEVCAP_2_DEV_CHARGER)
#define LOG_DEV_MAPX      0
#define ACRFS_DIV_SUPPORT 0

//1st interrupt
#define RX_CBUS_EMSC_INTR_INT (1<<7)
#define RX_CBUS_TDM_INTR_INT  (1<<0)
#define RX_CBUS_CBUS_INTR_INT (1<<1)

//2st interrupt
#define RX_CBUS_INT_0_STAT_CBUS_CONNECTION           (1<<0)
#define RX_CBUS_INT_0_STAT_CBUS_MSC_CMD_DONE         (1<<1)
#define RX_CBUS_INT_0_STAT_CBUS_HPD_CHANGE   		 (1<<2)
#define RX_CBUS_INT_0_STAT_CBUS_WRITE_STATE_RECV     (1<<3)
#define RX_CBUS_INT_0_STAT_CBUS_MSC_MSG_RECV         (1<<4)
#define RX_CBUS_INT_0_STAT_CBUS_WRITE_BURST_RECV     (1<<5)
#define RX_CBUS_INT_0_STAT_CBUS_SET_INT_RECV         (1<<6)
#define RX_CBUS_INT_0_STAT_CBUS_MSC_MSG_NACK_DONE	 (1<<7)

#define RX_CBUS_INT_1_STAT_CBUS_MSC_HEARTBEAT_MAX_FAIL  (1<<0x10)
#define RX_CBUS_INT_1_STAT_CBUS_DDC_ABORT               (1<<0x12)
#define RX_CBUS_INT_1_STAT_CBUS_MSC_RECV_ERROR_RES   	(1<<0x13)
#define RX_CBUS_INT_1_STAT_CBUS_CBUS_PACKET_RECV        (1<<0x15)
#define RX_CBUS_INT_1_STAT_CBUS_MSC_RECV_ERROR_REQ      (1<<0x16)
#define RX_CBUS_INT_1_STAT_CBUS_MHL_CABLE_CONNECT       (1<<0x17)

//Virtual Channel Feature_ID code
#define FEATURE_ID_EMSA 0x00
#define FEATURE_ID_USB  0x01
#define FEATURE_ID_AUDIO  0x02
#define FEATURE_ID_IP  0x03
#define FEATURE_ID_VIDEO  0x04
#define FEATURE_ID_HID  0x05

//Virtual Channel Responder Response Codes
#define RESPONCE_ACCEPT 0x00
#define RESPONCE_INVALID_VC_NUM 0x01
#define RESPONCE_INVALID_FEATURE_ID 0x02
#define RESPONCE_INVALID_CHANNEL_SIZE 0x03

#define ECBUS_PATTERN_PRBS  0x01
#define ECBUS_PATTERN_FIX8  0x02
#define ECBUS_PATTERN_FIX10 0x03

#define AV_LINK_PATTERN_PRBS 0x01
#define AV_LINK_PATTERN_FIX8 0x02
#define AV_LINK_PATTERN_FIX10 0x03

#define AV_LINK_RANDOMIZER_DISABLED 0x00
#define AV_LINK_RANDOMIZER_ENABLED  0x01

#define IMPEDANCE_MODE_AV_LINK_TX_LOW 0x00
#define IMPEDANCE_MODE_AV_LINK_TX_HIGH 0x01
#define IMPEDANCE_MODE_AV_LINK_RX 0x02
#define IMPEDANCE_MODE_ECBUS_D_TX_LOW 0x04
#define IMPEDANCE_MODE_ECBUS_D_TX_HIGH 0x05
#define IMPEDANCE_MODE_ECBUS_D_RX 0x06
#define IMPEDANCE_MODE_ECBUS_S_TX_LOW 0x08
#define IMPEDANCE_MODE_ECBUS_S_TX_HIGH 0x09
#define IMPEDANCE_MODE_ECBUS_S_RX 0x0A

#define BIST_REQUEST_STA_DO_NOTHING 0x00
#define BIST_REQUEST_STAT_REQUEST_RETURN_STAT 0x01

//Bist
#define BIST_ROLE_NA   0x00
#define BIST_ROLE_DUT  0x01
#define BIST_ROLE_TE   0x02

//Bist_Ready
#define BIST_READY_ECBUS_READY    (1<<0)
#define BIST_READY_AVLINK_READY   (1<<1)
#define BIST_READY_TERM_READY     (1<<2)
#define BIST_READY_ECBUS_ERROR    (1<<4)
#define BIST_READY_AVLINK_ERROR   (1<<5)

//Bist_Trigger
#define BIST_TRIGGER_ECBUS_TX_BIST    (1<<0)
#define BIST_TRIGGER_ECBUS_RX_BIST    (1<<1)
#define BIST_TRIGGER_ECBUS_SELECT     (1<<3)
#define BIST_TRIGGER_AVLINK_TX_BIST   (1<<4)
#define BIST_TRIGGER_AVLINK_RX_BIST   (1<<5)
#define BIST_TRIGGER_IMPEDANCE_BIST	(1<<6)

//MSC_MSGE
#define MSC_MSGE_NOERROR       		  0x00
#define MSC_MSGE_INVALID_SUB_COMMAND  0x01

enum
{
	CONNECTED_RDY = 0x00,
	LINK_MODE =0x01,
	VERSION_STAT = 0x02,
	NUM_STAT_REGS
};

enum
{
	CURR_ECBUS_MODE =0x00,
	AVLINK_MODE_STATUS =0x01,
	AVLINK_MODE_CONTROL =0x02,
	MULTI_SINK_STATUS =0x03,
	NUM_XSTAT_REGS
};

enum
{
	MHL_MSC_MSGE                = 0x02,
    MHL_MSC_MSG_RCP             = 0x10,     // RCP sub-command
    MHL_MSC_MSG_RCPK            = 0x11,     // RCP Acknowledge sub-command
    MHL_MSC_MSG_RCPE            = 0x12,     // RCP Error sub-command
    
    MHL_MSC_MSG_RAP             = 0x20,     // RAP sub-command
    MHL_MSC_MSG_RAPK            = 0x21,     // RAP Acknowledge sub-command

	MHL_MSC_MSG_RBP             = 0x22,
	MHL_MSC_MSG_RBPK			= 0x23,
	MHL_MSC_MSG_RBPE			= 0x24,
    
    MHL_MSC_MSG_UCP             = 0x30,
    MHL_MSC_MSG_UCPK            = 0x31,
    MHL_MSC_MSG_UCPE            = 0x32,

	MHL_MSC_MSG_RHID			= 0x42,
	MHL_MSC_MSG_RHIDK			= 0x43,

	MHL_MSC_MSG_ATT             = 0x50,
	MHL_MSC_MSG_ATTK            = 0x51,

	MHL_MSC_MSG_BIST_TRIGGER      = 0x60,
	MHL_MSC_MSG_BIST_REQUEST_STAT = 0x61,
	MHL_MSC_MSG_BIST_READY        = 0x62,
	MHL_MSC_MSG_BIST_STOP         = 0x63,

	MHL_MSC_MSG_TTR               = 0xf0,
	MHL_MSC_MSG_TTRK			  = 0xf1
};

typedef enum
{
	BURST_3D_VIC = 0x0010,
	BURST_3D_DTD = 0x0011,
	HEV_VIC      = 0x0020,
	HEV_DTDA     = 0x0021,
	HEV_DTDB     = 0x0022,
	VC_ASSIGN    = 0x0038,
	VC_CONFIRM   = 0x0039,
	AUD_DELAY    = 0x0040,
	ADT_BURSTID  = 0x0041,
	BIST_SETUP   = 0x0051,
	BIST_RETURN_STAT = 0x0052,
	EMSC_SUPPORT     = 0x0061,
	HID_PAYLOAD		 = 0x0062,
	BLK_RCV_BUFFER_INFO = 0x0063,
	BITS_PER_PIXEL_FMT  = 0x0064
}MhlRxBurstId_t;

typedef struct
{
    UINT8 u1Index;
	UINT8 u1VicDtd;
    UINT8 u13dTB: 1;
    UINT8 u13dLR: 1;
    UINT8 u13dFS: 1;  
}MhlRx3dDescription_t;

typedef struct
{
	UINT8 u1High;
	UINT8 u1Low;
}MhlRxVideoDescripter_t;

typedef struct
{
	UINT8 burstIdH;
	UINT8 burstIdL;
	UINT8 u1CheckSum;
	UINT8 u1TotEnt;
	UINT8 u1Seq;
	UINT8 u1NumEnt;
	MhlRxVideoDescripter_t videoDescripter[5];
}MhlRxVideoBurstDescripter_t;

typedef struct
{
	UINT16 u2PeerBlkRcvBufferAvailable;
	UINT16 u2UnloadCount;
	UINT16 u2HeaderIndex;
	UINT16 u2LengthRemaining;
	UINT8 *pHeader;
	UINT8 u1ReceiveData[EMSC_BLOCK_MAX_LENGTH];
}MhlRxEmscBlockData_t;

typedef struct
{
	BOOL bMhlCableConnected;
	BOOL bCbusConnected;
	BOOL bHpdSent;
	BOOL bPathEnSent;
	BOOL bMhlVerStatSent;
	BOOL bDcapRdySent;
	BOOL bDcapChgSent;
	BOOL bLinkStable;
	BOOL bLinkNormal;
	BOOL bTdmSync;
	BOOL bIsEdidReady;
	BOOL bClkReady;
	BOOL bMVerified;
	BOOL bVaildM;
	BOOL bIsValidMTimeOut;
	BOOL bIsLnkStbTimeout;
	BOOL bIsTranTimeOut;
	BOOL bIsRapkTimeout;
	BOOL bCocCaliDone;
	BOOL bCocLocked;
	BOOL bCocClkCalOk;
	BOOL bRev2;
	UINT32 u2AvLinkM0Value;
	UINT32 u2AvLinkM1Value;
	UINT8 u1ClkReadTimeOutCnt;
	UINT8 u1ClkReadyLostTimeOutCnt;
	UINT8 u1ValidMCnt;
	UINT8 u1ValidMLostCnt;
}MhlRxCbus_t;

typedef struct
{
	UINT8 u1BurstIdH;
	UINT8 u1BurstIdL;
	UINT8 u1CheckSum;
	UINT8 u1EcbusDuration;
	UINT8 u1EcbusPattern;
	UINT8 u1EcbusFixedH;
	UINT8 u1EcbusFixedL;
	UINT8 u1Reserved;
	UINT8 u1AvLinkDataRate;
	UINT8 u1AvLinkPattern;
	UINT8 u1AvLinkVideoMode;
	UINT8 u1AvLinkDuration;
	UINT8 u1AvLinkFixedH;
	UINT8 u1AvLinkFixedL;
	UINT8 u1AvLinkRandomizer;
	UINT8 u1ImpedanceMode;
}MhlRxCbusBistSetupFormatData_t;

typedef struct
{
	UINT8 burstIdH;
	UINT8 burstIdL;
	UINT8 u1CheckSum;
	UINT8 u1Reserved[9];
	UINT8 u1EcbusStatH;
	UINT8 u1EcbusStatL;
	UINT8 u1AvLinkStatH;
	UINT8 u1AvLinkStatL;
}MhlRxCbusBistReturnStatFormatData_t;

typedef struct
{
	UINT8 u1EcbusDuration;
	UINT8 u1EcbusPattern;
	UINT8 u1EcbusFixedH;
	UINT8 u1EcbusFixedL;
	UINT8 u1AvLinkDataRate;
	UINT8 u1AvLinkPattern;
	UINT8 u1AvLinkVideoMode;
	UINT8 u1AvLinkDuration;
	UINT8 u1AvLinkFixedH;
	UINT8 u1AvLinkFixedL;
	UINT8 u1AvLinkRandomizer;
	UINT8 u1ImpedanceMode;
	UINT8 u1TriggerData;
}MhlRxCbusHostSetBistParameters_t;

typedef struct
{
	MhlRxCbusBistReturnStatFormatData_t bistReturnData;
	MhlRxCbusHostSetBistParameters_t  cbusHostSetBistPara;
	UINT8 u1BistMode;
	UINT8 u1BistRole;
	BOOL  bReadyToSendBurst;
	
}MhlRxCbusBistBuffer_t;

typedef struct
{
	UINT8 u1VcNum;
	UINT8 u1FeatureID;
	UINT8 u1ChannelSizeResponse;
}MhlVirtualChannelDiscriptor_t;

typedef struct
{
	UINT8 burstIdH;
	UINT8 burstIdL;
	UINT8 u1CheckSum;
	UINT8 u1TotEnt;
	UINT8 u1Seq;
	UINT8 u1NumEnt;
	MhlVirtualChannelDiscriptor_t virtualChannelDescriptors[3];
	UINT8 u1Reserved;
}MhlRxCbusVcConfirmFormatData_t;

typedef struct
{
	UINT8 u1LocalDevCaps[MHL_MAX_BUFFER_SIZE];
	UINT8 u1LocalXDevCaps[MHL_MAX_BUFFER_SIZE];
	UINT8 u1PeerDevCap[MHL_MAX_BUFFER_SIZE];
	UINT8 u1PeerXDevCap[MHL_MAX_BUFFER_SIZE];
	UINT8 u1LastWriteBurstOut[MHL_SCRATCHPAD_SIZE];
	UINT8 u1DevStatus[NUM_STAT_REGS];
	UINT8 u1XDevStatus[NUM_XSTAT_REGS];

	pWRTIEBURSTCALLBACK pLastWriteBurstCallBack;

	UINT32 u4PendingEvent;
	UINT32 u4RxCbusEvent;
	
	BOOL bReadDevCap;//if peer device capability register has been read out
	BOOL bReadXDevCap;//if peer externded device capability register has been read out 
	BOOL bReadingPeerDevCap;

	BOOL bMhlSense;
	
	BOOL bAbortWait;
	BOOL bDcapRdy;
	BOOL bPeerFeatRdy;
	BOOL bFeatSent;
	BOOL bTxDevCapRdySent;
	BOOL bTxDevCapChgSent;
	BOOL bLinkStatusSent;
	BOOL bScratchPadBusy;
	BOOL bNeedWriteBurst;

	BOOL bLinkRateRecv;
	BOOL bPathEnRecv;
	BOOL bPpModeRecv;
	BOOL bContentOff;
	BOOL bRcpSupp;
	BOOL bRapSupp;
	BOOL bSpSupp;
	BOOL bUcpSendSupp;
	BOOL bUcpRecvSupp;
	BOOL bXvYccSupp;
	BOOL bRbpSupp;

	BOOL bEnableECBUS;
	BOOL bEcbusSynced;
	BOOL bEcbusSpeedRead;
	

	BOOL bEmscSyncStat;
	BOOL bEmscActive;
	BOOL bRev2;
	BOOL bRev3;
	BOOL bRev4;
	
	UINT8 u1EmscChannelSize;
	UINT8 u1UsbChannelSize;
	
	UINT8 u1CbusTimerCnt;
	UINT8 u1DcapRdyMoniterCnt;
	UINT8 u1Mhl3VersionCnt;
	UINT16 u2Mhl3EcbusBistCnt;
	UINT16 u2Mhl3AvLinkBistCnt;
	UINT16 u2Mhl3ImpedanceBistCnt;
	BOOL bMhl3VersionTimeOut;
	MhlRxCbusMode_t eCbusMode;
	MhlRxEmscBlockData_t eMscBlockData;
	MHL_RX_CBUS_LINK_RATE_t eLinkRate;
	MHL_RX_CBUS_OUT_QUEUE_t outCommand;
	MHL_RX_CBUS_IN_QUEUE_t inCommand;
	MhlRxCbus_t rxCbusSta;
	MHL_RX_CBUS_CALLBACK_PARAMETERS_t cbusCallbackParameter;

	MHL_RX_CBUS_WRITE_BURST_BUFFER_t writeBurstOutQueue;
	MHL_RX_CBUS_WRITE_BURST_BUFFER_t writeBurstInQueue;

	MhlRxCbusBistBuffer_t bistBuffer;
	
}MhlRxCbusObj_t;

#define FLD_HDMI_2_HPD_CBUS Fld(3,12,AC_MSKB1)//[14:12]
#define ENABLE_PINMUX_TO_CBUS() ((void)vIO32WriteFldAlign(PDWNC_PINMUX4,1,FLD_HDMI_2_HPD_CBUS))
#define DISABLE_PINMUX_TO_CBUS() ((void)vIO32WriteFldAlign(PDWNC_PINMUX4,0,FLD_HDMI_2_HPD_CBUS))

#ifndef AD_ECBUS_0_MON_CK
#define AD_ECBUS_0_MON_CK (0x66)
#endif

#ifndef AD_HDMI_0_DEEP680M_CK
#define AD_HDMI_0_DEEP680M_CK (0x6b)
#endif

#ifndef AD_HDMI_0_MON_CK
#define AD_HDMI_0_MON_CK (0x7d)
#endif

extern MhlRxCbusMode_t mMHL3GetCbusMode(void);
extern void vMHL3AvLinkFpllControl(void);
extern UINT8 bIsMhlSource(void);
extern BOOL fgMHL3GetAbortWait(void);
extern BOOL fgMHL3GetMhlCableStatus(void);
extern void vMHl3SwitchToEcbus(void);
extern void vMHl3SwitchToOcbus(void);

extern void vMHL3Init(void);
#endif

