mirror of
https://github.com/NVIDIA/open-gpu-kernel-modules.git
synced 2026-02-02 06:29:47 +00:00
535.54.03
This commit is contained in:
@@ -233,6 +233,13 @@ NvBool nvValidateSetLutCommonParams(
|
||||
const NVDevEvoRec *pDevEvo,
|
||||
const struct NvKmsSetLutCommonParams *pParams);
|
||||
|
||||
NvBool nvChooseColorRangeEvo(
|
||||
enum NvKmsOutputTf tf,
|
||||
const enum NvKmsDpyAttributeColorRangeValue requestedColorRange,
|
||||
const enum NvKmsDpyAttributeCurrentColorSpaceValue colorSpace,
|
||||
const enum NvKmsDpyAttributeColorBpcValue colorBpc,
|
||||
enum NvKmsDpyAttributeColorRangeValue *pColorRange);
|
||||
|
||||
NvBool nvChooseCurrentColorSpaceAndRangeEvo(
|
||||
const NVDpyEvoRec *pDpyEvo,
|
||||
enum NvYuv420Mode yuv420Mode,
|
||||
|
||||
@@ -2111,6 +2111,38 @@ NvBool nvGetDefaultColorSpace(
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
NvBool nvChooseColorRangeEvo(
|
||||
enum NvKmsOutputTf tf,
|
||||
const enum NvKmsDpyAttributeColorRangeValue requestedColorRange,
|
||||
const enum NvKmsDpyAttributeCurrentColorSpaceValue colorSpace,
|
||||
const enum NvKmsDpyAttributeColorBpcValue colorBpc,
|
||||
enum NvKmsDpyAttributeColorRangeValue *pColorRange)
|
||||
{
|
||||
/* Hardware supports BPC_6 only for RGB */
|
||||
nvAssert((colorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_RGB) ||
|
||||
(colorBpc != NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_BPC_6));
|
||||
|
||||
if ((colorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_RGB) &&
|
||||
(colorBpc == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_BPC_6)) {
|
||||
/* At depth 18 only RGB and full range are allowed */
|
||||
if (tf == NVKMS_OUTPUT_TF_PQ) {
|
||||
/* NVKMS_OUTPUT_TF_PQ requires limited color range */
|
||||
return FALSE;
|
||||
}
|
||||
*pColorRange = NV_KMS_DPY_ATTRIBUTE_COLOR_RANGE_FULL;
|
||||
} else if ((colorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr444) ||
|
||||
(colorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr422) ||
|
||||
(colorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr420) ||
|
||||
(tf == NVKMS_OUTPUT_TF_PQ)) {
|
||||
/* Both YUV and NVKMS_OUTPUT_TF_PQ requires limited color range. */
|
||||
*pColorRange = NV_KMS_DPY_ATTRIBUTE_COLOR_RANGE_LIMITED;
|
||||
} else {
|
||||
*pColorRange = requestedColorRange;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/*!
|
||||
* Choose current colorSpace and colorRange for the given dpy based on
|
||||
* the dpy's color format capailities, the given modeset parameters (YUV420
|
||||
@@ -2206,23 +2238,9 @@ NvBool nvChooseCurrentColorSpaceAndRangeEvo(
|
||||
}
|
||||
}
|
||||
|
||||
/* Hardware supports BPC_6 only for RGB */
|
||||
nvAssert((newColorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_RGB) ||
|
||||
(newColorBpc != NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_BPC_6));
|
||||
/*
|
||||
* Both YUV and NVKMS_OUTPUT_TF_PQ requires limited color range.
|
||||
*/
|
||||
if ((newColorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr444) ||
|
||||
(newColorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr422) ||
|
||||
(newColorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_YCbCr420) ||
|
||||
(tf == NVKMS_OUTPUT_TF_PQ)) {
|
||||
newColorRange = NV_KMS_DPY_ATTRIBUTE_COLOR_RANGE_LIMITED;
|
||||
} else if ((newColorSpace == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_RGB) &&
|
||||
(newColorBpc == NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_BPC_6)) {
|
||||
/* At depth 18 only RGB and full range are allowed */
|
||||
newColorRange = NV_KMS_DPY_ATTRIBUTE_COLOR_RANGE_FULL;
|
||||
} else {
|
||||
newColorRange = requestedColorRange;
|
||||
if (!nvChooseColorRangeEvo(tf, requestedColorRange, newColorSpace,
|
||||
newColorBpc, &newColorRange)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
*pCurrentColorSpace = newColorSpace;
|
||||
|
||||
@@ -146,31 +146,23 @@ static NvBool UpdateProposedFlipStateOneApiHead(
|
||||
if (!nvIsHDRCapableHead(pDispEvo, apiHead)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* NVKMS_OUTPUT_TF_PQ requires the RGB color space */
|
||||
if (pProposedApiHead->hdr.colorSpace !=
|
||||
NV_KMS_DPY_ATTRIBUTE_CURRENT_COLOR_SPACE_RGB) {
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
if (!nvChooseCurrentColorSpaceAndRangeEvo(pDpyEvo,
|
||||
pApiHeadState->timings.yuv420Mode,
|
||||
pParams->tf.val,
|
||||
pDpyEvo->requestedColorSpace,
|
||||
pDpyEvo->requestedColorRange,
|
||||
&pProposedApiHead->hdr.colorSpace,
|
||||
&pProposedApiHead->hdr.colorBpc,
|
||||
&pProposedApiHead->hdr.colorRange)) {
|
||||
if (!nvChooseColorRangeEvo(pParams->tf.val,
|
||||
pDpyEvo->requestedColorRange,
|
||||
pProposedApiHead->hdr.colorSpace,
|
||||
pProposedApiHead->hdr.colorBpc,
|
||||
&pProposedApiHead->hdr.colorRange)) {
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Change in colorSpace and colorBpc is not handled. For DisplayPort,
|
||||
* colorSpace and colorBpc can not be changed without a modeset.
|
||||
*/
|
||||
if ((pProposedApiHead->hdr.colorSpace !=
|
||||
pApiHeadState->attributes.colorSpace) ||
|
||||
(pProposedApiHead->hdr.colorBpc !=
|
||||
pApiHeadState->attributes.colorBpc)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (pParams->viewPortIn.specified) {
|
||||
pProposedApiHead->dirty.viewPortPointIn = TRUE;
|
||||
pProposedApiHead->viewPortPointIn = pParams->viewPortIn.point;
|
||||
|
||||
@@ -691,6 +691,10 @@ static void SetHdmiAudioMute(const NVDispEvoRec *pDispEvo,
|
||||
static void EnableHdmiAudio(const NVDispEvoRec *pDispEvo,
|
||||
const NvU32 head, const NvBool enable)
|
||||
{
|
||||
/*
|
||||
* XXX Is it correct to use pktType_GeneralControl to mute/unmute
|
||||
* the audio? pktType_GeneralControl controls both the audio and video data.
|
||||
*/
|
||||
static const NvU8 InfoframeMutePacket[] = {
|
||||
pktType_GeneralControl, 0, 0, HDMI_GENCTRL_PACKET_MUTE_ENABLE, 0, 0, 0, 0,
|
||||
0, 0
|
||||
@@ -998,12 +1002,13 @@ void nvHdmiDpConstructHeadAudioState(const NvU32 displayId,
|
||||
return;
|
||||
}
|
||||
|
||||
pAudioState->isAudioOverHdmi = nvDpyIsHdmiEvo(pDpyEvo);
|
||||
|
||||
if (FillELDBuffer(displayId,
|
||||
nvConnectorUsesDPLib(pDpyEvo->pConnectorEvo),
|
||||
&pDpyEvo->parsedEdid,
|
||||
&pAudioState->eld,
|
||||
&pAudioState->maxFreqSupported)) {
|
||||
pAudioState->isAudioOverHdmi = nvDpyIsHdmiEvo(pDpyEvo);
|
||||
pAudioState->enabled = TRUE;
|
||||
}
|
||||
}
|
||||
@@ -1197,37 +1202,25 @@ void nvHdmiDpEnableDisableAudio(const NVDispEvoRec *pDispEvo,
|
||||
return;
|
||||
}
|
||||
|
||||
if (!pHeadState->audio.enabled) {
|
||||
|
||||
if (enable) {
|
||||
/* Make sure to remove corresponding audio device */
|
||||
if (!enable) {
|
||||
/*
|
||||
* This is pre modeset code path. If audio device is enabled
|
||||
* (pHeadState->audio.enabled == TRUE) then invalidate ELD buffer
|
||||
* before disabling audio.
|
||||
*/
|
||||
if (pHeadState->audio.enabled) {
|
||||
RmSetELDAudioCaps(pDispEvo,
|
||||
pConnectorEvo,
|
||||
nvDpyIdToNvU32(pConnectorEvo->displayId),
|
||||
pHeadState->activeRmId,
|
||||
deviceEntry,
|
||||
0 /* maxFreqSupported */,
|
||||
NULL /* pEld */,
|
||||
NV_ELD_POWER_ON_RESET);
|
||||
} else {
|
||||
/* Do nothing. The audio device is already in the disabled state. */
|
||||
NV_ELD_PRE_MODESET);
|
||||
|
||||
if (nvConnectorUsesDPLib(pConnectorEvo)) {
|
||||
SetDpAudioEnable(pDispEvo, head, FALSE /* enable */);
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
/* Invalidate ELD buffer before disabling audio */
|
||||
if (!enable) {
|
||||
RmSetELDAudioCaps(pDispEvo,
|
||||
pConnectorEvo,
|
||||
pHeadState->activeRmId,
|
||||
deviceEntry,
|
||||
0 /* maxFreqSupported */,
|
||||
NULL /* pEld */,
|
||||
NV_ELD_PRE_MODESET);
|
||||
}
|
||||
|
||||
if (nvConnectorUsesDPLib(pConnectorEvo)) {
|
||||
SetDpAudioEnable(pDispEvo, head, enable);
|
||||
}
|
||||
|
||||
if (pHeadState->audio.isAudioOverHdmi) {
|
||||
@@ -1236,15 +1229,34 @@ void nvHdmiDpEnableDisableAudio(const NVDispEvoRec *pDispEvo,
|
||||
SendHdmiGcp(pDispEvo, head, !enable /* avmute */);
|
||||
}
|
||||
|
||||
/* Populate ELD buffer after enabling audio */
|
||||
if (enable) {
|
||||
RmSetELDAudioCaps(pDispEvo,
|
||||
pConnectorEvo,
|
||||
pHeadState->activeRmId,
|
||||
deviceEntry,
|
||||
pHeadState->audio.maxFreqSupported,
|
||||
&pHeadState->audio.eld,
|
||||
NV_ELD_POST_MODESET);
|
||||
/*
|
||||
* This is post modeset code path. If audio device is enabled
|
||||
* (pHeadState->audio.enabled == TRUE) then populate ELD buffer after
|
||||
* enabling audio, otherwise make sure to remove corresponding audio
|
||||
* device.
|
||||
*/
|
||||
if (pHeadState->audio.enabled) {
|
||||
if (nvConnectorUsesDPLib(pConnectorEvo)) {
|
||||
SetDpAudioEnable(pDispEvo, head, TRUE /* enable */);
|
||||
}
|
||||
|
||||
RmSetELDAudioCaps(pDispEvo,
|
||||
pConnectorEvo,
|
||||
pHeadState->activeRmId,
|
||||
deviceEntry,
|
||||
pHeadState->audio.maxFreqSupported,
|
||||
&pHeadState->audio.eld,
|
||||
NV_ELD_POST_MODESET);
|
||||
} else {
|
||||
RmSetELDAudioCaps(pDispEvo,
|
||||
pConnectorEvo,
|
||||
nvDpyIdToNvU32(pConnectorEvo->displayId),
|
||||
deviceEntry,
|
||||
0 /* maxFreqSupported */,
|
||||
NULL /* pEld */,
|
||||
NV_ELD_POWER_ON_RESET);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user