The X Resize, Rotate and Reflect Extension Version 1.2 2006-4-13 Jim Gettys Jim.Gettys@hp.com Cambridge Research Laboratory HP Labs Hewlett Packard Company Keith Packard keith.packard@intel.com Open Source Technology Center Intel Corporation 1. Introduction The X Resize, Rotate and Reflect Extension, called RandR for short, brings the ability to resize, rotate and reflect the root window of a screen. It is based on the X Resize and Rotate Extension as specified in the Proceedings of the 2001 Usenix Technical Conference [RANDR]. RandR as implemented and integrated into the X server differs in one substantial fashion from the design discussed in that paper: that is, RandR 1.0 does not implement the depth switching described in that document, and the support described for that in the protocol in that document and in the implementation has been removed from the protocol described here, as it has been overtaken by events. These events include: ► Modern toolkits (in this case, GTK+ 2.x) have progressed to the point of implementing migration between screens of arbitrary depths ► The continued advance of Moore's law has made limited amounts of VRAM less of an issue, reducing the pressure to implement depth switching on laptops or desktop systems ► The continued decline of legacy toolkits whose design would have required depth switching to support migration ► The lack of depth switching implementation experience in the intervening time, due to events beyond our control Additionally, the requirement to support depth switching might complicate other re-engineering of the device independent part of the X server that is currently being contemplated. Rather than further delaying RandR's widespread deployment for a feature long wanted by the community (resizing of screens, particularly on laptops), or the deployment of a protocol design that might be flawed due to lack of implementation experience, we decided to remove depth switching from the protocol. It may be implemented at a later time if resources and interests permit as a revision to the protocol described here, which will remain a stable base for applications. The protocol described here has been implemented in the main X.org server, and more fully in the hw/kdrive implementation in the distribution, which fully implements resizing, rotation and reflection. 1.2 Introduction to version 1.2 of the extension One of the significant limitations found in version 1.1 of the RandR protocol was the inability to deal with the Xinerama model where multiple monitors display portions of a common underlying screen. In this environment, zero or more video outputs are associated with each CRT controller which defines both a set of video timings and a 'viewport' within the larger screen. This viewport is independent of the overall size of the screen, and may be located anywhere within the screen. The effect is to decouple the reported size of the screen from the size presented by each video output, and to permit multiple outputs to present information for a single screen. To extend RandR for this model, we separate out the output, CRTC and screen configuration information and permit them to be configured separately. For compatibility with the 1.1 version of the protocol, we make the 1.1 requests simultaneously affect both the screen and the (presumably sole) CRTC and output. The set of available outputs are presented with UTF-8 encoded names and may be connected to CRTCs as permitted by the underlying hardware. CRTC configuration is now done with full mode information instead of just size and refresh rate, and these modes have names. These names also use UTF-8 encoding. New modes may also be added by the user. Additional requests and events are provided for this new functionality. ┌────────────────────────────────┬──────────┐ ┏━━━━━━━┳───────────────┐ ╔════════╗ ╔════════╗ ┃ 1 ┃ │ ║ A ║ ║ B ║ ┃ ┏━━━╋━━━━━━━━━━━━━━━┫ ║ ║ ║ ║ ┣━━━╋━━━┛ ┃ ╚════════╝ ╚════════╝ │ ┃ 2 ┃─────────────────┐ │ ┃ ┃ ╔═══════════════════╗ │ ┃ ┃ ║ ║ │ ┗━━━━━━━━━━━━━━━━━━━┫ ║ C ║ └───────────────────────┘ ║ ║ ┌──────┐ ┏━━━━┓ ╔══════╗ ║ ║ │screen│ ┃CRTC┃ ║output║ ╚═══════════════════╝ └──────┘ ┗━━━━┛ ╚══════╝ In this picture, the screen is covered (incompletely) by two CRTCs. CRTC1 is connected to two outputs, A and B. CRTC2 is connected to output C. Outputs A and B will present exactly the same region of the screen using the same mode line. Output C will present a different (larger) region of the screen using a different mode line. RandR provides information about each available CRTC and output; the connection between CRTC and output is under application control, although the hardware will probably impose restrictions on the possible configurations. The protocol doesn't try to describe these restrictions, instead it provides a mechanism to find out what combinations are supported. For instance, dual-link DVI gangs two CRTC outputs together to provide higher bandwidth for large resolution screens. This is exposed in RandR by requiring that nothing be connected to the second CRTC when driving a high resolution screen on the first. 1.1 Acknowledgements Our thanks to the contributors to the design found on the xpert mailing list, in particular: Alan Hourihane for work on the early implementation Andrew C. Aitchison for help with the XFree86 DDX implementation Andy Ritger for early questions about how mergefb/Xinerama work with RandR Carl Worth for editing the specification and Usenix paper David Dawes for XFree86 DDX integration work Thomas Winischhofer for the hardware-accelerated SiS rotation implementation Matthew Tippet and Kevin Martin for splitting outputs and CRTCs to more fully expose what video hardware can do ❧❧❧❧❧❧❧❧❧❧❧ 2. Screen change model Screens may change dynamically, either under control of this extension, or due to external events. Examples include: monitors being swapped, pressing a button to switch from internal display to an external monitor on a laptop, or, eventually, the hotplug of a display card entirely on busses such as Cardbus or Express Card which permit hot-swap (which will require other work in addition to this extension). Since the screen configuration is dynamic and asynchronous to the client and may change at any time RandR provides mechanisms to ensure that your clients view is up to date with the configuration possibilities of the moment and enforces applications that wish to control the configuration to prove that their information is up to date before honoring requests to change the screen configuration (by requiring a timestamp on the request). Interested applications are notified whenever the screen configuration changes, providing the current size of the screen and subpixel order (see the Render extension [RENDER]), to enable proper rendering of subpixel decimated client text to continue, along with a time stamp of the configuration change. A client must refresh its knowledge of the screen configuration before attempting to change the configuration after a notification, or the request will fail. To avoid multiplicative explosion between orientation, reflection and sizes, the sizes are only those sizes in the normal (0) rotation. Rotation and reflection and how they interact can be confusing. In Randr, the coordinate system is rotated in a counter-clockwise direction relative to the normal orientation. Reflection is along the window system coordinate system, not the physical screen X and Y axis, so that rotation and reflection do not interact. The other way to consider reflection is to is specified in the "normal" orientation, before rotation, if you find the other way confusing. We expect that most clients and toolkits will be oblivious to changes to the screen structure, as they generally use the values in the connections Display structure directly. By toolkits updating the values on the fly, we believe pop-up menus and other pop up windows will position themselves correctly in the face of screen configuration changes (the issue is ensuring that pop-ups are visible on the reconfigured screen). ❧❧❧❧❧❧❧❧❧❧❧ 3. Data Types The subpixel order is shared with the Render extension, and is documented there. The only datatype defined is the screen size, defined in the normal (0 degree) orientation. ❧❧❧❧❧❧❧❧❧❧❧ 4. Errors Errors are sent using core X error reports. Output A value for an OUTPUT argument does not name a defined OUTPUT. CRTC A value for a CRTC argument does not name a defined CRTC. Mode A value for a MODE argument does not name a defined MODE. ❧❧❧❧❧❧❧❧❧❧❧ 5. Protocol Types RRCONFIGSTATUS { Success InvalidConfigTime InvalidTime Failed } ROTATION { Rotate_0 Rotate_90 Rotate_180 Rotate_270 Reflect_X Reflect_Y } RRSELECTMASK { RRScreenChangeNotifyMask RRCrtcChangeNotifyMask (New in version 1.2) RROutputChangeNotifyMask (New in version 1.2) RROutputPropertyNotifyMask (New in version 1.2) } SIZEID { CARD16 } MODE { XID or None } CRTC { XID } OUTPUT { XID } CONNECTION { Connected, Disconnected, UnknownConnection } SUBPIXELORDER { SubPixelUnknown The subpixel order uses the Render SubPixelHorizontalRGB extensions definitions; they are here SubPixelHorizontalBGR only for convenience. SubPixelVerticalRGB SubPixelVerticalBGR SubPixelNone } SCREENSIZE { widthInPixels, heightInPixels: CARD16 widthInMillimeters, heightInMillimeters: CARD16 } MODEFLAG { hsync_positive hsync_negative vsync_positive vsync_negative interlace double_scan csync csync_positive csync_negative hskew_present bcast pixel_multiplex double_clock clock_divide_by_2 } MODEINFO { id: MODE name: STRING widthInPixels, heightInPixels: CARD16 widthInMillimeters, heightInMillimeters: CARD32 dotClock: CARD32 hSyncStart, hSyncEnd, hTotal, hSkew: CARD16 vSyncStart, vSyncEnd, vTotal: CARD16 modeFlags: SETofMODEFLAG } REFRESH { rates: LISTofCARD16 } ❧❧❧❧❧❧❧❧❧❧❧ 6. Extension Initialization The name of this extension is "RANDR". ┌─── RRQueryVersion client-major-version: CARD32 client-minor-version: CARD32 ▶ major-version: CARD32 minor-version: CARD32 └─── The client sends the highest supported version to the server and the server sends the highest version it supports, but no higher than the requested version. Major versions changes can introduce incompatibilities in existing functionality, minor version changes introduce only backward compatible changes. It is the clients responsibility to ensure that the server supports a version which is compatible with its expectations. ❧❧❧❧❧❧❧❧❧❧❧ 7. Extension Requests ┌─── RRSelectInput window: WINDOW enable: SETofRRSELECTMASK └─── Errors: Window, Value If 'enable' is RRScreenChangeNotifyMask, RRScreenChangeNotify events will be sent when the screen configuration changes, either from this protocol extension, or due to detected external screen configuration changes. RRScreenChangeNotify may also be sent when this request executes if the screen configuration has changed since the client connected, to avoid race conditions. New for version 1.2: If 'enable' contains RRCrtcChangeMask, RRCrtcChangeNotify events will be sent when a the configuration for a CRTC associated with the screen changes, either through this protocol extension or due to detected external changes. RRCrtcChangeNotify may also be sent when this request executes if the CRTC configuration has changed since the client connected, to avoid race conditions. If 'enable' contains RROutputChangeMask, RROutputChangeNotify events will be sent when a the configuration for an output associated with the screen changes, either through this protocol extension or due to detected external changes. RROutputChangeNotify may also be sent when this request executes if the output configuration has changed since the client connected, to avoid race conditions. If 'enable' contains RROutputPropertyNotifyMask, RROutputPropertyNotify events will be sent when properties change on this output. ┌─── RRSetScreenConfig window: WINDOW timestamp: TIMESTAMP config-timestamp: TIMESTAMP size-id: SIZEID rotation: ROTATION rate: CARD16 ▶ status: RRCONFIGSTATUS new-timestamp: TIMESTAMP config-timestamp: TIMESTAMP root: WINDOW subpixelOrder: SUBPIXELORDER └─── Errors: Value, Match If 'timestamp' is less than the time when the configuration was last successfully set, the request is ignored and InvalidTime returned in status. If 'config-timestamp' is not equal to when the server's screen configurations last changed, the request is ignored and InvalidConfigTime returned in status. This could occur if the screen changed since you last made a RRGetScreenInfo request, perhaps by a different piece of display hardware being installed. Rather than allowing an incorrect call to be executed based on stale data, the server will ignore the request. 'rate' contains the desired refresh rate. If it is zero, the server selects an appropriate rate. This request may fail for other indeterminate reasons, in which case 'status' will be set to Failed and no configuration change will be made. This request sets the screen to the specified size, rate, rotation and reflection. When this request succeeds, 'status' contains Success and the requested changes to configuration will have been made. 'new-time-stamp' contains the time at which this request was executed. 'config-timestamp' contains the time when the possible screen configurations were last changed. 'root' contains the root window for the screen indicated by the window. 'subpixelOrder' contains the resulting subpixel order of the screen to allow correct subpixel rendering. Value errors are generated when 'rotation', 'rate' or 'size-id' are invalid. ┌─── RRGetScreenInfo window: WINDOW ▶ rotations: SETofROTATION root: WINDOW timestamp: TIMESTAMP config-timestamp: TIMESTAMP size-id: SIZEID rotation: ROTATION rate: CARD16 sizes: LISTofSCREENSIZE refresh: LISTofREFRESH └─── Errors: Window RRGetScreenInfo returns information about the current and available configurations for the screen associated with 'window'. 'rotations' contains the set of rotations and reflections supported by the screen. 'root' is the root window of the screen. 'config-timestamp' indicates when the screen configuration information last changed: requests to set the screen will fail unless the timestamp indicates that the information the client is using is up to date, to ensure clients can be well behaved in the face of race conditions. 'timestamp' indicates when the configuration was last set. 'size-id' indicates which size is active. 'rate' is the current refresh rate. This is zero when the refresh rate is unknown or on devices for which refresh is not relevant. 'sizes' is the list of possible frame buffer sizes (at the normal orientation. Each size indicates both the linear physical size of the screen and the pixel size. 'refresh' is the list of refresh rates for each size. Each element of 'sizes' has a corresponding element in 'refresh'. An empty list indicates no known rates, or a device for which refresh is not relevant. The default size of the screen (the size that would become the current size when the server resets) is the first size in the list. 7.1. Extension Requests added in version 1.2 of the extension As introduced above, version 1.2 of the extension splits the screen size from the crtc and output configuration, permitting the subset of the screen presented by multiple outputs to be configured. As a separate notion, the size of the screen itself may be arbitrarily configured within a defined range. As crtcs and outputs are added and removed from the system, the set returned by the extension will change so that applications can detect dynamic changes in the display environment. ┌─── RRGetScreenSizeRange window: WINDOW ▶ CARD16 minWidth, minHeight CARD16 maxWidth, maxHeight └─── Errors: Window Returns the range of possible screen sizes. The screen may be set to any size within this range. ┌─── RRSetScreenSize window: WINDOW width: CARD16 height: CARD16 width-in-millimeters: CARD32 height-in-millimeters: CARD32 └─── Errors: Window, Match, Value Sets the screen to the specified size. 'width' and 'height' must be within the range allowed by GetScreenSizeRanges, otherwise a Value error results. All active monitors must be configured to display a subset of the specified size, else a Match error results. 'width-in-millimeters' and 'height-in-millimeters' can be set to reflect the physical size of the screen reported both through this extension and the core protocol. They must be non-zero, or Value error results. ┌─── RRGetScreenResources window: WINDOW ▶ timestamp: TIMESTAMP config-timestamp: TIMESTAMP crtcs: LISTofCRTC outputs: LISTofOUTPUT modes: LISTofMODEINFO └─── Errors: Window RRGetScreenResources returns the list of outputs and crtcs connected to the screen associated with 'window'. 'timestamp' indicates when the configuration was last set. 'config-timestamp' indicates when the configuration information last changed. Requests to configure the output will fail unless the timestamp indicates that the information the client is using is up to date, to ensure clients can be well behaved in the face of race conditions. 'crtcs' contains the list of CRTCs associated with the screen. 'outputs' contains the list of outputs associated with the screen. 'modes' contains the list of modes associated with the screen This request explicitly asks the server to ensure that the configuration data is up-to-date wrt the hardware. If that requires polling, this is when such polling would take place. Requests for further information should not poll, but rather return the data collected at this point. ┌─── RRGetOutputInfo output: OUTPUT config-timestamp: TIMESTAMP ▶ status: RRCONFIGSTATUS timestamp: TIMESTAMP crtc: CRTC name: STRING connection: CONNECTION subpixel-order: SUBPIXELORDER crtcs: LISTofCRTC clones: LISTofOUTPUT modes: LISTofMODE └─── Errors: Output RRGetOutputInfo returns information about the current and available configurations 'output'. If 'config-timestamp' does not match the current configuration timestamp (as returned by RRGetScreenResources), 'status' is set to InvalidConfigTime and the remaining reply data is empty. Otherwise, 'status' is set to Success. 'timestamp' indicates when the configuration was last set. 'crtc' is the current source CRTC for video data, or Disabled if the output is not connected to any CRTC. 'name' is a UTF-8 encoded string designed to be presented to the user to indicate which output this is. E.g. "S-Video" or "DVI". 'connection' indicates whether the hardware was able to detect a device connected to this output. If the hardware cannot determine whether something is connected, it will set this to UnknownConnection. 'subpixel-order' contains the resulting subpixel order of the connected device to allow correct subpixel rendering. 'crtcs' is the list of CRTCs that this output may be connected to. Attempting to connect this output to a different CRTC results in a Match error. 'clones' is the list of outputs which may be simultaneously connected to the same CRTC along with this output. Attempting to connect this output with an output not in the 'clones' list results in a Match error. 'modes' is the list of modes supported by this output. Attempting to connect this output to a CRTC not using one of these modes results in a Match error. ┌─── RRListOutputProperties output:OUTPUT ▶ atoms: LISTof ATOM └─── Errors: Output This request returns the atoms of properties currently defined on the output. ┌─── RRChangeOutputProperty output: OUTPUT property, type: ATOM format: {8, 16, 32} mode: { Replace, Prepend, Append } data: LISTofINT8 or LISTofINT16 or LISTofINT32 └─── Errors: Alloc, Atom, Match, Value, Output This request alters the property for the specified output. The type is uninterpreted by the server. The format specifies whether the data should be viewed as a list of 8-bit, 16-bit, or 32-bit quantities so that the server can correctly byte-swap as necessary. If the mode is Replace, the previous property value is discarded. If the mode is Prepend or Append, then the type and format must match the existing property value (or a Match error results). If the property is undefined, it is treated as defined with the correct type and format with zero-length data. For Prepend, the data is tacked on to the beginning of the existing data, and for Append, it is tacked on to the end of the existing data. This request generates a OutputPropertyNotify The lifetime of a property is not tied to the storing client. Properties remain until explicitly deleted, until the output is destroyed, or until server reset (see section 10). The maximum size of a property is server-dependent and may vary dynamically. ┌─── RRDeleteOutputProperty output: OUTPUT property: ATOM └─── Errors: Atom, Output This request deletes the property from the specified window if the property exists and generates a OutputPropertyNotify event unless the property does not exist. ┌─── RRGetOutputProperty output: OUTPUT property: ATOM type: ATOM or AnyPropertyType long-offset, long-length: CARD32 delete: BOOL ▶ type: ATOM or None format: {0, 8, 16, 32} bytes-after: CARD32 value: LISTofINT8 or LISTofINT16 or LISTofINT32 └─── Errors: Atom, Value, Output If the specified property does not exist for the specified output, then the return type is None, the format and bytes-after are zero, and the value is empty. The delete argument is ignored in this case. If the specified property exists but its type does not match the specified type, then the return type is the actual type of the property, the format is the actual format of the property (never zero), the bytes-after is the length of the property in bytes (even if the format is 16 or 32), and the value is empty. The delete argument is ignored in this case. If the specified property exists and either AnyPropertyType is specified or the specified type matches the actual type of the property, then the return type is the actual type of the property, the format is the actual format of the property (never zero), and the bytes-after and value are as follows, given: N = actual length of the stored property in bytes (even if the format is 16 or 32) I = 4 × offset T = N - I L = MINIMUM(T, 4 × long-length) A = N - (I + L) The returned value starts at byte index I in the property (indexing from 0), and its length in bytes is L. However, it is a Value error if long-offset is given such that L is negative. The value of bytes-after is A, giving the number of trailing unread bytes in the stored property. If delete is True and the bytes-after is zero, the property is also deleted from the output, and a RROutputPropertyNotify event is generated. ┌─── RRCreateMode window: WINDOW modeinfo: MODEINFO ▶ mode: MODE └─── Errors: Window, Name, Value 'modeinfo' provides a new mode for outputs on the screen associated with 'window'. If the name of 'modeinfo' names an existing mode, a Name error is returned. If some parameter of the mode is not valid in some other way, a Value error is returned. The returned 'mode' provides the id for the mode. ┌─── RRDestroyMode mode: MODE └─── Errors: Mode, Access The user-defined 'mode' is destroyed. 'mode' must name a mode defined with RRCreateMode, else an Match error is returned. If 'mode' is in use by some CRTC or Output, then an Access error is returned. ┌─── RRAddOutputMode output: OUTPUT mode: MODE └─── Errors: Output, Mode, Match 'output' indicates which output is to be configured. 'mode' specifies which mode to add. If 'mode' is not valid for 'output', then a Match error is generated. This request generates OutputChangeNotify events. ┌─── RRDeleteOutputMode output: OUTPUT mode: MODE └─── Errors: Output, Mode 'output' indicates which output is to be configured. 'mode' specifies which mode to delete. 'mode' must have been added with RRAddOutputMode, else an Access error is returned. 'mode' must not be active, else a Match error is returned. This request generates OutputChangeNotify events. ┌─── RRGetCrtcInfo crtc: CRTC config-timestamp: TIMESTAMP ▶ status: RRCONFIGSTATUS timestamp: TIMESTAMP x, y: INT16 width, height: CARD16 mode: MODE rotation: ROTATION outputs: LISTofOUTPUT rotations: SETofROTATION possible-outputs: LISTofOUTPUT └─── Errors: Window RRGetCrtcModes returns information about the current and available configurations for the specified crtc connected to the screen associated with 'window'. If 'config-timestamp' does not match the current configuration timestamp (as returned by RRGetScreenResources), 'status' is set to InvalidConfigTime and the remaining reply data is empty. Otherwise, 'status' is set to Success. 'timestamp' indicates when the configuration was last set. 'x' and 'y' indicate the position of this CRTC within the screen region. They will be set to 0 when the CRTC is disabled. 'width' and 'height' indicate the size of the area presented by this CRTC. 'mode' indicates which mode is active, or None indicating that the CRTC has been disabled and is not displaying the screen contents. 'rotation' indicates the active rotation. It is set to Rotate_0 when the CRTC is disabled. 'outputs' is the list of outputs currently connected to this CRTC and is empty when the CRTC is disabled. 'rotations' contains the set of rotations and reflections supported by the CRTC. 'possible-outputs' lists all of the outputs which may be connected to this CRTC. ┌─── RRSetCrtcConfig crtc: CRTC timestamp: TIMESTAMP config-timestamp: TIMESTAMP x, y: INT16 mode: MODE rotation: ROTATION outputs: LISTofOUTPUT ▶ status: RRCONFIGSTATUS new-timestamp: TIMESTAMP └─── Errors: Value, Match If 'timestamp' is less than the time when the configuration was last successfully set, the request is ignored and InvalidTime returned in status. If 'config-timestamp' is not equal to when the monitor's configuration last changed, the request is ignored and InvalidConfigTime returned in status. This could occur if the monitor changed since you last made a RRGetScreenInfo request, perhaps by a different monitor being connected to the machine. Rather than allowing an incorrect call to be executed based on stale data, the server will ignore the request. 'x' and 'y' contain the desired location within the screen for this monitor's content. 'x' and 'y' must be within the screen size, else a Value error results. 'mode' is either the desired mode or None indicating the CRTC should be disabled. If 'mode' is not one of these values, a Value error results. 'mode' must be valid for all of the configured outputs, else a Match error. 'rotation' contains the desired rotation along with which reflections should be enabled. The rotation and reflection values must be among those allowed for this monitor, else a Value error results. 'outputs' contains the set of outputs that this CRTC should be connected to. The set must be among the list of acceptable output sets for this CRTC or a Match error results. If 'mode' is None, then 'outputs' must be empty, else a Match error results. Conversely, if 'mode' is not None, then 'outputs' must not be empty, else a Match error results. This request may fail for other indeterminate reasons, in which case 'status' will be set to Failed and no configuration change will be made. This request sets the CRTC to the specified position, mode, rotation and reflection. The entire area of the CRTC must fit within the screen size, else a Match error results. As an example, rotating the screen so that a single CRTC fills the entire screen before and after may necessitate disabling the CRTC, resizing the screen, then re-enabling the CRTC at the new configuration to avoid an invalid intermediate configuration. When this request succeeds, 'status' contains Success and the requested changes to configuration will have been made. 'new-time-stamp' contains the time at which this request was executed. ┌─── RRGetCrtcGammaSize crtc: CRTC ▶ size: CARD16 └─── Errors: Crtc This request returns the size of the gamma ramps used by 'crtc'. ┌─── RRGetCrtcGamma crtc: CRTC ▶ red: LISTofCARD16 green: LISTofCARD16 blue: LISTofCARD16 └─── Errors: Crtc This request returns the currently set gamma ramps for 'crtc'. All three lists will be the size returned by the RRGetCrtcGammaSize request. ┌─── RRSetCrtcGamma crtc: CRTC red: LISTofCARD16 green: LISTofCARD16 blue: LISTofCARD16 └─── Errors: Crtc, Match This request sets the gamma ramps for 'crtc'. All three lists must be the size returned by RRGetCrtcGammaSize else a Value error results. ❧❧❧❧❧❧❧❧❧❧❧ 8. Extension Events Clients MAY select for ConfigureNotify on the root window to be informed of screen changes. This may be advantageous if all your clients need to know is the size of the root window, as it avoids round trips to set up the extension. RRScreenChangeNotify is sent if RRSelectInput has requested it whenever properties of the screen change, which may be due to external factors, such as re-cabling a monitor, etc. ┌─── RRScreenChangeNotify rotation: ROTATION; new rotation sequenceNumber: CARD16 low 16 bits of request seq. number timestamp: TIMESTAMP time screen was changed configTimestamp: TIMESTAMP time config data was changed root: WINDOW root window of screen window: WINDOW window requesting notification size-id: SIZEID index of new size subpixelOrder: SUBPIXELORDER order of subpixels widthInPixels: CARD16 heightInPixels: CARD16 widthInMillimeters: CARD16 heightInMillimeters: CARD16 └─── This event is generated whenever the screen configuration is changed and sent to requesting clients. 'timestamp' indicates when the screen configuration was changed. 'configTimestamp' says when the last time the configuration was changed. 'root' is the root of the screen the change occurred on, 'window' is window selecting for this event. 'size-id' contains the index of the current size. This event is sent whenever the screen's configuration changes or if a new screen configuration becomes available that was not available in the past. In this case (config-timestamp in the event not being equal to the config-timestamp returned in the last call to RRGetScreenInfo), the client MUST call RRGetScreenInfo to update its view of possible screen configurations to have a correct view of possible screen organizations. Clients which select screen change notification events may be sent an event immediately if the screen configuration was changed between when they connected to the X server and selected for notification. This is to prevent a common race that might occur on log-in, where many applications start up just at the time when a display manager or log in script might be changing the screen size or configuration. 8.1 Events added in version 1.2 of the RandR extension ┌─── RROutputChangeNotify: timestamp: TIMESTAMP time screen was reconfigured config-timestamp: TIMESTAMP time available config data was changed window: WINDOW window requesting notification output: OUTPUT output affected by change crtc: CRTC connected CRTC or None mode: MODE mode in use on CRTC or None connection: CONNECTION connection status └─── This event is generated whenever the available output configurations have changed and is sent to requesting clients. 'timestamp' indicates when the crtc configuration was changed by a client. 'config-timestamp' says when the last time the available configurations changed. 'root' is the root of the screen the change occurred on, 'window' is window selecting for this event. The precise change can be detected by examining the new state of the system. ┌─── RROutputPropertyNotify: window: WINDOW window requesting notification output: OUTPUT output affected by change atom: ATOM affected property time: TIMESTAMP time property was changed subpixel-order: SUBPIXELORDER order of subpixels state: { NewValue, Deleted } new property state └─── This event is reported to clients selecting RROutputPropertyChange on the window and is generated with state NewValue when a property of the window is changed using RRChangeOutputProperty even when adding zero-length data and when replacing all or part of a property with identical data. It is generated with state Deleted when a property of the window is deleted using either RRDeleteOutputProperty or RRGetOutputProperty. The timestamp indicates the server time when the property was changed. ┌─── RRCrtcChangeNotify timestamp: TIMESTAMP time monitor was changed config-timestamp: TIMESTAMP time config data was changed root: WINDOW root window of screen window: WINDOW window requesting notification crtc: CRTC CRTC which changed mode: MODE new mode rotation: ROTATION; new rotation x: INT16 x position of CRTC within screen y: INT16 y position of CRTC within screen └─── This event is generated whenever the CRTC configuration is changed and sent to requesting clients. 'timestamp' indicates when the CRTC configuration was changed. 'config-timestamp' says when the last time the configuration was changed. 'root' is the root of the screen the change occurred on, 'window' is window selecting for this event. This event is sent whenever the monitor's configuration changes or if a new monitor configuration becomes available that was not available in the past. In this case (config-timestamp in the event not being equal to the config-timestamp returned in the last call to RRGetCrtcModes), the client MUST call RRGetCrtcModes to update its view of possible monitor configurations to have a correct view of possible monitor organizations. Clients which select monitor change notification events may be sent an event immediately if the monitor configuration was changed between when they connected to the X server and selected for notification. This is to prevent a common race that might occur on log-in, where many applications start up just at the time when a display manager or log in script might be changing the monitor size or configuration. ❧❧❧❧❧❧❧❧❧❧❧ 9. Extension Versioning The RandR extension was developed in parallel with the implementation to ensure the feasibility of various portions of the design. As portions of the extension are implemented, the version number of the extension has changed to reflect the portions of the standard provided. This document describes the version 1.2 of the specification, the partial implementations have version numbers less than that. Here's a list of what each version provided: 0.0: This prototype implemented resize and rotation in the TinyX server Used approximately the protocol described in the Usenix paper. Appeared in the TinyX server in XFree86 4.2, but not in the XFree86 main server. 0.1: Added subpixel order, added an event for subpixel order. This version was never checked in to XFree86 CVS. 1.0: Implements resize, rotation, and reflection. Implemented both in the XFree86 main server (size change only at this date), and fully (size change, rotation, and reflection) in XFree86's TinyX server. 1.1: Added refresh rates 1.2: Separate screens from CRTCs and outputs, switch to full VESA modes Compatibility between 0.0 and 1.0 was *NOT* preserved, and 0.0 clients will fail against 1.0 servers. The wire encoding op-codes were changed for GetScreenInfo to ensure this failure in a relatively graceful way. Version 1.1 servers and clients are cross compatible with 1.0. Version 1.1 is considered to be stable and we intend upward compatibility from this point. Version 1.2 offers an extended model of the system with multiple output support. It offers backward compatibility with version 1.1. ❧❧❧❧❧❧❧❧❧❧❧ 10. Relationship with other extensions Two other extensions have a direct relationship with this extension. This section attempts to explain how these three are supposed to work together. 10.1 XFree86-VidModeExtension XFree86-VidModeExtension changes the configuration of a single monitor attached to the screen without changing the configuration of the screen itself. It provides the ability to specify new mode lines for the server to use along with selecting among existing mode lines. As it uses screen numbers instead of window identifiers, it can be used to affect multiple monitors in a single-screen Xinerama configuration. However, the association between screen numbers and root windows in a multi-Screen environment is not defined by the extension. Version 2.0 of this extension added the ability to adjust the DAC values in a TrueColor server to modify the brightness curves of the display. All of the utility of this extension is subsumed by RandR version 1.2, RandR should be used in preference to XFree86-VidModeExtension where both are present. 10.2 Xinerama Xinerama provides a mechanism for describing the relationship between the overall screen display and monitors placed within that area. As such, it provides the query functionality of RandR 1.2 without any of the configuration functionality. Applications using Xinerama to discover monitor geometry can continue to do so, with the caveat that they will not be informed of changes when they occur. However, Xinerama configuration data will be updated, so applications selecting for RandR notification and re-querying the configuration with the Xinerama extension will get updated information. It is probably better to view RandR as a superset of Xinerama at this point and use it in preference to Xinerama where both are present. ❧❧❧❧❧❧❧❧❧❧❧ Appendix A. Protocol Encoding Syntactic Conventions This document uses the same syntactic conventions as the core X protocol encoding document. A.1 Common Types ┌─── ROTATION 0x0001 Rotate_0 0x0002 Rotate_90 0x0004 Rotate_180 0x0008 Rotate_270 0x0010 Reflect_X 0x0020 Reflect_Y └─── Used to encode both sets of possible rotations and individual selected rotations. ┌─── RRSELECTMASK 0x0001 ScreenChangeNotifyMask 0x0002 CrtcChangeNotifyMask Added in version 1.2 0x0004 OutputChangeNotifyMask Added in version 1.2 └─── Event select mask for RRSelectInput ┌─── RRCONFIGSTATUS 0x0 Success 0x1 InvalidConfigTime 0x2 InvalidTime 0x3 Failed └─── Return status for requests which depend on time. ┌─── MODEINFO (40) Added in version 1.2 4 CARD32 id 2 CARD16 width in pixels 2 CARD16 height in pixels 4 CARD32 width in millimeters 4 CARD32 height in millimeters 4 CARD32 dot clock 2 CARD16 h sync start 2 CARD16 h sync end 2 CARD16 h total 2 CARD16 h skew 2 CARD16 v sync start 2 CARD16 v sync end 2 CARD16 v total 2 CARD16 name length 4 SETofMODEFLAG mode flags └─── An output mode specifies the complete CRTC timings for a specific mode. The vertical and horizontal synchronization rates can be computed given the dot clock and the h total/v total values. If the dot clock is zero, then all of the timing parameters and flags are not used, and must be zero as this indicates that the timings are unknown or otherwise unused. The name itself will be encoded separately in each usage. A.2 Protocol Requests Opcodes 0x1 and 0x3 were used in the 0.0 protocols, and will return errors if used in version 1.0. ┌─── RRQueryVersion 1 CARD8 major opcode 1 0x00 RandR opcode 2 3 length 4 CARD32 major version 4 CARD32 minor version ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 0 reply length 1 CARD32 major version 1 CARD32 minor version └─── ┌─── RRSetScreenConfig 1 CARD8 major opcode 1 0x02 RandR opcode 2 6 length 4 WINDOW window on screen to be configured 4 TIMESTAMP timestamp 4 TIMESTAMP config timestamp 2 SIZEID size index 2 ROTATION rotation/reflection 2 CARD16 refresh rate (1.1 only) 2 CARD16 pad ▶ 1 1 Reply 1 RRCONFIGSTATUS status 2 CARD16 sequence number 4 0 reply length 4 TIMESTAMP new timestamp 4 TIMESTAMP new configuration timestamp 4 WINDOW root 2 SUBPIXELORDER subpixel order defined in Render 2 CARD16 pad4 4 CARD32 pad5 4 CARD32 pad6 └─── ┌─── RRSelectInput 1 CARD8 major opcode 1 0x04 RandR opcode 2 3 length 4 WINDOW window 2 SETofRRSELECTMASK enable 2 CARD16 pad └─── ┌─── RRGetScreenInfo 1 CARD8 major opcode 1 0x05 RandR opcode 2 2 length 4 WINDOW window ▶ 1 1 Reply 1 CARD8 set of Rotations 2 CARD16 sequence number 4 0 reply length 4 WINDOW root window 4 TIMESTAMP timestamp 4 TIMESTAMP config timestamp 2 CARD16 number of SCREENSIZE following 2 SIZEID current size index 2 ROTATION current rotation and reflection 2 CARD16 current rate (added in version 1.1) 2 CARD16 length of rate info (number of CARD16s) 2 CARD16 pad SCREENSIZE 2 CARD16 width in pixels 2 CARD16 height in pixels 2 CARD16 width in millimeters 2 CARD16 height in millimeters REFRESH 2 CARD16 number of rates (n) 2n CARD16 rates └─── A.2.1 Protocol Requests added with version 1.2 ┌─── RRGetScreenSizeRange 1 CARD8 major opcode 1 0x06 RandR opcode 2 2 length 4 WINDOW window ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 0 reply length 2 CARD16 minWidth 2 CARD16 minHeight 2 CARD16 maxWidth 2 CARD16 maxHeight 16 unused └─── ┌─── RRSetScreenSize 1 CARD8 major opcode 1 0x07 RandR opcode 2 5 length 4 WINDOW window 2 CARD16 width 2 CARD16 height 4 CARD32 width in millimeters 4 CARD32 height in millimeters └─── ┌─── RRGetScreenResources 1 CARD8 major opcode 1 0x08 RandR opcode 2 2 length 4 WINDOW window ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 c+o+10m+(b+p)/4 reply length 4 TIMESTAMP timestamp 4 TIMESTAMP config-timestamp 2 c number of CRTCs 2 o number of outputs 2 m number of modeinfos 2 b total bytes in mode names 10 unused 4c LISTofCRTC crtcs 4o LISTofOUTPUT outputs 40m LISTofMODEINFO modeinfos b STRING8 mode names p unused, p=pad(b) └─── ┌─── RRGetOutputInfo 1 CARD8 major opcode 1 0x09 RandR opcode 2 3 length 4 OUTPUT output 4 TIMESTAMP config-timestamp ▶ 1 1 Reply 1 RRCONFIGSTATUS status 2 CARD16 sequence number 4 c+m+(n+p)/4 reply length 4 TIMESTAMP timestamp 4 CRTC current connected crtc 1 CONNECTION connection 1 SUBPIXELORDER subpixel-order 2 c number of CRTCs 2 m number of modes 2 n length of name 8 unused 4c LISTofCRTC crtcs 4m LISTofMODE modes n STRING8 name p unused, p=pad(n) └─── ┌─── RRListOutputProperties 1 CARD8 major opcode 1 0x09 RandR opcode 2 3 length 4 OUTPUT output ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 n reply length 2 n number of ATOMs in atoms 22 unused 4n LISTofATOM atoms └─── ┌─── RRChangeOutputProperty 1 CARD8 major opcode 1 RandR opcode 2 6+(n+p)/4 request length 4 OUTPUT output 4 ATOM property 4 ATOM type 1 CARD8 format 1 mode 0 Replace 1 Prepend 2 Append 2 unused 4 CARD32 length of data in format units (= n for format = 8) (= n/2 for format = 16) (= n/4 for format = 32) n LISTofBYTE data (n is a multiple of 2 for format = 16) (n is a multiple of 4 for format = 32) p unused, p=pad(n) └─── ┌─── RRDeleteOutputProperty 1 CARD8 major opcode 1 RandR opcode 2 3 request length 4 OUTPUT output 4 ATOM property └─── ┌─── RRGetOutputProperty 1 CARD8 major opcode 1 RandR opcode 2 7 request length 4 OUTPUT output 4 ATOM property 4 ATOM type 0 AnyPropertyType 4 CARD32 long-offset 4 CARD32 long-length 1 BOOL delete 3 unused ▶ 1 1 Reply 1 CARD8 format 2 CARD16 sequence number 4 (n+p)/4 reply length 4 ATOM type 0 None 4 CARD32 bytes-after 4 CARD32 length of value in format units (= 0 for format = 0) (= n for format = 8) (= n/2 for format = 16) (= n/4 for format = 32) 12 unused n LISTofBYTE value (n is zero for format = 0) (n is a multiple of 2 for format = 16) (n is a multiple of 4 for format = 32) p unused, p=pad(n) └─── ┌─── RRCreateMode 1 CARD8 major opcode 1 0x0a RandR opcode 2 12+(n+p)/4 length 4 WINDOW window 40 MODEINFO mode n STRING8 mode name p unused, p=pad(n) ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 0 reply length 4 MODE mode 20 unused └─── ┌─── RRDestroyMode 1 CARD8 major opcode 1 0x0b RandR opcode 2 2 length 4 MODE mode └─── ┌─── RRAddOutputMode 1 CARD8 major opcode 1 0x0c RandR opcode 2 3 length 4 OUTPUT output 4 MODE mode └─── ┌─── RRDeleteOutputMode 1 CARD8 major opcode 1 0x0d RandR opcode 2 3 length 4 OUTPUT output 4 MODE mode └─── ┌─── RRGetCrtcInfo 1 CARD8 major opcode 1 0x0e RandR opcode 2 3 length 4 CRTC crtc 4 TIMESTAMP config-timestamp ▶ 1 1 Reply 1 RRCONFIGSTATUS status 2 CARD16 sequence number 4 o+p reply length 2 INT16 x 2 INT16 y 2 CARD16 width 2 CARD16 height 4 MODE mode 2 ROTATION current rotation and reflection 2 ROTATION set of possible rotations 2 o number of outputs 2 p number of possible outputs 4 unused 4o LISTofOUTPUT outputs 4p LISTofOUTPUT possible outputs └─── ┌─── RRSetCrtcConfig 1 CARD8 major opcode 1 0x0f RandR opcode 2 7+n length 4 CRTC crtc 4 TIMESTAMP timestamp 4 TIMESTAMP config timestamp 2 INT16 x 2 INT16 y 4 MODE mode 2 ROTATION rotation/reflection 2 n number of outputs 4n LISTofOUTPUT outputs ▶ 1 1 Reply 1 RRCONFIGSTATUS status 2 CARD16 sequence number 4 0 reply length 4 TIMESTAMP new timestamp 1 SUBPIXELORDER subpixel order 19 unused └─── ┌─── RRGetCrtcGammaSize 1 CARD8 major opcode 1 RandR opcode 2 2 length 4 CRTC crtc ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 0 reply length 2 CARD16 size 22 unused └─── ┌─── RRGetCrtcGamma 1 CARD8 major opcode 1 RandR opcode 2 2 length 4 CRTC crtc ▶ 1 1 Reply 1 unused 2 CARD16 sequence number 4 (6n+2)/4 reply length 2 n size 20 unused 2n LISTofCARD16 red 2n LISTofCARD16 green 2n LISTofCARD16 blue └─── ┌─── RRSetCrtcGamma 1 CARD8 major opcode 1 0x0f RandR opcode 2 3+(6n+2)/4 length 4 CRTC crtc 2 n size 2 unused 2n LISTofCARD16 red 2n LISTofCARD16 green 2n LISTofCARD16 blue └─── A.3 Protocol Events ┌─── RRScreenChangeNotify 1 Base + 0 code 1 ROTATION new rotation and reflection 2 CARD16 sequence number 4 TIMESTAMP timestamp 4 TIMESTAMP configuration timestamp 4 WINDOW root window 4 WINDOW request window 2 SIZEID size ID 2 SUBPIXELORDER subpixel order defined in Render 2 CARD16 width in pixels 2 CARD16 height in pixels 2 CARD16 width in millimeters 2 CARD16 height in millimeters └─── A.3.1 Protocol Events added with version 1.2 ┌─── RROutputChangeNotify 1 Base + 1 code 1 0 sub-code 2 CARD16 sequence number 4 TIMESTAMP timestamp 4 TIMESTAMP configuration timestamp 4 WINDOW request window 4 OUTPUT output affected 4 CRTC crtc in use 4 MODE mode in use 2 ROTATION rotation in use 1 CONNECTION connection status 1 SUBPIXELORDER subpixel order └─── ┌─── RRCrtcChangeNotify 1 Base + 2 code 1 1 sub-code 2 CARD16 sequence number 4 TIMESTAMP timestamp 4 WINDOW request window 4 CRTC crtc affected 4 MODE mode in use 2 ROTATION new rotation and reflection 2 INT16 x 2 INT16 y 2 CARD16 width 2 CARD16 height 2 unused └─── Bibliography [RANDR] Gettys, Jim and Keith Packard, "The X Resize and Rotate Extension - RandR", Proceedings of the 2001 USENIX Annual Technical Conference, Boston, MA [RENDER] Packard, Keith, "The X Rendering Extension", work in progress, documents found in xc/specs/Render.