static RROutputPtr rdpRRAddOutput(rdpPtr dev, const char *aname, int x, int y, int width, int height) { RRModePtr mode; RRCrtcPtr crtc; RROutputPtr output; xRRModeInfo modeInfo; char name[64]; sprintf (name, "%dx%d", width, height); memset (&modeInfo, 0, sizeof(modeInfo)); modeInfo.width = width; modeInfo.height = height; modeInfo.nameLength = strlen(name); mode = RRModeGet(&modeInfo, name); if (mode == 0) { LLOGLN(0, ("rdpRRAddOutput: RRModeGet failed")); return 0; } crtc = RRCrtcCreate(dev->pScreen, NULL); if (crtc == 0) { LLOGLN(0, ("rdpRRAddOutput: RRCrtcCreate failed")); RRModeDestroy(mode); return 0; } output = RROutputCreate(dev->pScreen, aname, strlen(aname), NULL); if (output == 0) { LLOGLN(0, ("rdpRRAddOutput: RROutputCreate failed")); RRCrtcDestroy(crtc); RRModeDestroy(mode); return 0; } if (!RROutputSetClones(output, NULL, 0)) { LLOGLN(0, ("rdpRRAddOutput: RROutputSetClones failed")); } if (!RROutputSetModes(output, &mode, 1, 0)) { LLOGLN(0, ("rdpRRAddOutput: RROutputSetModes failed")); } if (!RROutputSetCrtcs(output, &crtc, 1)) { LLOGLN(0, ("rdpRRAddOutput: RROutputSetCrtcs failed")); } if (!RROutputSetConnection(output, RR_Connected)) { LLOGLN(0, ("rdpRRAddOutput: RROutputSetConnection failed")); } RRCrtcNotify(crtc, mode, x, y, RR_Rotate_0, NULL, 1, &output); dev->output[dev->extra_outputs] = output; dev->crtc[dev->extra_outputs] = crtc; dev->extra_outputs++; return output; }
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; }
static Bool RRCloseScreen (int i, ScreenPtr pScreen) { rrScrPriv(pScreen); int j; unwrap (pScrPriv, pScreen, CloseScreen); for (j = pScrPriv->numCrtcs - 1; j >= 0; j--) RRCrtcDestroy (pScrPriv->crtcs[j]); for (j = pScrPriv->numOutputs - 1; j >= 0; j--) RROutputDestroy (pScrPriv->outputs[j]); xfree (pScrPriv->crtcs); xfree (pScrPriv->outputs); xfree (pScrPriv); RRNScreens -= 1; /* ok, one fewer screen with RandR running */ return (*pScreen->CloseScreen) (i, pScreen); }