blob: 87c8527d5a8827e85db72a5d73e8bc4c2420ea0a [file] [log] [blame]
codeworkx62f02ba2012-05-20 12:00:36 +02001/*
2**
3** Copyright 2009 Samsung Electronics Co, Ltd.
4**
5** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
8**
9** http://www.apache.org/licenses/LICENSE-2.0
10**
11** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
15** limitations under the License.
16**
17**
18*/
19
20#define LOG_NDEBUG 0
21#define LOG_TAG "FimgExynos5"
22#include <utils/Log.h>
23
24#include "FimgExynos5.h"
25
26namespace android
27{
28Mutex FimgV4x::m_instanceLock;
29int FimgV4x::m_curFimgV4xIndex = 0;
30int FimgV4x::m_numOfInstance = 0;
31FimgApi * FimgV4x::m_ptrFimgApiList[NUMBER_FIMG_LIST] = {NULL, };
32
33//---------------------------------------------------------------------------//
34
35FimgV4x::FimgV4x()
36 : m_g2dFd(0),
37 m_g2dVirtAddr(NULL),
38 m_g2dSize(0),
39 m_g2dSrcVirtAddr(NULL),
40 m_g2dSrcSize(0),
41 m_g2dDstVirtAddr(NULL),
42 m_g2dDstSize(0)
43{
44 m_lock = new Mutex(Mutex::SHARED, "FimgV4x");
45}
46
47FimgV4x::~FimgV4x()
48{
49 delete m_lock;
50}
51
52FimgApi *FimgV4x::CreateInstance()
53{
54 Mutex::Autolock autolock(m_instanceLock);
55
56 FimgApi *ptrFimg = NULL;
57
58 for(int i = m_curFimgV4xIndex; i < NUMBER_FIMG_LIST; i++) {
59 if (m_ptrFimgApiList[i] == NULL)
60 m_ptrFimgApiList[i] = new FimgV4x;
61
62 if (m_ptrFimgApiList[i]->FlagCreate() == false) {
63 if (m_ptrFimgApiList[i]->Create() == false) {
64 PRINT("%s::Create(%d) fail\n", __func__, i);
65 goto CreateInstance_End;
66 }
67 else
68 m_numOfInstance++;
69 }
70
71 if (i < NUMBER_FIMG_LIST - 1)
72 m_curFimgV4xIndex = i + 1;
73 else
74 m_curFimgV4xIndex = 0;
75
76 ptrFimg = m_ptrFimgApiList[i];
77 goto CreateInstance_End;
78 }
79
80CreateInstance_End :
81
82 return ptrFimg;
83}
84
85void FimgV4x::DestroyInstance(FimgApi * ptrFimgApi)
86{
87 Mutex::Autolock autolock(m_instanceLock);
88
89 for(int i = 0; i < NUMBER_FIMG_LIST; i++) {
90 if (m_ptrFimgApiList[i] != NULL && m_ptrFimgApiList[i] == ptrFimgApi) {
91 if (m_ptrFimgApiList[i]->FlagCreate() == true && m_ptrFimgApiList[i]->Destroy() == false) {
92 PRINT("%s::Destroy() fail\n", __func__);
93 } else {
94 FimgV4x * tempFimgV4x = (FimgV4x *)m_ptrFimgApiList[i];
95 delete tempFimgV4x;
96 m_ptrFimgApiList[i] = NULL;
97
98 m_numOfInstance--;
99 }
100
101 break;
102 }
103 }
104}
105
106void FimgV4x::DestroyAllInstance(void)
107{
108 Mutex::Autolock autolock(m_instanceLock);
109
110 for(int i = 0; i < NUMBER_FIMG_LIST; i++) {
111 if (m_ptrFimgApiList[i] != NULL) {
112 if (m_ptrFimgApiList[i]->FlagCreate() == true
113 && m_ptrFimgApiList[i]->Destroy() == false) {
114 PRINT("%s::Destroy() fail\n", __func__);
115 } else {
116 FimgV4x * tempFimgV4x = (FimgV4x *)m_ptrFimgApiList[i];
117 delete tempFimgV4x;
118 m_ptrFimgApiList[i] = NULL;
119 }
120 }
121 }
122}
123
124bool FimgV4x::t_Create(void)
125{
126 bool ret = true;
127
128 if (m_CreateG2D() == false) {
129 PRINT("%s::m_CreateG2D() fail \n", __func__);
130
131 if (m_DestroyG2D() == false)
132 PRINT("%s::m_DestroyG2D() fail \n", __func__);
133
134 ret = false;
135 }
136
137 return ret;
138}
139
140bool FimgV4x::t_Destroy(void)
141{
142 bool ret = true;
143
144 if (m_DestroyG2D() == false) {
145 PRINT("%s::m_DestroyG2D() fail \n", __func__);
146 ret = false;
147 }
148
149 return ret;
150}
151
152bool FimgV4x::t_Stretch(struct fimg2d_blit *cmd)
153{
154#ifdef CHECK_FIMGV4x_PERFORMANCE
155#define NUM_OF_STEP (10)
156 StopWatch stopWatch("CHECK_FIMGV4x_PERFORMANCE");
157 const char *stopWatchName[NUM_OF_STEP];
158 nsecs_t stopWatchTime[NUM_OF_STEP];
159 int stopWatchIndex = 0;
160#endif // CHECK_FIMGV4x_PERFORMANCE
161
162 if (m_DoG2D(cmd) == false) {
163 goto STRETCH_FAIL;
164 }
165
166#ifdef G2D_NONE_BLOCKING_MODE
167 if (m_PollG2D(&m_g2dPoll) == false)
168 {
169 PRINT("%s::m_PollG2D() fail\n", __func__);
170 goto STRETCH_FAIL;
171 }
172#endif
173
174 #ifdef CHECK_FIMGV4x_PERFORMANCE
175 m_PrintFimgV4xPerformance(src, dst, stopWatchIndex, stopWatchName, stopWatchTime);
176 #endif // CHECK_FIMGV4x_PERFORMANCE
177
178 return true;
179
180STRETCH_FAIL:
181 return false;
182
183}
184
185bool FimgV4x::t_Sync(void)
186{
187 if (m_PollG2D(&m_g2dPoll) == false)
188 {
189 PRINT("%s::m_PollG2D() fail\n", __func__);
190 goto SYNC_FAIL;
191 }
192 return true;
193
194SYNC_FAIL:
195 return false;
196
197}
198
199bool FimgV4x::t_Lock(void)
200{
201 m_lock->lock();
202 return true;
203}
204
205bool FimgV4x::t_UnLock(void)
206{
207 m_lock->unlock();
208 return true;
209}
210
211bool FimgV4x::m_CreateG2D(void)
212{
213 void * mmap_base;
214
215 if (m_g2dFd != 0) {
216 PRINT("%s::m_g2dFd(%d) is not 0 fail\n", __func__, m_g2dFd);
217 return false;
218 }
219
220#ifdef G2D_NONE_BLOCKING_MODE
221 m_g2dFd = open(SEC_G2D_DEV_NAME, O_RDWR | O_NONBLOCK);
222#else
223 m_g2dFd = open(SEC_G2D_DEV_NAME, O_RDWR);
224#endif
225 if (m_g2dFd < 0) {
226 PRINT("%s::open(%s) fail(%s)\n", __func__, SEC_G2D_DEV_NAME, strerror(errno));
227 m_g2dFd = 0;
228 return false;
229 }
230
231 memset(&m_g2dPoll, 0, sizeof(m_g2dPoll));
232 m_g2dPoll.fd = m_g2dFd;
233 m_g2dPoll.events = POLLOUT | POLLERR;
234
235 return true;
236}
237
238bool FimgV4x::m_DestroyG2D(void)
239{
240 if (m_g2dVirtAddr != NULL) {
241 munmap(m_g2dVirtAddr, m_g2dSize);
242 m_g2dVirtAddr = NULL;
243 m_g2dSize = 0;
244 }
245
246 if (0 < m_g2dFd) {
247 close(m_g2dFd);
248 }
249 m_g2dFd = 0;
250
251 return true;
252}
253
254bool FimgV4x::m_DoG2D(struct fimg2d_blit *cmd)
255{
256
257 if (ioctl(m_g2dFd, FIMG2D_BITBLT_BLIT, cmd) < 0)
258 return false;
259
260 return true;
261}
262
263inline bool FimgV4x::m_PollG2D(struct pollfd * events)
264{
265#define G2D_POLL_TIME (1000)
266
267 int ret;
268
269 ret = poll(events, 1, G2D_POLL_TIME);
270
271 if (ret < 0) {
272 PRINT("%s::poll fail \n", __func__);
273 return false;
274 }
275 else if (ret == 0) {
276 PRINT("%s::No data in %d milli secs..\n", __func__, G2D_POLL_TIME);
277 return false;
278 }
279
280 return true;
281}
282
283//---------------------------------------------------------------------------//
284// extern function
285//---------------------------------------------------------------------------//
286extern "C" struct FimgApi * createFimgApi()
287{
288 if (fimgApiAutoFreeThread == 0)
289 fimgApiAutoFreeThread = new FimgApiAutoFreeThread();
290 else
291 fimgApiAutoFreeThread->SetOneMoreSleep();
292
293 return FimgV4x::CreateInstance();
294}
295
296extern "C" void destroyFimgApi(FimgApi * ptrFimgApi)
297{
298 // Dont' call DestroyInstance.
299}
300
301}; // namespace android