static void RRMonitorGetCrtcGeometry(RRCrtcPtr crtc, RRMonitorGeometryPtr geometry) { ScreenPtr screen = crtc->pScreen; rrScrPrivPtr pScrPriv = rrGetScrPriv(screen); BoxRec panned_area; /* Check to see if crtc is panned and return the full area when applicable. */ if (pScrPriv && pScrPriv->rrGetPanning && pScrPriv->rrGetPanning(screen, crtc, &panned_area, NULL, NULL) && (panned_area.x2 > panned_area.x1) && (panned_area.y2 > panned_area.y1)) { geometry->box = panned_area; } else { int width, height; RRCrtcGetScanoutSize(crtc, &width, &height); geometry->box.x1 = crtc->x; geometry->box.y1 = crtc->y; geometry->box.x2 = geometry->box.x1 + width; geometry->box.y2 = geometry->box.y1 + height; } if (crtc->numOutputs && crtc->outputs[0]->mmWidth && crtc->outputs[0]->mmHeight) { RROutputPtr output = crtc->outputs[0]; geometry->mmWidth = output->mmWidth; geometry->mmHeight = output->mmHeight; } else { geometry->mmWidth = floor ((geometry->box.x2 - geometry->box.x1) / DEFAULT_PIXELS_PER_MM + 0.5); geometry->mmHeight = floor ((geometry->box.y2 - geometry->box.y1) / DEFAULT_PIXELS_PER_MM + 0.5); } }
int ProcRRSetOutputPrimary(ClientPtr client) { REQUEST(xRRSetOutputPrimaryReq); RROutputPtr output = NULL; WindowPtr pWin; rrScrPrivPtr pScrPriv; int rc; REQUEST_SIZE_MATCH(xRRSetOutputPrimaryReq); rc = dixLookupWindow(&pWin, stuff->window, client, DixGetAttrAccess); if (rc != Success) return rc; if (stuff->output) { VERIFY_RR_OUTPUT(stuff->output, output, DixReadAccess); if (output->pScreen != pWin->drawable.pScreen) { client->errorValue = stuff->window; return BadMatch; } } pScrPriv = rrGetScrPriv(pWin->drawable.pScreen); RRSetPrimaryOutput(pWin->drawable.pScreen, pScrPriv, output); return Success; }
static Bool xf86RandR12Init12 (ScreenPtr pScreen) { ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; rrScrPrivPtr rp = rrGetScrPriv(pScreen); rp->rrGetInfo = xf86RandR12GetInfo12; rp->rrScreenSetSize = xf86RandR12ScreenSetSize; rp->rrCrtcSet = xf86RandR12CrtcSet; rp->rrCrtcSetGamma = xf86RandR12CrtcSetGamma; rp->rrOutputSetProperty = xf86RandR12OutputSetProperty; rp->rrOutputValidateMode = xf86RandR12OutputValidateMode; rp->rrModeDestroy = xf86RandR12ModeDestroy; rp->rrSetConfig = NULL; pScrn->PointerMoved = xf86RandR12PointerMoved; if (!xf86RandR12CreateObjects12 (pScreen)) return FALSE; /* * Configure output modes */ if (!xf86RandR12SetInfo12 (pScreen)) return FALSE; return TRUE; }
int ProcRRGetOutputPrimary(ClientPtr client) { REQUEST(xRRGetOutputPrimaryReq); WindowPtr pWin; rrScrPrivPtr pScrPriv; xRRGetOutputPrimaryReply rep; RROutputPtr primary = NULL; int rc; REQUEST_SIZE_MATCH(xRRGetOutputPrimaryReq); rc = dixLookupWindow(&pWin, stuff->window, client, DixGetAttrAccess); if (rc != Success) return rc; pScrPriv = rrGetScrPriv(pWin->drawable.pScreen); if (pScrPriv) primary = pScrPriv->primaryOutput; memset(&rep, 0, sizeof(rep)); rep.type = X_Reply; rep.sequenceNumber = client->sequence; rep.output = primary ? primary->id : None; if (client->swapped) { swaps(&rep.sequenceNumber); swapl(&rep.output); } WriteToClient(client, sizeof(xRRGetOutputPrimaryReply), &rep); return Success; }
RROutputPtr RROutputCreate(ScreenPtr pScreen, const char *name, int nameLength, void *devPrivate) { RROutputPtr output; RROutputPtr *outputs; rrScrPrivPtr pScrPriv; if (!RRInit()) return NULL; pScrPriv = rrGetScrPriv(pScreen); if (pScrPriv->numOutputs) outputs = realloc(pScrPriv->outputs, (pScrPriv->numOutputs + 1) * sizeof(RROutputPtr)); else outputs = malloc(sizeof(RROutputPtr)); if (!outputs) return FALSE; pScrPriv->outputs = outputs; output = malloc(sizeof(RROutputRec) + nameLength + 1); if (!output) return NULL; output->id = FakeClientID(0); output->pScreen = pScreen; output->name = (char *) (output + 1); output->nameLength = nameLength; memcpy(output->name, name, nameLength); output->name[nameLength] = '\0'; output->connection = RR_UnknownConnection; output->subpixelOrder = SubPixelUnknown; output->mmWidth = 0; output->mmHeight = 0; output->crtc = NULL; output->numCrtcs = 0; output->crtcs = NULL; output->numClones = 0; output->clones = NULL; output->numModes = 0; output->numPreferred = 0; output->modes = NULL; output->numUserModes = 0; output->userModes = NULL; output->properties = NULL; output->pendingProperties = FALSE; output->changed = FALSE; output->devPrivate = devPrivate; if (!AddResource(output->id, RROutputType, (void *) output)) return NULL; pScrPriv->outputs[pScrPriv->numOutputs++] = output; RRResourcesChanged(pScreen); return output; }
Bool xf86RandR12Init (ScreenPtr pScreen) { rrScrPrivPtr rp; XF86RandRInfoPtr randrp; #ifdef PANORAMIX /* XXX disable RandR when using Xinerama */ if (!noPanoramiXExtension) return TRUE; #endif if (xf86RandR12Generation != serverGeneration) xf86RandR12Generation = serverGeneration; #if XORG_VERSION_CURRENT < XORG_VERSION_NUMERIC(7,0,0,0,0) xf86RandR12Key = &xf86RandR12KeyIndex; #else xf86RandR12Index = AllocateScreenPrivateIndex(); #endif randrp = xalloc (sizeof (XF86RandRInfoRec)); if (!randrp) return FALSE; if (!RRScreenInit(pScreen)) { xfree (randrp); return FALSE; } rp = rrGetScrPriv(pScreen); rp->rrGetInfo = xf86RandR12GetInfo; rp->rrSetConfig = xf86RandR12SetConfig; randrp->virtualX = -1; randrp->virtualY = -1; randrp->mmWidth = pScreen->mmWidth; randrp->mmHeight = pScreen->mmHeight; randrp->rotation = RR_Rotate_0; /* initial rotated mode */ randrp->supported_rotations = RR_Rotate_0; randrp->maxX = randrp->maxY = 0; #if XORG_VERSION_CURRENT < XORG_VERSION_NUMERIC(7,0,0,0,0) dixSetPrivate(&pScreen->devPrivates, xf86RandR12Key, randrp); #else pScreen->devPrivates[xf86RandR12Index].ptr = randrp; #endif #if RANDR_12_INTERFACE if (!xf86RandR12Init12 (pScreen)) return FALSE; #endif return TRUE; }
int rdpRRSetRdpOutputs(rdpPtr dev) { rrScrPrivPtr pRRScrPriv; int index; int width; int height; char text[256]; RROutputPtr output; pRRScrPriv = rrGetScrPriv(dev->pScreen); LLOGLN(0, ("rdpRRSetRdpOutputs: numCrtcs %d", pRRScrPriv->numCrtcs)); while (pRRScrPriv->numCrtcs > 0) { RRCrtcDestroy(pRRScrPriv->crtcs[0]); } LLOGLN(0, ("rdpRRSetRdpOutputs: numOutputs %d", pRRScrPriv->numOutputs)); while (pRRScrPriv->numOutputs > 0) { RROutputDestroy(pRRScrPriv->outputs[0]); } if (dev->monitorCount == 0) { rdpRRAddOutput(dev, "rdp0", 0, 0, dev->width, dev->height); } else { for (index = 0; index < dev->monitorCount; index++) { snprintf(text, 255, "rdp%d", index); width = dev->minfo[index].right - dev->minfo[index].left + 1; height = dev->minfo[index].bottom - dev->minfo[index].top + 1; output = rdpRRAddOutput(dev, text, dev->minfo[index].left, dev->minfo[index].top, width, height); if ((output != 0) && (dev->minfo[index].is_primary)) { RRSetPrimaryOutput(pRRScrPriv, output); } } } for (index = 0; index < pRRScrPriv->numOutputs; index++) { RROutputSetCrtcs(pRRScrPriv->outputs[index], pRRScrPriv->crtcs, pRRScrPriv->numCrtcs); } return 0; }
/* * Create a CRTC */ RRCrtcPtr RRCrtcCreate (ScreenPtr pScreen, void *devPrivate) { RRCrtcPtr crtc; RRCrtcPtr *crtcs; rrScrPrivPtr pScrPriv; if (!RRInit()) return NULL; pScrPriv = rrGetScrPriv(pScreen); /* make space for the crtc pointer */ if (pScrPriv->numCrtcs) crtcs = realloc(pScrPriv->crtcs, (pScrPriv->numCrtcs + 1) * sizeof (RRCrtcPtr)); else crtcs = malloc(sizeof (RRCrtcPtr)); if (!crtcs) return FALSE; pScrPriv->crtcs = crtcs; crtc = calloc(1, sizeof (RRCrtcRec)); if (!crtc) return NULL; crtc->id = FakeClientID (0); crtc->pScreen = pScreen; crtc->mode = NULL; crtc->x = 0; crtc->y = 0; crtc->rotation = RR_Rotate_0; crtc->rotations = RR_Rotate_0; crtc->outputs = NULL; crtc->numOutputs = 0; crtc->gammaSize = 0; crtc->gammaRed = crtc->gammaBlue = crtc->gammaGreen = NULL; crtc->changed = FALSE; crtc->devPrivate = devPrivate; RRTransformInit (&crtc->client_pending_transform); RRTransformInit (&crtc->client_current_transform); pixman_transform_init_identity (&crtc->transform); pixman_f_transform_init_identity (&crtc->f_transform); pixman_f_transform_init_identity (&crtc->f_inverse); if (!AddResource (crtc->id, RRCrtcType, (pointer) crtc)) return NULL; /* attach the screen and crtc together */ crtc->pScreen = pScreen; pScrPriv->crtcs[pScrPriv->numCrtcs++] = crtc; return crtc; }
static Bool RRMonitorCrtcPrimary(RRCrtcPtr crtc) { ScreenPtr screen = crtc->pScreen; rrScrPrivPtr pScrPriv = rrGetScrPriv(screen); int o; for (o = 0; o < crtc->numOutputs; o++) if (crtc->outputs[o] == pScrPriv->primaryOutput) return TRUE; return FALSE; }
Bool fakeRandRInit (ScreenPtr pScreen) { rrScrPrivPtr pScrPriv; if (!RRScreenInit (pScreen)) return FALSE; pScrPriv = rrGetScrPriv(pScreen); pScrPriv->rrGetInfo = fakeRandRGetInfo; pScrPriv->rrSetConfig = fakeRandRSetConfig; return TRUE; }
int ProcRRCreateMode (ClientPtr client) { REQUEST(xRRCreateModeReq); xRRCreateModeReply rep; WindowPtr pWin; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; xRRModeInfo *modeInfo; long units_after; char *name; int error, rc; RRModePtr mode; REQUEST_AT_LEAST_SIZE (xRRCreateModeReq); rc = dixLookupWindow(&pWin, stuff->window, client, DixGetAttrAccess); if (rc != Success) return rc; pScreen = pWin->drawable.pScreen; pScrPriv = rrGetScrPriv(pScreen); modeInfo = &stuff->modeInfo; name = (char *) (stuff + 1); units_after = (stuff->length - bytes_to_int32(sizeof (xRRCreateModeReq))); /* check to make sure requested name fits within the data provided */ if (bytes_to_int32(modeInfo->nameLength) > units_after) return BadLength; mode = RRModeCreateUser (pScreen, modeInfo, name, &error); if (!mode) return error; rep.type = X_Reply; rep.pad0 = 0; rep.sequenceNumber = client->sequence; rep.length = 0; rep.mode = mode->mode.id; if (client->swapped) { int n; swaps(&rep.sequenceNumber, n); swapl(&rep.length, n); swapl(&rep.mode, n); } WriteToClient(client, sizeof(xRRCreateModeReply), (char *)&rep); /* Drop out reference to this mode */ RRModeDestroy (mode); return client->noClientException; }
static Bool sdlRandRInit (ScreenPtr pScreen) { rrScrPrivPtr pScrPriv; printf("%s", __func__); if (!RRScreenInit (pScreen)) return FALSE; pScrPriv = rrGetScrPriv(pScreen); pScrPriv->rrGetInfo = sdlRandRGetInfo; pScrPriv->rrSetConfig = sdlRandRSetConfig; return TRUE; }
static void RRMonitorGetGeometry(RRMonitorPtr monitor, RRMonitorGeometryPtr geometry) { if (RRMonitorAutomaticGeometry(monitor) && monitor->numOutputs > 0) { ScreenPtr screen = monitor->pScreen; rrScrPrivPtr pScrPriv = rrGetScrPriv(screen); RRMonitorGeometryRec first = { .box = { 0, 0, 0, 0 }, .mmWidth = 0, .mmHeight = 0 }; RRMonitorGeometryRec this; int c, o, co; int active_crtcs = 0; *geometry = first; for (o = 0; o < monitor->numOutputs; o++) { RRCrtcPtr crtc = NULL; Bool in_use = FALSE; for (c = 0; !in_use && c < pScrPriv->numCrtcs; c++) { crtc = pScrPriv->crtcs[c]; if (!crtc->mode) continue; for (co = 0; !in_use && co < crtc->numOutputs; co++) if (monitor->outputs[o] == crtc->outputs[co]->id) in_use = TRUE; } if (!in_use) continue; RRMonitorGetCrtcGeometry(crtc, &this); if (active_crtcs == 0) { first = this; *geometry = this; } else { geometry->box.x1 = min(this.box.x1, geometry->box.x1); geometry->box.x2 = max(this.box.x2, geometry->box.x2); geometry->box.y1 = min(this.box.y1, geometry->box.y1); geometry->box.y2 = max(this.box.y2, geometry->box.y2); } active_crtcs++; } /* Adjust physical sizes to account for total area */ if (active_crtcs > 1 && first.box.x2 != first.box.x1 && first.box.y2 != first.box.y1) { geometry->mmWidth = (this.box.x2 - this.box.x1) / (first.box.x2 - first.box.x1) * first.mmWidth; geometry->mmHeight = (this.box.y2 - this.box.y1) / (first.box.y2 - first.box.y1) * first.mmHeight; } } else {
Bool xf86RandRInit (ScreenPtr pScreen) { rrScrPrivPtr rp; XF86RandRInfoPtr randrp; ScrnInfoPtr scrp = XF86SCRNINFO(pScreen); #ifdef PANORAMIX /* XXX disable RandR when using Xinerama */ if (!noPanoramiXExtension) return TRUE; #endif if (xf86RandRGeneration != serverGeneration) { xf86RandRIndex = AllocateScreenPrivateIndex(); xf86RandRGeneration = serverGeneration; } randrp = xalloc (sizeof (XF86RandRInfoRec)); if (!randrp) return FALSE; if (!RRScreenInit (pScreen)) { xfree (randrp); return FALSE; } rp = rrGetScrPriv(pScreen); rp->rrGetInfo = xf86RandRGetInfo; rp->rrSetConfig = xf86RandRSetConfig; randrp->virtualX = scrp->virtualX; randrp->virtualY = scrp->virtualY; randrp->mmWidth = pScreen->mmWidth; randrp->mmHeight = pScreen->mmHeight; randrp->CreateScreenResources = pScreen->CreateScreenResources; pScreen->CreateScreenResources = xf86RandRCreateScreenResources; randrp->CloseScreen = pScreen->CloseScreen; pScreen->CloseScreen = xf86RandRCloseScreen; randrp->rotation = RR_Rotate_0; pScreen->devPrivates[xf86RandRIndex].ptr = randrp; return TRUE; }
Bool xf86RandRInit (ScreenPtr pScreen) { rrScrPrivPtr rp; XF86RandRInfoPtr randrp; ScrnInfoPtr scrp = XF86SCRNINFO(pScreen); #ifdef PANORAMIX /* XXX disable RandR when using Xinerama */ if (!noPanoramiXExtension) return TRUE; #endif xf86RandRKey = &xf86RandRKeyRec; if (!dixRegisterPrivateKey(&xf86RandRKeyRec, PRIVATE_SCREEN, 0)) return FALSE; randrp = malloc(sizeof (XF86RandRInfoRec)); if (!randrp) return FALSE; if (!RRScreenInit (pScreen)) { free(randrp); return FALSE; } rp = rrGetScrPriv(pScreen); rp->rrGetInfo = xf86RandRGetInfo; rp->rrSetConfig = xf86RandRSetConfig; randrp->virtualX = scrp->virtualX; randrp->virtualY = scrp->virtualY; randrp->mmWidth = pScreen->mmWidth; randrp->mmHeight = pScreen->mmHeight; randrp->CreateScreenResources = pScreen->CreateScreenResources; pScreen->CreateScreenResources = xf86RandRCreateScreenResources; randrp->CloseScreen = pScreen->CloseScreen; pScreen->CloseScreen = xf86RandRCloseScreen; randrp->rotation = RR_Rotate_0; dixSetPrivate(&pScreen->devPrivates, xf86RandRKey, randrp); return TRUE; }
Bool winRandRInit (ScreenPtr pScreen) { rrScrPrivPtr pRRScrPriv; ErrorF ("winRandRInit ()\n"); if (!RRScreenInit (pScreen)) { ErrorF ("winRandRInit () - RRScreenInit () failed\n"); return FALSE; } /* Set some RandR function pointers */ pRRScrPriv = rrGetScrPriv (pScreen); pRRScrPriv->rrGetInfo = winRandRGetInfo; pRRScrPriv->rrSetConfig = winRandRSetConfig; return TRUE; }
Bool winRandRInit (ScreenPtr pScreen) { rrScrPrivPtr pRRScrPriv; winDebug ("winRandRInit ()\n"); if (!RRScreenInit (pScreen)) { ErrorF ("winRandRInit () - RRScreenInit () failed\n"); return FALSE; } /* Set some RandR function pointers */ pRRScrPriv = rrGetScrPriv (pScreen); pRRScrPriv->rrGetInfo = winRandRGetInfo; pRRScrPriv->rrSetConfig = NULL; pRRScrPriv->rrScreenSetSize = winRandRScreenSetSize; pRRScrPriv->rrCrtcSet = NULL; pRRScrPriv->rrCrtcSetGamma = NULL; return TRUE; }
int ProcRRXineramaGetState(ClientPtr client) { REQUEST(xPanoramiXGetStateReq); WindowPtr pWin; xPanoramiXGetStateReply rep; register int rc; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; Bool active = FALSE; REQUEST_SIZE_MATCH(xPanoramiXGetStateReq); rc = dixLookupWindow(&pWin, stuff->window, client, DixGetAttrAccess); if (rc != Success) return rc; pScreen = pWin->drawable.pScreen; pScrPriv = rrGetScrPriv(pScreen); if (pScrPriv) { /* XXX do we need more than this? */ active = TRUE; } rep.type = X_Reply; rep.state = active; rep.sequenceNumber = client->sequence; rep.length = 0; rep.window = stuff->window; if (client->swapped) { swaps(&rep.sequenceNumber); swapl(&rep.length); swapl(&rep.window); } WriteToClient(client, sizeof(xPanoramiXGetStateReply), &rep); return Success; }
static Bool xf86RandR12Init12 (ScreenPtr pScreen) { ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; rrScrPrivPtr rp = rrGetScrPriv(pScreen); XF86RandRInfoPtr randrp = XF86RANDRINFO(pScreen); rp->rrGetInfo = xf86RandR12GetInfo12; rp->rrScreenSetSize = xf86RandR12ScreenSetSize; rp->rrCrtcSet = xf86RandR12CrtcSet; rp->rrCrtcSetGamma = xf86RandR12CrtcSetGamma; rp->rrCrtcGetGamma = xf86RandR12CrtcGetGamma; rp->rrOutputSetProperty = xf86RandR12OutputSetProperty; rp->rrOutputValidateMode = xf86RandR12OutputValidateMode; #if RANDR_13_INTERFACE rp->rrOutputGetProperty = xf86RandR13OutputGetProperty; rp->rrGetPanning = xf86RandR13GetPanning; rp->rrSetPanning = xf86RandR13SetPanning; #endif rp->rrModeDestroy = xf86RandR12ModeDestroy; rp->rrSetConfig = NULL; pScrn->PointerMoved = xf86RandR12PointerMoved; pScrn->ChangeGamma = xf86RandR12ChangeGamma; randrp->orig_EnterVT = pScrn->EnterVT; pScrn->EnterVT = xf86RandR12EnterVT; if (!xf86RandR12CreateObjects12 (pScreen)) return FALSE; /* * Configure output modes */ if (!xf86RandR12SetInfo12 (pScreen)) return FALSE; return TRUE; }
int ProcRRGetPanning (ClientPtr client) { REQUEST(xRRGetPanningReq); xRRGetPanningReply rep; RRCrtcPtr crtc; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; BoxRec total; BoxRec tracking; INT16 border[4]; int n; REQUEST_SIZE_MATCH(xRRGetPanningReq); VERIFY_RR_CRTC(stuff->crtc, crtc, DixReadAccess); /* All crtcs must be associated with screens before client * requests are processed */ pScreen = crtc->pScreen; pScrPriv = rrGetScrPriv(pScreen); if (!pScrPriv) return RRErrorBase + BadRRCrtc; memset(&rep, 0, sizeof(rep)); rep.type = X_Reply; rep.status = RRSetConfigSuccess; rep.sequenceNumber = client->sequence; rep.length = 1; rep.timestamp = pScrPriv->lastSetTime.milliseconds; if (pScrPriv->rrGetPanning && pScrPriv->rrGetPanning (pScreen, crtc, &total, &tracking, border)) { rep.left = total.x1; rep.top = total.y1; rep.width = total.x2 - total.x1; rep.height = total.y2 - total.y1; rep.track_left = tracking.x1; rep.track_top = tracking.y1; rep.track_width = tracking.x2 - tracking.x1; rep.track_height = tracking.y2 - tracking.y1; rep.border_left = border[0]; rep.border_top = border[1]; rep.border_right = border[2]; rep.border_bottom = border[3]; } if (client->swapped) { swaps(&rep.sequenceNumber, n); swapl(&rep.length, n); swaps(&rep.timestamp, n); swaps(&rep.left, n); swaps(&rep.top, n); swaps(&rep.width, n); swaps(&rep.height, n); swaps(&rep.track_left, n); swaps(&rep.track_top, n); swaps(&rep.track_width, n); swaps(&rep.track_height, n); swaps(&rep.border_left, n); swaps(&rep.border_top, n); swaps(&rep.border_right, n); swaps(&rep.border_bottom, n); } WriteToClient(client, sizeof(xRRGetPanningReply), (char *)&rep); return Success; }
int ProcRRSetCrtcConfig (ClientPtr client) { REQUEST(xRRSetCrtcConfigReq); xRRSetCrtcConfigReply rep; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; RRCrtcPtr crtc; RRModePtr mode; int numOutputs; RROutputPtr *outputs = NULL; RROutput *outputIds; TimeStamp configTime; TimeStamp time; Rotation rotation; int rc, i, j; REQUEST_AT_LEAST_SIZE(xRRSetCrtcConfigReq); numOutputs = (stuff->length - bytes_to_int32(SIZEOF (xRRSetCrtcConfigReq))); VERIFY_RR_CRTC(stuff->crtc, crtc, DixSetAttrAccess); if (stuff->mode == None) { mode = NULL; if (numOutputs > 0) return BadMatch; } else { VERIFY_RR_MODE(stuff->mode, mode, DixSetAttrAccess); if (numOutputs == 0) return BadMatch; } if (numOutputs) { outputs = malloc(numOutputs * sizeof (RROutputPtr)); if (!outputs) return BadAlloc; } else outputs = NULL; outputIds = (RROutput *) (stuff + 1); for (i = 0; i < numOutputs; i++) { rc = dixLookupResourceByType((pointer *)(outputs + i), outputIds[i], RROutputType, client, DixSetAttrAccess); if (rc != Success) { free(outputs); return rc; } /* validate crtc for this output */ for (j = 0; j < outputs[i]->numCrtcs; j++) if (outputs[i]->crtcs[j] == crtc) break; if (j == outputs[i]->numCrtcs) { free(outputs); return BadMatch; } /* validate mode for this output */ for (j = 0; j < outputs[i]->numModes + outputs[i]->numUserModes; j++) { RRModePtr m = (j < outputs[i]->numModes ? outputs[i]->modes[j] : outputs[i]->userModes[j - outputs[i]->numModes]); if (m == mode) break; } if (j == outputs[i]->numModes + outputs[i]->numUserModes) { free(outputs); return BadMatch; } } /* validate clones */ for (i = 0; i < numOutputs; i++) { for (j = 0; j < numOutputs; j++) { int k; if (i == j) continue; for (k = 0; k < outputs[i]->numClones; k++) { if (outputs[i]->clones[k] == outputs[j]) break; } if (k == outputs[i]->numClones) { free(outputs); return BadMatch; } } } pScreen = crtc->pScreen; pScrPriv = rrGetScrPriv(pScreen); time = ClientTimeToServerTime(stuff->timestamp); configTime = ClientTimeToServerTime(stuff->configTimestamp); if (!pScrPriv) { time = currentTime; rep.status = RRSetConfigFailed; goto sendReply; } /* * Validate requested rotation */ rotation = (Rotation) stuff->rotation; /* test the rotation bits only! */ switch (rotation & 0xf) { case RR_Rotate_0: case RR_Rotate_90: case RR_Rotate_180: case RR_Rotate_270: break; default: /* * Invalid rotation */ client->errorValue = stuff->rotation; free(outputs); return BadValue; } if (mode) { if ((~crtc->rotations) & rotation) { /* * requested rotation or reflection not supported by screen */ client->errorValue = stuff->rotation; free(outputs); return BadMatch; } #ifdef RANDR_12_INTERFACE /* * Check screen size bounds if the DDX provides a 1.2 interface * for setting screen size. Else, assume the CrtcSet sets * the size along with the mode. If the driver supports transforms, * then it must allow crtcs to display a subset of the screen, so * only do this check for drivers without transform support. */ if (pScrPriv->rrScreenSetSize && !crtc->transforms) { int source_width; int source_height; PictTransform transform; struct pixman_f_transform f_transform, f_inverse; RRTransformCompute (stuff->x, stuff->y, mode->mode.width, mode->mode.height, rotation, &crtc->client_pending_transform, &transform, &f_transform, &f_inverse); RRModeGetScanoutSize (mode, &transform, &source_width, &source_height); if (stuff->x + source_width > pScreen->width) { client->errorValue = stuff->x; free(outputs); return BadValue; } if (stuff->y + source_height > pScreen->height) { client->errorValue = stuff->y; free(outputs); return BadValue; } } #endif } if (!RRCrtcSet (crtc, mode, stuff->x, stuff->y, rotation, numOutputs, outputs)) { rep.status = RRSetConfigFailed; goto sendReply; } rep.status = RRSetConfigSuccess; pScrPriv->lastSetTime = time; sendReply: free(outputs); rep.type = X_Reply; /* rep.status has already been filled in */ rep.length = 0; rep.sequenceNumber = client->sequence; rep.newTimestamp = pScrPriv->lastSetTime.milliseconds; if (client->swapped) { int n; swaps(&rep.sequenceNumber, n); swapl(&rep.length, n); swapl(&rep.newTimestamp, n); } WriteToClient(client, sizeof(xRRSetCrtcConfigReply), (char *)&rep); return Success; }
int ProcRRGetCrtcInfo (ClientPtr client) { REQUEST(xRRGetCrtcInfoReq); xRRGetCrtcInfoReply rep; RRCrtcPtr crtc; CARD8 *extra; unsigned long extraLen; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; RRModePtr mode; RROutput *outputs; RROutput *possible; int i, j, k, n; int width, height; BoxRec panned_area; REQUEST_SIZE_MATCH(xRRGetCrtcInfoReq); VERIFY_RR_CRTC(stuff->crtc, crtc, DixReadAccess); /* All crtcs must be associated with screens before client * requests are processed */ pScreen = crtc->pScreen; pScrPriv = rrGetScrPriv(pScreen); mode = crtc->mode; rep.type = X_Reply; rep.status = RRSetConfigSuccess; rep.sequenceNumber = client->sequence; rep.length = 0; rep.timestamp = pScrPriv->lastSetTime.milliseconds; if (pScrPriv->rrGetPanning && pScrPriv->rrGetPanning (pScreen, crtc, &panned_area, NULL, NULL) && (panned_area.x2 > panned_area.x1) && (panned_area.y2 > panned_area.y1)) { rep.x = panned_area.x1; rep.y = panned_area.y1; rep.width = panned_area.x2 - panned_area.x1; rep.height = panned_area.y2 - panned_area.y1; } else { RRCrtcGetScanoutSize (crtc, &width, &height); rep.x = crtc->x; rep.y = crtc->y; rep.width = width; rep.height = height; } rep.mode = mode ? mode->mode.id : 0; rep.rotation = crtc->rotation; rep.rotations = crtc->rotations; rep.nOutput = crtc->numOutputs; k = 0; for (i = 0; i < pScrPriv->numOutputs; i++) for (j = 0; j < pScrPriv->outputs[i]->numCrtcs; j++) if (pScrPriv->outputs[i]->crtcs[j] == crtc) k++; rep.nPossibleOutput = k; rep.length = rep.nOutput + rep.nPossibleOutput; extraLen = rep.length << 2; if (extraLen) { extra = malloc(extraLen); if (!extra) return BadAlloc; } else extra = NULL; outputs = (RROutput *) extra; possible = (RROutput *) (outputs + rep.nOutput); for (i = 0; i < crtc->numOutputs; i++) { outputs[i] = crtc->outputs[i]->id; if (client->swapped) swapl (&outputs[i], n); } k = 0; for (i = 0; i < pScrPriv->numOutputs; i++) for (j = 0; j < pScrPriv->outputs[i]->numCrtcs; j++) if (pScrPriv->outputs[i]->crtcs[j] == crtc) { possible[k] = pScrPriv->outputs[i]->id; if (client->swapped) swapl (&possible[k], n); k++; } if (client->swapped) { swaps(&rep.sequenceNumber, n); swapl(&rep.length, n); swapl(&rep.timestamp, n); swaps(&rep.x, n); swaps(&rep.y, n); swaps(&rep.width, n); swaps(&rep.height, n); swapl(&rep.mode, n); swaps(&rep.rotation, n); swaps(&rep.rotations, n); swaps(&rep.nOutput, n); swaps(&rep.nPossibleOutput, n); } WriteToClient(client, sizeof(xRRGetCrtcInfoReply), (char *)&rep); if (extraLen) { WriteToClient (client, extraLen, (char *) extra); free(extra); } return Success; }
static Bool vncRandRScreenSetSize(ScreenPtr pScreen, CARD16 width, CARD16 height, CARD32 mmWidth, CARD32 mmHeight) { vfbScreenInfoPtr pvfb = &vfbScreens[pScreen->myNum]; vfbFramebufferInfo fb; rrScrPrivPtr rp = rrGetScrPriv(pScreen); PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen); void *pbits; Bool ret; int oldwidth, oldheight, oldmmWidth, oldmmHeight; /* Prevent updates while we fiddle */ xf86SetRootClip(pScreen, FALSE); /* Store current state in case we fail */ oldwidth = pScreen->width; oldheight = pScreen->height; oldmmWidth = pScreen->mmWidth; oldmmHeight = pScreen->mmHeight; /* Then set the new dimensions */ pScreen->width = width; pScreen->height = height; pScreen->mmWidth = mmWidth; pScreen->mmHeight = mmHeight; /* Allocate a new framebuffer */ memset(&fb, 0, sizeof(vfbFramebufferInfo)); fb.width = pScreen->width; fb.height = pScreen->height; fb.depth = pvfb->fb.depth; pbits = vfbAllocateFramebufferMemory(&fb); if (!pbits) { /* Allocation failed. Restore old state */ pScreen->width = oldwidth; pScreen->height = oldheight; pScreen->mmWidth = oldmmWidth; pScreen->mmHeight = oldmmHeight; xf86SetRootClip(pScreen, TRUE); return FALSE; } /* Update root pixmap with the new dimensions and buffer */ ret = pScreen->ModifyPixmapHeader(rootPixmap, fb.width, fb.height, -1, -1, fb.paddedBytesWidth, pbits); if (!ret) { /* Update failed. Free the new framebuffer and restore old state */ vfbFreeFramebufferMemory(&fb); pScreen->width = oldwidth; pScreen->height = oldheight; pScreen->mmWidth = oldmmWidth; pScreen->mmHeight = oldmmHeight; xf86SetRootClip(pScreen, TRUE); return FALSE; } /* Free the old framebuffer and keep the info about the new one */ vfbFreeFramebufferMemory(&pvfb->fb); memcpy(&pvfb->fb, &fb, sizeof(vfbFramebufferInfo)); /* Let VNC get the new framebuffer (actual update is in vncHooks.cc) */ vncFbptr[pScreen->myNum] = pbits; vncFbstride[pScreen->myNum] = fb.paddedWidth; /* Restore ability to update screen, now with new dimensions */ xf86SetRootClip(pScreen, TRUE); /* * Let RandR know we changed something (it doesn't assume that * TRUE means something changed for some reason...). */ RRScreenSizeNotify(pScreen); /* Crop all CRTCs to the new screen */ for (int i = 0;i < rp->numCrtcs;i++) { RRCrtcPtr crtc; RRModePtr mode; crtc = rp->crtcs[i]; /* Disabled? */ if (crtc->mode == NULL) continue; /* Fully inside? */ if ((crtc->x + crtc->mode->mode.width <= width) && (crtc->y + crtc->mode->mode.height <= height)) continue; /* Fully outside? */ if ((crtc->x >= width) || (crtc->y >= height)) { /* Disable it */ ret = vncRandRCrtcSet(pScreen, crtc, NULL, crtc->x, crtc->y, crtc->rotation, 0, NULL); if (!ret) ErrorF("Warning: Unable to disable CRTC that is outside of new screen dimensions"); continue; } /* Just needs to be resized to a temporary mode */ mode = vncRandRModeGet(width - crtc->x, height - crtc->y); if (mode == NULL) { ErrorF("Warning: Unable to create custom mode for %dx%d", width - crtc->x, height - crtc->y); continue; } ret = vncRandRCrtcSet(pScreen, crtc, mode, crtc->x, crtc->y, crtc->rotation, crtc->numOutputs, crtc->outputs); RRModeDestroy(mode); if (!ret) ErrorF("Warning: Unable to crop CRTC to new screen dimensions"); } return TRUE; }
int ProcRRSetPanning (ClientPtr client) { REQUEST(xRRSetPanningReq); xRRSetPanningReply rep; RRCrtcPtr crtc; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; TimeStamp time; BoxRec total; BoxRec tracking; INT16 border[4]; int n; REQUEST_SIZE_MATCH(xRRSetPanningReq); VERIFY_RR_CRTC(stuff->crtc, crtc, DixReadAccess); /* All crtcs must be associated with screens before client * requests are processed */ pScreen = crtc->pScreen; pScrPriv = rrGetScrPriv(pScreen); if (!pScrPriv) { time = currentTime; rep.status = RRSetConfigFailed; goto sendReply; } time = ClientTimeToServerTime(stuff->timestamp); if (!pScrPriv->rrGetPanning) return RRErrorBase + BadRRCrtc; total.x1 = stuff->left; total.y1 = stuff->top; total.x2 = total.x1 + stuff->width; total.y2 = total.y1 + stuff->height; tracking.x1 = stuff->track_left; tracking.y1 = stuff->track_top; tracking.x2 = tracking.x1 + stuff->track_width; tracking.y2 = tracking.y1 + stuff->track_height; border[0] = stuff->border_left; border[1] = stuff->border_top; border[2] = stuff->border_right; border[3] = stuff->border_bottom; if (! pScrPriv->rrSetPanning (pScreen, crtc, &total, &tracking, border)) return BadMatch; pScrPriv->lastSetTime = time; rep.status = RRSetConfigSuccess; sendReply: rep.type = X_Reply; rep.sequenceNumber = client->sequence; rep.length = 0; rep.newTimestamp = pScrPriv->lastSetTime.milliseconds; if (client->swapped) { swaps(&rep.sequenceNumber, n); swapl(&rep.length, n); swaps(&rep.newTimestamp, n); } WriteToClient(client, sizeof(xRRSetPanningReply), (char *)&rep); return Success; }
vfbScreenInit(ScreenPtr pScreen, int argc, char **argv) #endif { #if XORG < 113 vfbScreenInfoPtr pvfb = &vfbScreens[index]; #else vfbScreenInfoPtr pvfb = &vfbScreens[pScreen->myNum]; #endif int dpi; int ret; void *pbits; #ifdef RANDR rrScrPrivPtr rp; #endif #if XORG >= 113 if (!dixRegisterPrivateKey(&cmapScrPrivateKeyRec, PRIVATE_SCREEN, 0)) return FALSE; #endif /* 96 is the default used by most other systems */ dpi = 96; if (monitorResolution) dpi = monitorResolution; pbits = vfbAllocateFramebufferMemory(&pvfb->fb); if (!pbits) return FALSE; #if XORG < 113 vncFbptr[index] = pbits; vncFbstride[index] = pvfb->fb.paddedWidth; #else vncFbptr[pScreen->myNum] = pbits; vncFbstride[pScreen->myNum] = pvfb->fb.paddedWidth; #endif miSetPixmapDepths(); switch (pvfb->fb.depth) { case 8: miSetVisualTypesAndMasks (8, ((1 << StaticGray) | (1 << GrayScale) | (1 << StaticColor) | (1 << PseudoColor) | (1 << TrueColor) | (1 << DirectColor)), 8, PseudoColor, 0, 0, 0); break; case 16: miSetVisualTypesAndMasks (16, ((1 << TrueColor) | (1 << DirectColor)), 8, TrueColor, 0xf800, 0x07e0, 0x001f); break; case 24: miSetVisualTypesAndMasks (24, ((1 << TrueColor) | (1 << DirectColor)), 8, TrueColor, 0xff0000, 0x00ff00, 0x0000ff); break; case 32: miSetVisualTypesAndMasks (32, ((1 << TrueColor) | (1 << DirectColor)), 8, TrueColor, 0xff000000, 0x00ff0000, 0x0000ff00); break; default: return FALSE; } ret = fbScreenInit(pScreen, pbits, pvfb->fb.width, pvfb->fb.height, dpi, dpi, pvfb->fb.paddedWidth, pvfb->fb.bitsPerPixel); #ifdef RENDER if (ret && Render) ret = fbPictureInit (pScreen, 0, 0); #endif if (!ret) return FALSE; #if XORG < 110 miInitializeBackingStore(pScreen); #endif /* * Circumvent the backing store that was just initialised. This amounts * to a truely bizarre way of initialising SaveDoomedAreas and friends. */ pScreen->InstallColormap = vfbInstallColormap; pScreen->UninstallColormap = vfbUninstallColormap; pScreen->ListInstalledColormaps = vfbListInstalledColormaps; pScreen->SaveScreen = vfbSaveScreen; miPointerInitialize(pScreen, &vfbPointerSpriteFuncs, &vfbPointerCursorFuncs, FALSE); pScreen->blackPixel = pvfb->blackPixel; pScreen->whitePixel = pvfb->whitePixel; if (!pvfb->pixelFormatDefined) { switch (pvfb->fb.depth) { case 16: pvfb->pixelFormatDefined = TRUE; pvfb->rgbNotBgr = TRUE; pvfb->blueBits = pvfb->redBits = 5; pvfb->greenBits = 6; break; case 24: case 32: pvfb->pixelFormatDefined = TRUE; pvfb->rgbNotBgr = TRUE; pvfb->blueBits = pvfb->redBits = pvfb->greenBits = 8; break; } } if (pvfb->pixelFormatDefined) { VisualPtr vis = pScreen->visuals; for (int i = 0; i < pScreen->numVisuals; i++) { if (pvfb->rgbNotBgr) { vis->offsetBlue = 0; vis->blueMask = (1 << pvfb->blueBits) - 1; vis->offsetGreen = pvfb->blueBits; vis->greenMask = ((1 << pvfb->greenBits) - 1) << vis->offsetGreen; vis->offsetRed = vis->offsetGreen + pvfb->greenBits; vis->redMask = ((1 << pvfb->redBits) - 1) << vis->offsetRed; } else { vis->offsetRed = 0; vis->redMask = (1 << pvfb->redBits) - 1; vis->offsetGreen = pvfb->redBits; vis->greenMask = ((1 << pvfb->greenBits) - 1) << vis->offsetGreen; vis->offsetBlue = vis->offsetGreen + pvfb->greenBits; vis->blueMask = ((1 << pvfb->blueBits) - 1) << vis->offsetBlue; } vis++; } } ret = fbCreateDefColormap(pScreen); if (!ret) return FALSE; miSetZeroLineBias(pScreen, pvfb->lineBias); pvfb->closeScreen = pScreen->CloseScreen; pScreen->CloseScreen = vfbCloseScreen; #ifdef RANDR ret = RRScreenInit(pScreen); if (!ret) return FALSE; rp = rrGetScrPriv(pScreen); rp->rrGetInfo = vncRandRGetInfo; rp->rrSetConfig = NULL; rp->rrScreenSetSize = vncRandRScreenSetSize; rp->rrCrtcSet = vncRandRCrtcSet; rp->rrOutputValidateMode = vncRandROutputValidateMode; rp->rrModeDestroy = vncRandRModeDestroy; ret = vncRandRInit(pScreen); if (!ret) return FALSE; #endif return TRUE; } /* end vfbScreenInit */
int ProcRRGetOutputInfo(ClientPtr client) { REQUEST(xRRGetOutputInfoReq); xRRGetOutputInfoReply rep; RROutputPtr output; CARD8 *extra; unsigned long extraLen; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; RRCrtc *crtcs; RRMode *modes; RROutput *clones; char *name; int i; REQUEST_SIZE_MATCH(xRRGetOutputInfoReq); VERIFY_RR_OUTPUT(stuff->output, output, DixReadAccess); pScreen = output->pScreen; pScrPriv = rrGetScrPriv(pScreen); rep.type = X_Reply; rep.sequenceNumber = client->sequence; rep.length = bytes_to_int32(OutputInfoExtra); rep.timestamp = pScrPriv->lastSetTime.milliseconds; rep.crtc = output->crtc ? output->crtc->id : None; rep.mmWidth = output->mmWidth; rep.mmHeight = output->mmHeight; rep.connection = output->connection; rep.subpixelOrder = output->subpixelOrder; rep.nCrtcs = output->numCrtcs; rep.nModes = output->numModes + output->numUserModes; rep.nPreferred = output->numPreferred; rep.nClones = output->numClones; rep.nameLength = output->nameLength; extraLen = ((output->numCrtcs + output->numModes + output->numUserModes + output->numClones + bytes_to_int32(rep.nameLength)) << 2); if (extraLen) { rep.length += bytes_to_int32(extraLen); extra = malloc(extraLen); if (!extra) return BadAlloc; } else extra = NULL; crtcs = (RRCrtc *) extra; modes = (RRMode *) (crtcs + output->numCrtcs); clones = (RROutput *) (modes + output->numModes + output->numUserModes); name = (char *) (clones + output->numClones); for (i = 0; i < output->numCrtcs; i++) { crtcs[i] = output->crtcs[i]->id; if (client->swapped) swapl(&crtcs[i]); } for (i = 0; i < output->numModes + output->numUserModes; i++) { if (i < output->numModes) modes[i] = output->modes[i]->mode.id; else modes[i] = output->userModes[i - output->numModes]->mode.id; if (client->swapped) swapl(&modes[i]); } for (i = 0; i < output->numClones; i++) { clones[i] = output->clones[i]->id; if (client->swapped) swapl(&clones[i]); } memcpy(name, output->name, output->nameLength); if (client->swapped) { swaps(&rep.sequenceNumber); swapl(&rep.length); swapl(&rep.timestamp); swapl(&rep.crtc); swapl(&rep.mmWidth); swapl(&rep.mmHeight); swaps(&rep.nCrtcs); swaps(&rep.nModes); swaps(&rep.nClones); swaps(&rep.nameLength); } WriteToClient(client, sizeof(xRRGetOutputInfoReply), (char *) &rep); if (extraLen) { WriteToClient(client, extraLen, (char *) extra); free(extra); } return Success; }
int ProcRRGetOutputInfo(ClientPtr client) { REQUEST(xRRGetOutputInfoReq); xRRGetOutputInfoReply rep; RROutputPtr output; CARD8 *extra; unsigned long extraLen; ScreenPtr pScreen; rrScrPrivPtr pScrPriv; RRCrtc *crtcs; RRMode *modes; RROutput *clones; char *name; int i; REQUEST_SIZE_MATCH(xRRGetOutputInfoReq); VERIFY_RR_OUTPUT(stuff->output, output, DixReadAccess); pScreen = output->pScreen; pScrPriv = rrGetScrPriv(pScreen); rep = (xRRGetOutputInfoReply) { .type = X_Reply, .status = RRSetConfigSuccess, .sequenceNumber = client->sequence, .length = bytes_to_int32(OutputInfoExtra), .timestamp = pScrPriv->lastSetTime.milliseconds, .crtc = output->crtc ? output->crtc->id : None, .mmWidth = output->mmWidth, .mmHeight = output->mmHeight, .connection = output->connection, .subpixelOrder = output->subpixelOrder, .nCrtcs = output->numCrtcs, .nModes = output->numModes + output->numUserModes, .nPreferred = output->numPreferred, .nClones = output->numClones, .nameLength = output->nameLength }; extraLen = ((output->numCrtcs + output->numModes + output->numUserModes + output->numClones + bytes_to_int32(rep.nameLength)) << 2); if (extraLen) { rep.length += bytes_to_int32(extraLen); extra = malloc(extraLen); if (!extra) return BadAlloc; } else extra = NULL; crtcs = (RRCrtc *) extra; modes = (RRMode *) (crtcs + output->numCrtcs); clones = (RROutput *) (modes + output->numModes + output->numUserModes); name = (char *) (clones + output->numClones); for (i = 0; i < output->numCrtcs; i++) { crtcs[i] = output->crtcs[i]->id; if (client->swapped) swapl(&crtcs[i]); } for (i = 0; i < output->numModes + output->numUserModes; i++) { if (i < output->numModes) modes[i] = output->modes[i]->mode.id; else modes[i] = output->userModes[i - output->numModes]->mode.id; if (client->swapped) swapl(&modes[i]); } for (i = 0; i < output->numClones; i++) { clones[i] = output->clones[i]->id; if (client->swapped) swapl(&clones[i]); } memcpy(name, output->name, output->nameLength); if (client->swapped) { swaps(&rep.sequenceNumber); swapl(&rep.length); swapl(&rep.timestamp); swapl(&rep.crtc); swapl(&rep.mmWidth); swapl(&rep.mmHeight); swaps(&rep.nCrtcs); swaps(&rep.nModes); swaps(&rep.nPreferred); swaps(&rep.nClones); swaps(&rep.nameLength); } WriteToClient(client, sizeof(xRRGetOutputInfoReply), &rep); if (extraLen) { WriteToClient(client, extraLen, extra); free(extra); } return Success; } static void RRSetPrimaryOutput(ScreenPtr pScreen, rrScrPrivPtr pScrPriv, RROutputPtr output) { if (pScrPriv->primaryOutput == output) return; /* clear the old primary */ if (pScrPriv->primaryOutput) { RROutputChanged(pScrPriv->primaryOutput, 0); pScrPriv->primaryOutput = NULL; } /* set the new primary */ if (output) { pScrPriv->primaryOutput = output; RROutputChanged(output, 0); } pScrPriv->layoutChanged = TRUE; RRTellChanged(pScreen); } int ProcRRSetOutputPrimary(ClientPtr client) { REQUEST(xRRSetOutputPrimaryReq); RROutputPtr output = NULL; WindowPtr pWin; rrScrPrivPtr pScrPriv; int ret; REQUEST_SIZE_MATCH(xRRSetOutputPrimaryReq); ret = dixLookupWindow(&pWin, stuff->window, client, DixGetAttrAccess); if (ret != Success) return ret; if (stuff->output) { VERIFY_RR_OUTPUT(stuff->output, output, DixReadAccess); if (!output->pScreen->isGPU && output->pScreen != pWin->drawable.pScreen) { client->errorValue = stuff->window; return BadMatch; } if (output->pScreen->isGPU && output->pScreen->current_master != pWin->drawable.pScreen) { client->errorValue = stuff->window; return BadMatch; } } pScrPriv = rrGetScrPriv(pWin->drawable.pScreen); if (pScrPriv) RRSetPrimaryOutput(pWin->drawable.pScreen, pScrPriv, output); return Success; }