aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/evas/src/modules/engines/psl1ght/rsxutil.c
diff options
context:
space:
mode:
Diffstat (limited to 'libraries/evas/src/modules/engines/psl1ght/rsxutil.c')
-rw-r--r--libraries/evas/src/modules/engines/psl1ght/rsxutil.c275
1 files changed, 275 insertions, 0 deletions
diff --git a/libraries/evas/src/modules/engines/psl1ght/rsxutil.c b/libraries/evas/src/modules/engines/psl1ght/rsxutil.c
new file mode 100644
index 0000000..7567a8c
--- /dev/null
+++ b/libraries/evas/src/modules/engines/psl1ght/rsxutil.c
@@ -0,0 +1,275 @@
1/*
2 * This software is distributed under the terms of the MIT License
3 */
4
5#include <ppu-lv2.h>
6#include <stdio.h>
7#include <malloc.h>
8#include <string.h>
9#include <unistd.h>
10#include <sysutil/video.h>
11#include <rsx/gcm_sys.h>
12#include <rsx/rsx.h>
13#include <io/pad.h>
14#include <time.h>
15#include <cairo/cairo.h>
16#include <math.h>
17
18#include "rsxutil.h"
19
20#define GCM_LABEL_INDEX 255
21
22static void
23waitRSXIdle(gcmContextData *context);
24
25static int flipped = FALSE;
26
27void
28waitFlip()
29{
30 if (flipped)
31 {
32 while (gcmGetFlipStatus () != 0)
33 usleep (200); /* Sleep, to not stress the cpu. */
34 gcmResetFlipStatus ();
35 flipped = FALSE;
36 }
37}
38
39int
40flipBuffer(gcmContextData *context, s32 buffer)
41{
42 if (gcmSetFlip (context, buffer) == 0)
43 {
44 rsxFlushBuffer (context);
45 // Prevent the RSX from continuing until the flip has finished.
46 gcmSetWaitFlip (context);
47
48 flipped = TRUE;
49 return TRUE;
50 }
51 return FALSE;
52}
53
54int
55makeBuffer(rsxBuffer *buffer, u16 width, u16 height, int id)
56{
57 int depth = sizeof(u32);
58 int pitch = depth * width;
59 int size = depth * width * height;
60
61 buffer->ptr = (uint32_t *)rsxMemalign (64, size);
62
63 if (buffer->ptr == NULL)
64 goto error;
65
66 if (rsxAddressToOffset (buffer->ptr, &buffer->offset) != 0)
67 goto error;
68
69 /* Register the display buffer with the RSX */
70 if (gcmSetDisplayBuffer (id, buffer->offset, pitch, width, height) != 0)
71 goto error;
72
73 buffer->width = width;
74 buffer->height = height;
75 buffer->id = id;
76
77 return TRUE;
78
79error:
80 if (buffer->ptr != NULL)
81 rsxFree (buffer->ptr);
82
83 return FALSE;
84}
85
86int
87copyBuffer(gcmContextData *context, rsxBuffer *source, rsxBuffer *destination)
88{
89 rsxSetTransferData(context, GCM_TRANSFER_LOCAL_TO_LOCAL,
90 destination->offset,
91 destination->width * sizeof(u32),
92 source->offset,
93 source->width * sizeof(u32),
94 source->width * sizeof(u32),
95 source->height);
96}
97
98int
99getResolution(u16 *width, u16 *height)
100{
101 videoState state;
102 videoResolution resolution;
103
104 /* Get the state of the display */
105 if (videoGetState (0, 0, &state) == 0 &&
106 videoGetResolution (state.displayMode.resolution, &resolution) == 0)
107 {
108 if (width)
109 *width = resolution.width;
110 if (height)
111 *height = resolution.height;
112
113 return TRUE;
114 }
115 return FALSE;
116}
117
118static u8
119getPreferredResolution(u16 width, u16 height)
120{
121 videoDeviceInfo info;
122 videoResolution res;
123 int area = width * height;
124 int mode_area;
125 int min_area_diff = abs (area - (720 * 480));
126 int area_diff;
127 u8 resolution = VIDEO_RESOLUTION_480;
128 int i;
129
130 videoGetDeviceInfo(0, 0, &info);
131
132 for (i = 0; i < info.availableModeCount; i++) {
133 videoGetResolution (info.availableModes[i].resolution, &res);
134 mode_area = res.width * res.height;
135 area_diff = abs (area - mode_area);
136 if (area_diff < min_area_diff)
137 {
138 min_area_diff = area_diff;
139 resolution = info.availableModes[i].resolution;
140 }
141 }
142
143 return resolution;
144}
145
146int
147setResolution(gcmContextData *context, u16 *width, u16 *height)
148{
149 videoState state;
150 videoConfiguration vconfig;
151 videoResolution res;
152 u8 resolution;
153
154 resolution = getPreferredResolution (*width, *height);
155
156 /* Get the state of the display */
157 if (videoGetState (0, 0, &state) != 0)
158 return FALSE;
159
160 /* Make sure display is enabled */
161 if (state.state != 0)
162 return FALSE;
163
164 if (videoGetResolution (resolution, &res) != 0)
165 return FALSE;
166
167 /* Configure the buffer format to xRGB */
168 memset (&vconfig, 0, sizeof(videoConfiguration));
169 vconfig.resolution = resolution;
170 vconfig.format = VIDEO_BUFFER_FORMAT_XRGB;
171 vconfig.pitch = res.width * sizeof(u32);
172 vconfig.aspect = VIDEO_ASPECT_AUTO;
173
174 flushRSX(context);
175
176 if (videoConfigure (0, &vconfig, NULL, 0) != 0)
177 return FALSE;
178
179 *width = res.width;
180 *height = res.height;
181
182 return TRUE;
183}
184
185gcmContextData *
186initScreen(void *host_addr, u32 size)
187{
188 gcmContextData *context = NULL; /* Context to keep track of the RSX buffer. */
189 videoState state;
190 videoConfiguration vconfig;
191 videoResolution res; /* Screen Resolution */
192
193 /* Initilise Reality, which sets up the command buffer and shared IO memory */
194 context = rsxInit (CB_SIZE, size, host_addr);
195 if (context == NULL)
196 goto error;
197
198 /* Get the state of the display */
199 if (videoGetState (0, 0, &state) != 0)
200 goto error;
201
202 /* Make sure display is enabled */
203 if (state.state != 0)
204 goto error;
205
206 /* Get the current resolution */
207 if (videoGetResolution (state.displayMode.resolution, &res) != 0)
208 goto error;
209
210 /* Configure the buffer format to xRGB */
211 memset (&vconfig, 0, sizeof(videoConfiguration));
212 vconfig.resolution = state.displayMode.resolution;
213 vconfig.format = VIDEO_BUFFER_FORMAT_XRGB;
214 vconfig.pitch = res.width * sizeof(u32);
215 vconfig.aspect = state.displayMode.aspect;
216
217 flushRSX(context);
218
219 if (videoConfigure (0, &vconfig, NULL, 0) != 0)
220 goto error;
221
222 if (videoGetState (0, 0, &state) != 0)
223 goto error;
224
225 gcmSetFlipMode (GCM_FLIP_VSYNC); // Wait for VSYNC to flip
226
227 gcmResetFlipStatus();
228
229 return context;
230
231error:
232 if (context)
233 rsxFinish (context, 0);
234
235 return NULL;
236}
237
238void
239freeScreen(gcmContextData *context)
240{
241 rsxFinish (context, 0);
242}
243
244static void
245waitFinish(gcmContextData *context, u32 sLabelVal)
246{
247 rsxSetWriteBackendLabel (context, GCM_LABEL_INDEX, sLabelVal);
248
249 rsxFlushBuffer (context);
250
251 while (*(vu32 *)gcmGetLabelAddress (GCM_LABEL_INDEX) != sLabelVal)
252 usleep(30);
253}
254
255static void
256waitRSXIdle(gcmContextData *context)
257{
258 static u32 sLabelVal = 1;
259
260 rsxSetWriteBackendLabel (context, GCM_LABEL_INDEX, sLabelVal);
261 rsxSetWaitLabel (context, GCM_LABEL_INDEX, sLabelVal);
262
263 sLabelVal++;
264
265 waitFinish(context, sLabelVal++);
266}
267
268void
269flushRSX(gcmContextData *context)
270{
271 if (flipped)
272 waitFlip ();
273 waitRSXIdle(context);
274}
275