source: rtems-docs/bsp_howto/frame_buffer.rst @ 489740f

4.115
Last change on this file since 489740f was 489740f, checked in by Chris Johns <chrisj@…>, on 05/20/16 at 02:47:09

Set SPDX License Identifier in each source file.

  • Property mode set to 100644
File size: 8.0 KB
Line 
1.. comment SPDX-License-Identifier: CC-BY-SA-4.0
2
3Frame Buffer Driver
4###################
5
6In this chapter, we present the basic functionality implemented by a
7frame buffer driver: ``frame_buffer_initialize()``, ``frame_buffer_open()``,``frame_buffer_close()``, ``frame_buffer_read()``, ``frame_buffer_write()``
8and ``frame_buffer_control()``.
9
10Introduction
11============
12
13The purpose of the frame buffer driver is to provide an abstraction for
14graphics hardware.
15By using the frame buffer interface, an application can display graphics
16without knowing anything about the low-level details of interfacing to a
17particular graphics adapter. The parameters governing the mapping of
18memory to displayed pixels (planar or linear, bit depth, etc) is still
19implementation-specific, but device-independent methods are provided to
20determine and potentially modify these parameters.
21
22The frame buffer driver is commonly located in the ``console``
23directory of the BSP and registered by the name */dev/fb0*.
24Additional frame buffers (if available) are named */dev/fb1*,*/dev/fb2*, etc.
25
26To work with the frame buffer, the following operation sequence is used:``open()``, ``ioctls()`` to get the frame buffer info, ``read()`` and/or``write()``, and ``close()``.
27
28Driver Function Overview
29========================
30
31Initialization
32--------------
33
34The driver initialization is called once during the RTEMS initialization
35process and returns RTEMS_SUCCESSFUL when the device driver is successfully
36initialized. During the initialization, a name is assigned to the frame
37buffer device.  If the graphics hardware supports console text output,
38as is the case with the pc386 VGA hardware, initialization into graphics
39mode may be deferred until the device is ``open()`` ed.
40
41The ``frame_buffer_initialize()`` function may look like this:
42
43.. code:: c
44
45    rtems_device_driver frame_buffer_initialize(
46    rtems_device_major_number  major,
47    rtems_device_minor_number  minor,
48    void                      \*arg)
49    {
50    rtems_status_code status;
51    printk( "frame buffer driver initializing..\\n" );
52    /*
53    * Register the device
54    \*/
55    status = rtems_io_register_name("/dev/fb0", major, 0);
56    if (status != RTEMS_SUCCESSFUL)
57    {
58    printk("Error registering frame buffer device!\\n");
59    rtems_fatal_error_occurred( status );
60    }
61    /*
62    * graphics hardware initialization goes here for non-console
63    * devices
64    \*/
65    return RTEMS_SUCCESSFUL;
66    }
67
68Opening the Frame Buffer Device
69-------------------------------
70
71The ``frame_buffer_open()`` function is called whenever a frame buffer device is opened.
72If the frame buffer is registered as "/dev/fb0", the ``frame_buffer_open`` entry point
73will be called as the result of an  ``open("/dev/fb0", mode)`` in the application.
74
75Thread safety of the frame buffer driver is implementation-dependent.
76The VGA driver shown below uses a mutex to prevent multiple open()
77operations of the frame buffer device.
78
79The ``frame_buffer_open()`` function returns RTEMS_SUCCESSFUL when the device driver
80is successfully opened, and RTEMS_UNSATISFIED if the device is already open:
81.. code:: c
82
83    rtems_device_driver frame_buffer_close(
84    rtems_device_major_number  major,
85    rtems_device_minor_number  minor,
86    void                      \*arg
87    )
88    {
89    if (pthread_mutex_unlock(&mutex) == 0){
90    /* restore previous state.  for VGA this means return to text mode.
91    * leave out if graphics hardware has been initialized in
92    * frame_buffer_initialize() \*/
93    ega_hwterm();
94    printk( "FBVGA close called.\\n" );
95    return RTEMS_SUCCESSFUL;
96    }
97    return RTEMS_UNSATISFIED;
98    }
99
100In the previous example, the function ``ega_hwinit()`` takes care of
101hardware-specific initialization.
102
103Closing the Frame Buffer Device
104-------------------------------
105
106The ``frame_buffer_close()`` is invoked when the frame buffer device
107is closed.  It frees up any resources allocated in``frame_buffer_open()``, and should restore previous hardware state.
108The entry point corresponds to the device driver close entry point.
109
110Returns RTEMS_SUCCESSFUL when the device driver is successfully closed:
111.. code:: c
112
113    rtems_device_driver frame_buffer_close(
114    rtems_device_major_number  major,
115    rtems_device_minor_number  minor,
116    void                      \*arg)
117    {
118    pthread_mutex_unlock(&mutex);
119    /* TODO check mutex return value, RTEMS_UNSATISFIED if it failed.  we
120    * don't want to unconditionally call ega_hwterm()... \*/
121    /* restore previous state.  for VGA this means return to text mode.
122    * leave out if graphics hardware has been initialized in
123    * frame_buffer_initialize() \*/
124    ega_hwterm();
125    printk( "frame buffer close called.\\n" );
126    return RTEMS_SUCCESSFUL;
127    }
128
129Reading from the Frame Buffer Device
130------------------------------------
131
132The ``frame_buffer_read()`` is invoked from a ``read()`` operation
133on the frame buffer device.
134Read functions should allow normal and partial reading at the end of frame buffer memory.
135This method returns RTEMS_SUCCESSFUL when the device is successfully read from:
136.. code:: c
137
138    rtems_device_driver frame_buffer_read(
139    rtems_device_major_number  major,
140    rtems_device_minor_number  minor,
141    void                      \*arg
142    )
143    {
144    rtems_libio_rw_args_t \*rw_args = (rtems_libio_rw_args_t \*)arg;
145    rw_args->bytes_moved = ((rw_args->offset + rw_args->count) > fb_fix.smem_len ) ? (fb_fix.smem_len - rw_args->offset) : rw_args->count;
146    memcpy(rw_args->buffer, (const void \*) (fb_fix.smem_start + rw_args->offset), rw_args->bytes_moved);
147    return RTEMS_SUCCESSFUL;
148    }
149
150Writing to the Frame Buffer Device
151----------------------------------
152
153The ``frame_buffer_write()`` is invoked from a ``write()``
154operation on the frame buffer device.
155The frame buffer write function is similar to the read function, and
156should handle similar cases involving partial writes.
157
158This method returns RTEMS_SUCCESSFUL when the device is successfully
159written to:
160.. code:: c
161
162    rtems_device_driver frame_buffer_write(
163    rtems_device_major_number  major,
164    rtems_device_minor_number  minor,
165    void                      \*arg
166    )
167    {
168    rtems_libio_rw_args_t \*rw_args = (rtems_libio_rw_args_t \*)arg;
169    rw_args->bytes_moved = ((rw_args->offset + rw_args->count) > fb_fix.smem_len ) ? (fb_fix.smem_len - rw_args->offset) : rw_args->count;
170    memcpy( (void \*) (fb_fix.smem_start + rw_args->offset), rw_args->buffer, rw_args->bytes_moved);
171    return RTEMS_SUCCESSFUL;
172    }
173
174Frame Buffer IO Control
175-----------------------
176
177The frame buffer driver allows several ioctls, partially compatible with
178the Linux kernel,
179to obtain information about the hardware.
180
181All ``ioctl()`` operations on the frame buffer device invoke``frame_buffer_control()``.
182
183Ioctls supported:
184
185- ioctls to get the frame buffer screen info (fixed and variable).
186
187- ioctl to set and get palette.
188
189.. code:: c
190
191    rtems_device_driver frame_buffer_control(
192    rtems_device_major_number  major,
193    rtems_device_minor_number  minor,
194    void                      \*arg
195    )
196    {
197    rtems_libio_ioctl_args_t \*args = arg;
198    printk( "FBVGA ioctl called, cmd=%x\\n", args->command  );
199    switch( args->command ) {
200    case FBIOGET_FSCREENINFO:
201    args->ioctl_return =  get_fix_screen_info( ( struct fb_fix_screeninfo * ) args->buffer );
202    break;
203    case FBIOGET_VSCREENINFO:
204    args->ioctl_return =  get_var_screen_info( ( struct fb_var_screeninfo * ) args->buffer );
205    break;
206    case FBIOPUT_VSCREENINFO:
207    /* not implemented yet*/
208    args->ioctl_return = -1;
209    return RTEMS_UNSATISFIED;
210    case FBIOGETCMAP:
211    args->ioctl_return =  get_palette( ( struct fb_cmap * ) args->buffer );
212    break;
213    case FBIOPUTCMAP:
214    args->ioctl_return =  set_palette( ( struct fb_cmap * ) args->buffer );
215    break;
216    default:
217    args->ioctl_return = 0;
218    break;
219    }
220    return RTEMS_SUCCESSFUL;
221    }
222
223See ``rtems/fb.h`` for more information on the list of ioctls and
224data structures they work with.
225
226.. COMMENT: COPYRIGHT (c) 1988-2002.
227
228.. COMMENT: On-Line Applications Research Corporation (OAR).
229
230.. COMMENT: All rights reserved.
231
Note: See TracBrowser for help on using the repository browser.