X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=src%2Fgallium%2Fstate_trackers%2Fxorg%2Fxorg_output.c;h=b183cdf9dc1df8ca2085f0a3cd32d4f97b8d328c;hb=fb18ec4f2775f96982a39247efd1c70cccbc46fc;hp=26f45f8d64592b7ae1deefec210d815904f8633c;hpb=5b4c0b864a25fa193e7ba828cf5ce483ca05bd4e;p=mesa.git diff --git a/src/gallium/state_trackers/xorg/xorg_output.c b/src/gallium/state_trackers/xorg/xorg_output.c index 26f45f8d645..b183cdf9dc1 100644 --- a/src/gallium/state_trackers/xorg/xorg_output.c +++ b/src/gallium/state_trackers/xorg/xorg_output.c @@ -32,6 +32,7 @@ #include #include #include +#include #include #include #include @@ -49,105 +50,119 @@ #include #endif -#include "X11/Xatom.h" - #include "xorg_tracker.h" -static char *connector_enum_list[] = { +struct output_private +{ + drmModeConnectorPtr drm_connector; + drmModePropertyBlobPtr edid_blob; + int fd; + int c; +}; + +static char *output_enum_list[] = { "Unknown", "VGA", - "DVI-I", - "DVI-D", - "DVI-A", + "DVI", + "DVI", + "DVI", "Composite", "SVIDEO", "LVDS", - "Component", - "9-pin DIN", - "DisplayPort", - "HDMI Type A", - "HDMI Type B", + "CTV", + "DIN", + "DP", + "HDMI", + "HDMI", }; static void -dpms(xf86OutputPtr output, int mode) -{ -} - -static void -save(xf86OutputPtr output) -{ -} - -static void -restore(xf86OutputPtr output) -{ -} - -static int -mode_valid(xf86OutputPtr output, DisplayModePtr pMode) -{ - return MODE_OK; -} - -static Bool -mode_fixup(xf86OutputPtr output, DisplayModePtr mode, - DisplayModePtr adjusted_mode) -{ - return TRUE; -} - -static void -prepare(xf86OutputPtr output) -{ - dpms(output, DPMSModeOff); -} - -static void -mode_set(xf86OutputPtr output, DisplayModePtr mode, - DisplayModePtr adjusted_mode) +output_create_resources(xf86OutputPtr output) { +#ifdef RANDR_12_INTERFACE +#endif /* RANDR_12_INTERFACE */ } static void -commit(xf86OutputPtr output) +output_dpms(xf86OutputPtr output, int mode) { - dpms(output, DPMSModeOn); - - if (output->scrn->pScreen != NULL) - xf86_reload_cursors(output->scrn->pScreen); } static xf86OutputStatus -detect(xf86OutputPtr output) +output_detect(xf86OutputPtr output) { - drmModeConnectorPtr drm_connector = output->driver_private; + modesettingPtr ms = modesettingPTR(output->scrn); + struct output_private *priv = output->driver_private; + drmModeConnectorPtr drm_connector; + xf86OutputStatus status; + + drm_connector = drmModeGetConnector(ms->fd, priv->drm_connector->connector_id); + if (drm_connector) { + drmModeFreeConnector(priv->drm_connector); + priv->drm_connector = drm_connector; + } else { + drm_connector = priv->drm_connector; + } switch (drm_connector->connection) { case DRM_MODE_CONNECTED: - return XF86OutputStatusConnected; + status = XF86OutputStatusConnected; + break; case DRM_MODE_DISCONNECTED: - return XF86OutputStatusDisconnected; + status = XF86OutputStatusDisconnected; + break; default: - return XF86OutputStatusUnknown; + status = XF86OutputStatusUnknown; } + + return status; } static DisplayModePtr -get_modes(xf86OutputPtr output) +output_get_modes(xf86OutputPtr output) { - drmModeConnectorPtr drm_connector = output->driver_private; + struct output_private *priv = output->driver_private; + drmModeConnectorPtr drm_connector = priv->drm_connector; drmModeModeInfoPtr drm_mode = NULL; + drmModePropertyPtr props = NULL; + xf86MonPtr ddc_mon = NULL; DisplayModePtr modes = NULL, mode = NULL; int i; + for (i = 0; i < drm_connector->count_props; i++) { + props = drmModeGetProperty(priv->fd, drm_connector->props[i]); + if (!props) + continue; + + if (!(props->flags & DRM_MODE_PROP_BLOB)) + goto out_free; + + if (!strcmp(props->name, "EDID")) { + if (priv->edid_blob) + drmModeFreePropertyBlob(priv->edid_blob); + priv->edid_blob = drmModeGetPropertyBlob(priv->fd, + drm_connector->prop_values[i]); + } + + out_free: + drmModeFreeProperty(props); + } + + if (priv->edid_blob) { + ddc_mon = xf86InterpretEDID(output->scrn->scrnIndex, + priv->edid_blob->data); + + if (ddc_mon && priv->edid_blob->length > 128) + ddc_mon->flags |= MONITOR_EDID_COMPLETE_RAWDATA; + } + xf86OutputSetEDID(output, ddc_mon); + for (i = 0; i < drm_connector->count_modes; i++) { drm_mode = &drm_connector->modes[i]; if (drm_mode) { - mode = xcalloc(1, sizeof(DisplayModeRec)); + mode = calloc(1, sizeof(DisplayModeRec)); if (!mode) continue; - mode->type = 0; mode->Clock = drm_mode->clock; mode->HDisplay = drm_mode->hdisplay; mode->HSyncStart = drm_mode->hsync_start; @@ -162,6 +177,11 @@ get_modes(xf86OutputPtr output) mode->VScan = drm_mode->vscan; mode->VRefresh = xf86ModeVRefresh(mode); mode->Private = (void *)drm_mode; + mode->type = 0; + if (drm_mode->type & DRM_MODE_TYPE_PREFERRED) + mode->type |= M_T_PREFERRED; + if (drm_mode->type & DRM_MODE_TYPE_DRIVER) + mode->type |= M_T_DRIVER; xf86SetModeDefaultName(mode); modes = xf86ModesAdd(modes, mode); xf86PrintModeline(0, mode); @@ -171,22 +191,24 @@ get_modes(xf86OutputPtr output) return modes; } -static void -destroy(xf86OutputPtr output) +static int +output_mode_valid(xf86OutputPtr output, DisplayModePtr pMode) { - drmModeFreeConnector(output->driver_private); -} + modesettingPtr ms = modesettingPTR(output->scrn); + CustomizerPtr cust = ms->cust; -static void -create_resources(xf86OutputPtr output) -{ -#ifdef RANDR_12_INTERFACE -#endif /* RANDR_12_INTERFACE */ + if (cust && cust->winsys_check_fb_size && + !cust->winsys_check_fb_size(cust, pMode->HDisplay * + output->scrn->bitsPerPixel / 8, + pMode->VDisplay)) + return MODE_BAD; + + return MODE_OK; } #ifdef RANDR_12_INTERFACE static Bool -set_property(xf86OutputPtr output, Atom property, RRPropertyValuePtr value) +output_set_property(xf86OutputPtr output, Atom property, RRPropertyValuePtr value) { return TRUE; } @@ -194,53 +216,49 @@ set_property(xf86OutputPtr output, Atom property, RRPropertyValuePtr value) #ifdef RANDR_13_INTERFACE static Bool -get_property(xf86OutputPtr output, Atom property) +output_get_property(xf86OutputPtr output, Atom property) { return TRUE; } #endif /* RANDR_13_INTERFACE */ -#ifdef RANDR_GET_CRTC_INTERFACE -static xf86CrtcPtr -get_crtc(xf86OutputPtr output) +static void +output_destroy(xf86OutputPtr output) { - return NULL; + struct output_private *priv = output->driver_private; + if (priv->edid_blob) + drmModeFreePropertyBlob(priv->edid_blob); + drmModeFreeConnector(priv->drm_connector); + free(priv); + output->driver_private = NULL; } -#endif static const xf86OutputFuncsRec output_funcs = { - .create_resources = create_resources, - .dpms = dpms, - .save = save, - .restore = restore, - .mode_valid = mode_valid, - .mode_fixup = mode_fixup, - .prepare = prepare, - .mode_set = mode_set, - .commit = commit, - .detect = detect, - .get_modes = get_modes, + .create_resources = output_create_resources, #ifdef RANDR_12_INTERFACE - .set_property = set_property, + .set_property = output_set_property, #endif #ifdef RANDR_13_INTERFACE - .get_property = get_property, -#endif - .destroy = destroy, -#ifdef RANDR_GET_CRTC_INTERFACE - .get_crtc = get_crtc, + .get_property = output_get_property, #endif + .dpms = output_dpms, + .detect = output_detect, + + .get_modes = output_get_modes, + .mode_valid = output_mode_valid, + .destroy = output_destroy, }; void -output_init(ScrnInfoPtr pScrn) +xorg_output_init(ScrnInfoPtr pScrn) { modesettingPtr ms = modesettingPTR(pScrn); xf86OutputPtr output; drmModeResPtr res; drmModeConnectorPtr drm_connector = NULL; drmModeEncoderPtr drm_encoder = NULL; - char *name; + struct output_private *priv; + char name[32]; int c, v, p; res = drmModeGetResources(ms->fd); @@ -273,11 +291,21 @@ output_init(ScrnInfoPtr pScrn) (void)v; #endif - name = connector_enum_list[drm_connector->connector_type]; + snprintf(name, 32, "%s%d", + output_enum_list[drm_connector->connector_type], + drm_connector->connector_type_id); + + + priv = calloc(sizeof(*priv), 1); + if (!priv) { + continue; + } output = xf86OutputCreate(pScrn, &output_funcs, name); - if (!output) + if (!output) { + free(priv); continue; + } drm_encoder = drmModeGetEncoder(ms->fd, drm_connector->encoders[0]); if (drm_encoder) { @@ -287,7 +315,10 @@ output_init(ScrnInfoPtr pScrn) output->possible_crtcs = 0; output->possible_clones = 0; } - output->driver_private = drm_connector; + priv->c = c; + priv->drm_connector = drm_connector; + priv->fd = ms->fd; + output->driver_private = priv; output->subpixel_order = SubPixelHorizontalRGB; output->interlaceAllowed = FALSE; output->doubleScanAllowed = FALSE; @@ -297,4 +328,11 @@ output_init(ScrnInfoPtr pScrn) drmModeFreeResources(res); } +unsigned +xorg_output_get_id(xf86OutputPtr output) +{ + struct output_private *priv = output->driver_private; + return priv->drm_connector->connector_id; +} + /* vim: set sw=4 ts=8 sts=4: */