@@ -1770,6 +1770,9 @@ static int i915_dsc_fec_support_show(struct seq_file *m, void *data)
str_yes_no(drm_dp_sink_supports_dsc(intel_dp->dsc_dpcd)));
seq_printf(m, "Force_DSC_Enable: %s\n",
str_yes_no(intel_dp->force_dsc_en));
+ seq_printf(m, "DSC_YCBCR420_Sink_Support: %s\n",
+ str_yes_no(drm_dp_dsc_sink_supports_format(intel_dp->dsc_dpcd,
+ DP_DSC_YCbCr420_Native)));
if (!intel_dp_is_edp(intel_dp))
seq_printf(m, "FEC_Sink_Support: %s\n",
str_yes_no(drm_dp_sink_supports_fec(intel_dp->fec_capable)));
@@ -1893,6 +1896,85 @@ static const struct file_operations i915_dsc_bpc_fops = {
.write = i915_dsc_bpc_write
};
+static int i915_dsc_ycbcr420_show(struct seq_file *m, void *data)
+{
+ struct drm_connector *connector = m->private;
+ struct drm_device *dev = connector->dev;
+ struct drm_crtc *crtc;
+ struct intel_dp *intel_dp;
+ struct intel_crtc_state *crtc_state;
+ struct intel_encoder *encoder = intel_attached_encoder(to_intel_connector(connector));
+ int ret;
+
+ if (!encoder)
+ return -ENODEV;
+
+ ret = drm_modeset_lock_single_interruptible(&dev->mode_config.connection_mutex);
+ if (ret)
+ return ret;
+
+ crtc = connector->state->crtc;
+ if (connector->status != connector_status_connected || !crtc) {
+ ret = -ENODEV;
+ goto out;
+ }
+
+ intel_dp = intel_attached_dp(to_intel_connector(connector));
+ crtc_state = to_intel_crtc_state(crtc->state);
+ seq_printf(m, "Force_DSC_YCBCR420_Enable: %s\n",
+ str_yes_no(intel_dp->force_dsc_ycbcr420_en));
+
+out: drm_modeset_unlock(&dev->mode_config.connection_mutex);
+
+ return ret;
+}
+
+static ssize_t i915_dsc_ycbcr420_write(struct file *file,
+ const char __user *ubuf,
+ size_t len, loff_t *offp)
+{
+ struct drm_connector *connector =
+ ((struct seq_file *)file->private_data)->private;
+ struct intel_encoder *encoder = intel_attached_encoder(to_intel_connector(connector));
+ struct drm_i915_private *i915 = to_i915(encoder->base.dev);
+ struct intel_dp *intel_dp = enc_to_intel_dp(encoder);
+ bool dsc_ycbcr420_enable = false;
+ int ret;
+
+ if (len == 0)
+ return 0;
+
+ drm_dbg(&i915->drm,
+ "Copied %zu bytes from user to force YCBCR420 for DSC\n", len);
+
+ ret = kstrtobool_from_user(ubuf, len, &dsc_ycbcr420_enable);
+ if (ret < 0)
+ return ret;
+
+ drm_dbg(&i915->drm, "Got %s for DSC YCBCR420 Enable\n",
+ (dsc_ycbcr420_enable) ? "true" : "false");
+ intel_dp->force_dsc_ycbcr420_en = dsc_ycbcr420_enable;
+
+ *offp += len;
+
+ return len;
+}
+
+static int i915_dsc_ycbcr420_open(struct inode *inode,
+ struct file *file)
+{
+ return single_open(file, i915_dsc_ycbcr420_show, inode->i_private);
+}
+
+static const struct file_operations i915_dsc_ycbcr420_fops = {
+ .owner = THIS_MODULE,
+ .open = i915_dsc_ycbcr420_open,
+ .read = seq_read,
+ .llseek = seq_lseek,
+ .release = single_release,
+ .write = i915_dsc_ycbcr420_write
+};
+
/*
* Returns the Current CRTC's bpc.
* Example usage: cat /sys/kernel/debug/dri/0/crtc-0/i915_current_bpc
@@ -1964,6 +2046,9 @@ void intel_connector_debugfs_add(struct intel_connector *intel_connector)
debugfs_create_file("i915_dsc_bpc", 0644, root,
connector, &i915_dsc_bpc_fops);
+
+ debugfs_create_file("i915_dsc_ycbcr420", 0644, root,
+ connector, &i915_dsc_ycbcr420_fops);
}
if (connector->connector_type == DRM_MODE_CONNECTOR_DSI ||
@@ -1717,6 +1717,7 @@ struct intel_dp {
/* Display stream compression testing */
bool force_dsc_en;
+ bool force_dsc_ycbcr420_en;
int force_dsc_bpc;
bool hobl_failed;