source: rtems/c/src/lib/libbsp/arm/raspberrypi/misc/vc.c @ a48c052

5
Last change on this file since a48c052 was a48c052, checked in by Pavel Pisa <pisa@…>, on Jul 15, 2016 at 2:21:12 PM

arm/raspberrypi: cache manager can be used for mailbox synchronization now. Remove workarounds.

Signed-off-by: Pavel Pisa <pisa@…>

  • Property mode set to 100644
File size: 11.5 KB
Line 
1/**
2 * @file
3 *
4 * @ingroup raspberrypi_vc
5 *
6 * @brief video core support.
7 *
8 */
9
10/*
11 * Copyright (c) 2015 Yang Qiao
12 *
13 *  The license and distribution terms for this file may be
14 *  found in the file LICENSE in this distribution or at
15 *
16 *  http://www.rtems.org/license/LICENSE
17 *
18 */
19#include <pthread.h>
20
21#include <bsp.h>
22#include <bsp/raspberrypi.h>
23#include <bsp/mailbox.h>
24#include <bsp/vc.h>
25#include <libcpu/arm-cp15.h>
26#include "vc_defines.h"
27
28#if ( RPI_L2_CACHE_ENABLE == 1 )
29  #define BCM2835_VC_MEMORY_MAPPING 0x40000000
30#else
31  #define BCM2835_VC_MEMORY_MAPPING 0xC0000000
32#endif
33
34static inline bool bcm2835_mailbox_buffer_suceeded(
35  const bcm2835_mbox_buf_hdr *hdr )
36{
37  RTEMS_COMPILER_MEMORY_BARRIER();
38  return ( hdr->buf_code == BCM2835_MBOX_BUF_CODE_REQUEST_SUCCEED );
39}
40
41static inline int bcm2835_mailbox_send_read_buffer( void *buf )
42{
43  raspberrypi_mailbox_write( BCM2835_MBOX_CHANNEL_PROP_AVC,
44    (unsigned int) buf + BCM2835_VC_MEMORY_MAPPING );
45  raspberrypi_mailbox_read( BCM2835_MBOX_CHANNEL_PROP_AVC );
46  return 0;
47}
48
49/*
50 * When cache is enabled then content of buffer exchanged
51 * with VideoCore has to be propagated through ARM11/Cortex-A7
52 * caches
53 */
54static inline void bcm2835_mailbox_buffer_flush_and_invalidate(
55  void  *buf,
56  size_t size
57)
58{
59  rtems_cache_flush_multiple_data_lines( buf, size );
60  rtems_cache_invalidate_multiple_data_lines( buf, size );
61}
62
63#define BCM2835_MBOX_VAL_LENGTH_MASK( _val_len ) \
64  ( _val_len & ( ~BCM2835_MBOX_TAG_VAL_LEN_RESPONSE ) )
65
66int bcm2835_mailbox_get_display_size(
67  bcm2835_get_display_size_entries *_entries )
68{
69  struct {
70    bcm2835_mbox_buf_hdr hdr;
71    bcm2835_mbox_tag_display_size get_display_size;
72    uint32_t end_tag;
73  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
74  BCM2835_MBOX_INIT_BUF( &buffer );
75  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_display_size,
76    BCM2835_MAILBOX_TAG_GET_DISPLAY_SIZE );
77  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
78
79  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
80    return -1;
81
82  _entries->width = buffer.get_display_size.body.resp.width;
83  _entries->height = buffer.get_display_size.body.resp.height;
84
85  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
86    return -2;
87
88  return 0;
89}
90
91int bcm2835_mailbox_init_frame_buffer(
92  bcm2835_init_frame_buffer_entries *_entries )
93{
94  struct {
95    bcm2835_mbox_buf_hdr hdr;
96    bcm2835_mbox_tag_display_size set_display_size;
97    bcm2835_mbox_tag_virtual_size set_virtual_size;
98    bcm2835_mbox_tag_depth set_depth;
99    bcm2835_mbox_tag_pixel_order set_pixel_order;
100    bcm2835_mbox_tag_alpha_mode set_alpha_mode;
101    bcm2835_mbox_tag_virtual_offset set_virtual_offset;
102    bcm2835_mbox_tag_overscan set_overscan;
103    bcm2835_mbox_tag_allocate_buffer allocate_buffer;
104    bcm2835_mbox_tag_get_pitch get_pitch;
105    uint32_t end_tag;
106  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
107  BCM2835_MBOX_INIT_BUF( &buffer );
108  BCM2835_MBOX_INIT_TAG( &buffer.set_display_size,
109    BCM2835_MAILBOX_TAG_SET_DISPLAY_SIZE );
110  buffer.set_display_size.body.req.width = _entries->xres;
111  buffer.set_display_size.body.req.height = _entries->yres;
112  BCM2835_MBOX_INIT_TAG( &buffer.set_virtual_size,
113    BCM2835_MAILBOX_TAG_SET_VIRTUAL_SIZE );
114  buffer.set_virtual_size.body.req.vwidth = _entries->xvirt;
115  buffer.set_virtual_size.body.req.vheight = _entries->yvirt;
116  BCM2835_MBOX_INIT_TAG( &buffer.set_depth,
117    BCM2835_MAILBOX_TAG_SET_DEPTH );
118  buffer.set_depth.body.req.depth = _entries->depth;
119  BCM2835_MBOX_INIT_TAG( &buffer.set_pixel_order,
120    BCM2835_MAILBOX_TAG_SET_PIXEL_ORDER );
121  buffer.set_pixel_order.body.req.pixel_order = _entries->pixel_order;
122  BCM2835_MBOX_INIT_TAG( &buffer.set_alpha_mode,
123    BCM2835_MAILBOX_TAG_SET_ALPHA_MODE );
124  buffer.set_alpha_mode.body.req.alpha_mode = _entries->alpha_mode;
125  BCM2835_MBOX_INIT_TAG( &buffer.set_virtual_offset,
126    BCM2835_MAILBOX_TAG_SET_VIRTUAL_OFFSET );
127  buffer.set_virtual_offset.body.req.voffset_x = _entries->voffset_x;
128  buffer.set_virtual_offset.body.req.voffset_x = _entries->voffset_y;
129  BCM2835_MBOX_INIT_TAG( &buffer.set_overscan,
130    BCM2835_MAILBOX_TAG_SET_OVERSCAN );
131  buffer.set_overscan.body.req.overscan_top = _entries->overscan_top;
132  buffer.set_overscan.body.req.overscan_bottom = _entries->overscan_bottom;
133  buffer.set_overscan.body.req.overscan_left = _entries->overscan_left;
134  buffer.set_overscan.body.req.overscan_right = _entries->overscan_right;
135  BCM2835_MBOX_INIT_TAG( &buffer.allocate_buffer,
136    BCM2835_MAILBOX_TAG_ALLOCATE_BUFFER );
137  buffer.allocate_buffer.body.req.align = 0x100;
138  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_pitch,
139    BCM2835_MAILBOX_TAG_GET_PITCH );
140  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
141
142  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
143    return -1;
144
145  _entries->xres = buffer.set_display_size.body.resp.width;
146  _entries->yres = buffer.set_display_size.body.resp.height;
147  _entries->xvirt = buffer.set_virtual_size.body.resp.vwidth;
148  _entries->yvirt = buffer.set_virtual_size.body.resp.vheight;
149  _entries->depth = buffer.set_depth.body.resp.depth;
150#if ( BSP_IS_RPI2 == 1 )
151  _entries->base = buffer.allocate_buffer.body.resp.base;
152#else
153  _entries->base = buffer.allocate_buffer.body.resp.base -
154                   BCM2835_VC_MEMORY_MAPPING;
155#endif
156  _entries->size = buffer.allocate_buffer.body.resp.size;
157  _entries->pixel_order = buffer.set_pixel_order.body.resp.pixel_order;
158  _entries->alpha_mode = buffer.set_alpha_mode.body.resp.alpha_mode;
159  _entries->voffset_x = buffer.set_virtual_offset.body.resp.voffset_x;
160  _entries->voffset_y = buffer.set_virtual_offset.body.resp.voffset_y;
161  _entries->overscan_left = buffer.set_overscan.body.resp.overscan_left;
162  _entries->overscan_right = buffer.set_overscan.body.resp.overscan_right;
163  _entries->overscan_top = buffer.set_overscan.body.resp.overscan_top;
164  _entries->overscan_bottom = buffer.set_overscan.body.resp.overscan_bottom;
165
166  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
167    return -2;
168
169  return 0;
170}
171
172int bcm2835_mailbox_get_pitch( bcm2835_get_pitch_entries *_entries )
173{
174  struct {
175    bcm2835_mbox_buf_hdr hdr;
176    bcm2835_mbox_tag_get_pitch get_pitch;
177    uint32_t end_tag;
178  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
179  BCM2835_MBOX_INIT_BUF( &buffer );
180  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_pitch,
181    BCM2835_MAILBOX_TAG_GET_PITCH );
182  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
183
184  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
185    return -1;
186
187  _entries->pitch = buffer.get_pitch.body.resp.pitch;
188
189  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
190    return -2;
191
192  return 0;
193}
194
195int bcm2835_mailbox_get_cmdline( bcm2835_get_cmdline_entries *_entries )
196{
197  int i;
198
199  struct {
200    bcm2835_mbox_buf_hdr hdr;
201    bcm2835_mbox_tag_get_cmd_line get_cmd_line;
202    uint32_t end_tag;
203  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
204  BCM2835_MBOX_INIT_BUF( &buffer );
205  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_cmd_line,
206    BCM2835_MAILBOX_TAG_GET_CMD_LINE );
207  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
208
209  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
210    return -1;
211
212  for ( i = 0;
213        i < BCM2835_MBOX_VAL_LENGTH_MASK( buffer.get_cmd_line.tag_hdr.val_len );
214        ++i ) {
215    _entries->cmdline[ i ] = buffer.get_cmd_line.body.resp.cmdline[ i ];
216  }
217
218  _entries->cmdline[ i ] = '\0';
219
220  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
221    return -2;
222
223  return 0;
224}
225
226int bcm2835_mailbox_set_power_state( bcm2835_set_power_state_entries *_entries )
227{
228  struct {
229    bcm2835_mbox_buf_hdr hdr;
230    bcm2835_mbox_tag_power_state set_power_state;
231    uint32_t end_tag;
232  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
233  BCM2835_MBOX_INIT_BUF( &buffer );
234  BCM2835_MBOX_INIT_TAG( &buffer.set_power_state,
235    BCM2835_MAILBOX_TAG_SET_POWER_STATE );
236  buffer.set_power_state.body.req.dev_id = _entries->dev_id;
237  buffer.set_power_state.body.req.state = _entries->state;
238  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
239
240  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
241    return -1;
242
243  _entries->dev_id = buffer.set_power_state.body.resp.dev_id;
244  _entries->state = buffer.set_power_state.body.resp.state;
245
246  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
247    return -2;
248
249  return 0;
250}
251
252int bcm2835_mailbox_get_arm_memory( bcm2835_get_arm_memory_entries *_entries )
253{
254  struct {
255    bcm2835_mbox_buf_hdr hdr;
256    bcm2835_mbox_tag_get_arm_memory get_arm_memory;
257    uint32_t end_tag;
258  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
259  BCM2835_MBOX_INIT_BUF( &buffer );
260  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_arm_memory,
261    BCM2835_MAILBOX_TAG_GET_ARM_MEMORY );
262  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
263
264  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
265    return -1;
266
267  _entries->base = buffer.get_arm_memory.body.resp.base;
268  _entries->size = buffer.get_arm_memory.body.resp.size;
269
270  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
271    return -2;
272
273  return 0;
274}
275
276int bcm2835_mailbox_get_vc_memory( bcm2835_get_vc_memory_entries *_entries )
277{
278  struct {
279    bcm2835_mbox_buf_hdr hdr;
280    bcm2835_mbox_tag_get_vc_memory get_vc_memory;
281    uint32_t end_tag;
282  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
283  BCM2835_MBOX_INIT_BUF( &buffer );
284  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_vc_memory,
285    BCM2835_MAILBOX_TAG_GET_VC_MEMORY );
286  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
287
288  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
289    return -1;
290
291  _entries->base = buffer.get_vc_memory.body.resp.base;
292  _entries->size = buffer.get_vc_memory.body.resp.size;
293
294  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
295    return -2;
296
297  return 0;
298}
299
300int bcm2835_mailbox_get_firmware_revision(
301  bcm2835_mailbox_get_fw_rev_entries *_entries )
302{
303  struct {
304    bcm2835_mbox_buf_hdr hdr;
305    bcm2835_mbox_tag_get_fw_rev get_fw_rev;
306    uint32_t end_tag;
307  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
308  BCM2835_MBOX_INIT_BUF( &buffer );
309  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_fw_rev,
310    BCM2835_MAILBOX_TAG_FIRMWARE_REVISION );
311  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
312
313  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
314    return -1;
315
316  _entries->fw_rev = buffer.get_fw_rev.body.resp.rev;
317
318  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
319    return -2;
320
321  return 0;
322}
323
324int bcm2835_mailbox_get_board_model( bcm2835_get_board_spec_entries *_entries )
325{
326  struct {
327    bcm2835_mbox_buf_hdr hdr;
328    bcm2835_mbox_tag_get_board_spec get_board_model;
329    uint32_t end_tag;
330  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
331  BCM2835_MBOX_INIT_BUF( &buffer );
332  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_board_model,
333    BCM2835_MAILBOX_TAG_GET_BOARD_MODEL );
334  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
335
336  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
337    return -1;
338
339  _entries->spec = buffer.get_board_model.body.resp.spec;
340
341  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
342    return -2;
343
344  return 0;
345}
346
347int bcm2835_mailbox_get_board_revision(
348  bcm2835_get_board_spec_entries *_entries )
349{
350  struct {
351    bcm2835_mbox_buf_hdr hdr;
352    bcm2835_mbox_tag_get_board_spec get_board_revision;
353    uint32_t end_tag;
354  } buffer BCM2835_MBOX_BUF_ALIGN_ATTRIBUTE;
355  BCM2835_MBOX_INIT_BUF( &buffer );
356  BCM2835_MBOX_INIT_TAG_NO_REQ( &buffer.get_board_revision,
357    BCM2835_MAILBOX_TAG_GET_BOARD_VERSION );
358  bcm2835_mailbox_buffer_flush_and_invalidate( &buffer, sizeof( &buffer ) );
359
360  if ( bcm2835_mailbox_send_read_buffer( &buffer ) )
361    return -1;
362
363  _entries->spec = buffer.get_board_revision.body.resp.spec;
364
365  if ( !bcm2835_mailbox_buffer_suceeded( &buffer.hdr ) )
366    return -2;
367
368  return 0;
369}
Note: See TracBrowser for help on using the repository browser.