tizen 2.4 release
[kernel/linux-3.0.git] / drivers / gpu / arm / mali400 / mali / common / mali_kernel_core.c
1 /*
2  * Copyright (C) 2011-2012 ARM Limited. All rights reserved.
3  *
4  * This program is free software and is provided to you under the terms of the GNU General Public License version 2
5  * as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
6  *
7  * A copy of the licence is included with the program, and can also be obtained from Free Software
8  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
9  */
10
11 #include "mali_kernel_common.h"
12 #include "mali_session.h"
13 #include "mali_osk.h"
14 #include "mali_osk_mali.h"
15 #include "mali_ukk.h"
16 #include "mali_kernel_core.h"
17 #include "mali_memory.h"
18 #include "mali_mem_validation.h"
19 #include "mali_mmu.h"
20 #include "mali_mmu_page_directory.h"
21 #include "mali_dlbu.h"
22 #include "mali_broadcast.h"
23 #include "mali_gp.h"
24 #include "mali_pp.h"
25 #include "mali_gp_scheduler.h"
26 #include "mali_pp_scheduler.h"
27 #include "mali_group.h"
28 #include "mali_pm.h"
29 #include "mali_pmu.h"
30 #include "mali_scheduler.h"
31 #include "mali_kernel_utilization.h"
32 #include "mali_l2_cache.h"
33 #if defined(CONFIG_MALI400_PROFILING)
34 #include "mali_osk_profiling.h"
35 #endif
36 #if defined(CONFIG_MALI400_INTERNAL_PROFILING)
37 #include "mali_profiling_internal.h"
38 #endif
39
40
41 /* Mali GPU memory. Real values come from module parameter or from device specific data */
42 int mali_dedicated_mem_start = 0;
43 int mali_dedicated_mem_size = 0;
44 int mali_shared_mem_size = 0;
45
46 /* Frame buffer memory to be accessible by Mali GPU */
47 int mali_fb_start = 0;
48 int mali_fb_size = 0;
49
50 /** Start profiling from module load? */
51 int mali_boot_profiling = 0;
52
53 /** Limits for the number of PP cores behind each L2 cache. */
54 int mali_max_pp_cores_group_1 = 0xFF;
55 int mali_max_pp_cores_group_2 = 0xFF;
56
57 int mali_inited_pp_cores_group_1 = 0;
58 int mali_inited_pp_cores_group_2 = 0;
59
60 static _mali_product_id_t global_product_id = _MALI_PRODUCT_ID_UNKNOWN;
61 static u32 global_gpu_base_address = 0;
62 static u32 global_gpu_major_version = 0;
63 static u32 global_gpu_minor_version = 0;
64
65 /* MALI_SEC */
66 static u32 first_pp_offset = 0;
67
68 #define HANG_CHECK_MSECS_DEFAULT 500 /* 500 ms */
69 #define WATCHDOG_MSECS_DEFAULT 4000 /* 4 s */
70
71 /* timer related */
72 int mali_max_job_runtime = WATCHDOG_MSECS_DEFAULT;
73 int mali_hang_check_interval = HANG_CHECK_MSECS_DEFAULT;
74
75 static _mali_osk_errcode_t mali_parse_product_info(void)
76 {
77         /*
78          * Mali-200 has the PP core first, while Mali-300, Mali-400 and Mali-450 have the GP core first.
79          * Look at the version register for the first PP core in order to determine the GPU HW revision.
80          */
81
82         u32 first_pp_offset;
83         _mali_osk_resource_t first_pp_resource;
84
85         global_gpu_base_address = _mali_osk_resource_base_address();
86         if (0 == global_gpu_base_address)
87         {
88                 return _MALI_OSK_ERR_ITEM_NOT_FOUND;
89         }
90
91         /* Find out where the first PP core is located */
92         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x8000, NULL))
93         {
94                 /* Mali-300/400/450 */
95                 first_pp_offset = 0x8000;
96         }
97         else
98         {
99                 /* Mali-200 */
100                 first_pp_offset = 0x0000;
101         }
102
103         /* Find the first PP core resource (again) */
104         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + first_pp_offset, &first_pp_resource))
105         {
106                 /* Create a dummy PP object for this core so that we can read the version register */
107                 struct mali_group *group = mali_group_create(NULL, NULL, NULL);
108                 if (NULL != group)
109                 {
110                         struct mali_pp_core *pp_core = mali_pp_create(&first_pp_resource, group, MALI_FALSE);
111                         if (NULL != pp_core)
112                         {
113                                 u32 pp_version = mali_pp_core_get_version(pp_core);
114                                 mali_group_delete(group);
115
116                                 global_gpu_major_version = (pp_version >> 8) & 0xFF;
117                                 global_gpu_minor_version = pp_version & 0xFF;
118
119                                 switch (pp_version >> 16)
120                                 {
121                                         case MALI200_PP_PRODUCT_ID:
122                                                 global_product_id = _MALI_PRODUCT_ID_MALI200;
123                                                 MALI_DEBUG_PRINT(2, ("Found Mali GPU Mali-200 r%up%u\n", global_gpu_major_version, global_gpu_minor_version));
124                                                 break;
125                                         case MALI300_PP_PRODUCT_ID:
126                                                 global_product_id = _MALI_PRODUCT_ID_MALI300;
127                                                 MALI_DEBUG_PRINT(2, ("Found Mali GPU Mali-300 r%up%u\n", global_gpu_major_version, global_gpu_minor_version));
128                                                 break;
129                                         case MALI400_PP_PRODUCT_ID:
130                                                 global_product_id = _MALI_PRODUCT_ID_MALI400;
131                                                 MALI_DEBUG_PRINT(2, ("Found Mali GPU Mali-400 MP r%up%u\n", global_gpu_major_version, global_gpu_minor_version));
132                                                 break;
133                                         case MALI450_PP_PRODUCT_ID:
134                                                 global_product_id = _MALI_PRODUCT_ID_MALI450;
135                                                 MALI_DEBUG_PRINT(2, ("Found Mali GPU Mali-450 MP r%up%u\n", global_gpu_major_version, global_gpu_minor_version));
136                                                 break;
137                                         default:
138                                                 MALI_DEBUG_PRINT(2, ("Found unknown Mali GPU (r%up%u)\n", global_gpu_major_version, global_gpu_minor_version));
139                                                 return _MALI_OSK_ERR_FAULT;
140                                 }
141
142                                 return _MALI_OSK_ERR_OK;
143                         }
144                         else
145                         {
146                                 MALI_PRINT_ERROR(("Failed to create initial PP object\n"));
147                         }
148                 }
149                 else
150                 {
151                         MALI_PRINT_ERROR(("Failed to create initial group object\n"));
152                 }
153         }
154         else
155         {
156                 MALI_PRINT_ERROR(("First PP core not specified in config file\n"));
157         }
158
159         return _MALI_OSK_ERR_FAULT;
160 }
161
162
163 void mali_resource_count(u32 *pp_count, u32 *l2_count)
164 {
165         *pp_count = 0;
166         *l2_count = 0;
167
168         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x08000, NULL))
169         {
170                 ++(*pp_count);
171         }
172         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x0A000, NULL))
173         {
174                 ++(*pp_count);
175         }
176         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x0C000, NULL))
177         {
178                 ++(*pp_count);
179         }
180         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x0E000, NULL))
181         {
182                 ++(*pp_count);
183         }
184         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x28000, NULL))
185         {
186                 ++(*pp_count);
187         }
188         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2A000, NULL))
189         {
190                 ++(*pp_count);
191         }
192         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2C000, NULL))
193         {
194                 ++(*pp_count);
195         }
196         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2E000, NULL))
197         {
198                 ++(*pp_count);
199         }
200
201         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x1000, NULL))
202         {
203                 ++(*l2_count);
204         }
205         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x10000, NULL))
206         {
207                 ++(*l2_count);
208         }
209         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x11000, NULL))
210         {
211                 ++(*l2_count);
212         }
213 }
214
215 static void mali_delete_l2_cache_cores(void)
216 {
217         u32 i;
218         u32 number_of_l2_ccores = mali_l2_cache_core_get_glob_num_l2_cores();
219
220         for (i = 0; i < number_of_l2_ccores; i++)
221         {
222                 mali_l2_cache_delete(mali_l2_cache_core_get_glob_l2_core(i));
223         }
224 }
225
226 static _mali_osk_errcode_t mali_create_l2_cache_core(_mali_osk_resource_t *resource)
227 {
228         if (NULL != resource)
229         {
230                 struct mali_l2_cache_core *l2_cache;
231
232                 MALI_DEBUG_PRINT(3, ("Found L2 cache %s\n", resource->description));
233
234                 l2_cache = mali_l2_cache_create(resource);
235                 if (NULL == l2_cache)
236                 {
237                         MALI_PRINT_ERROR(("Failed to create L2 cache object\n"));
238                         return _MALI_OSK_ERR_FAULT;
239                 }
240         }
241         MALI_DEBUG_PRINT(3, ("Created L2 cache core object\n"));
242
243         return _MALI_OSK_ERR_OK;
244 }
245
246 static _mali_osk_errcode_t mali_parse_config_l2_cache(void)
247 {
248         if (_MALI_PRODUCT_ID_MALI200 == global_product_id)
249         {
250                 /* Create dummy L2 cache - nothing happens here!!! */
251                 return mali_create_l2_cache_core(NULL);
252         }
253         else if (_MALI_PRODUCT_ID_MALI300 == global_product_id || _MALI_PRODUCT_ID_MALI400 == global_product_id)
254         {
255                 _mali_osk_resource_t l2_resource;
256                 if (_MALI_OSK_ERR_OK != _mali_osk_resource_find(global_gpu_base_address + 0x1000, &l2_resource))
257                 {
258                         MALI_DEBUG_PRINT(3, ("Did not find required Mali L2 cache in config file\n"));
259                         return _MALI_OSK_ERR_FAULT;
260                 }
261
262                 return mali_create_l2_cache_core(&l2_resource);
263         }
264         else if (_MALI_PRODUCT_ID_MALI450 == global_product_id)
265         {
266                 /*
267                  * L2 for GP    at 0x10000
268                  * L2 for PP0-3 at 0x01000
269                  * L2 for PP4-7 at 0x11000 (optional)
270                  */
271
272                 _mali_osk_resource_t l2_gp_resource;
273                 _mali_osk_resource_t l2_pp_grp0_resource;
274                 _mali_osk_resource_t l2_pp_grp1_resource;
275
276                 /* Make cluster for GP's L2 */
277                 if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x10000, &l2_gp_resource))
278                 {
279                         _mali_osk_errcode_t ret;
280                         MALI_DEBUG_PRINT(3, ("Creating Mali-450 L2 cache core for GP\n"));
281                         ret = mali_create_l2_cache_core(&l2_gp_resource);
282                         if (_MALI_OSK_ERR_OK != ret)
283                         {
284                                 return ret;
285                         }
286                 }
287                 else
288                 {
289                         MALI_DEBUG_PRINT(3, ("Did not find required Mali L2 cache for GP in config file\n"));
290                         return _MALI_OSK_ERR_FAULT;
291                 }
292
293                 /* Make cluster for first PP core group */
294                 if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x1000, &l2_pp_grp0_resource))
295                 {
296                         _mali_osk_errcode_t ret;
297                         MALI_DEBUG_PRINT(3, ("Creating Mali-450 L2 cache core for PP group 0\n"));
298                         ret = mali_create_l2_cache_core(&l2_pp_grp0_resource);
299                         if (_MALI_OSK_ERR_OK != ret)
300                         {
301                                 return ret;
302                         }
303                 }
304                 else
305                 {
306                         MALI_DEBUG_PRINT(3, ("Did not find required Mali L2 cache for PP group 0 in config file\n"));
307                         return _MALI_OSK_ERR_FAULT;
308                 }
309
310                 /* Second PP core group is optional, don't fail if we don't find it */
311                 if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x11000, &l2_pp_grp1_resource))
312                 {
313                         _mali_osk_errcode_t ret;
314                         MALI_DEBUG_PRINT(3, ("Creating Mali-450 L2 cache core for PP group 1\n"));
315                         ret = mali_create_l2_cache_core(&l2_pp_grp1_resource);
316                         if (_MALI_OSK_ERR_OK != ret)
317                         {
318                                 return ret;
319                         }
320                 }
321         }
322
323         return _MALI_OSK_ERR_OK;
324 }
325
326 static _mali_osk_errcode_t mali_create_group(struct mali_l2_cache_core *cache,
327                                              _mali_osk_resource_t *resource_mmu,
328                                              _mali_osk_resource_t *resource_gp,
329                                              _mali_osk_resource_t *resource_pp)
330 {
331         struct mali_mmu_core *mmu;
332         struct mali_group *group;
333
334         MALI_DEBUG_PRINT(3, ("Starting new group for MMU %s\n", resource_mmu->description));
335
336         /* Create the group object */
337         group = mali_group_create(cache, NULL, NULL);
338         if (NULL == group)
339         {
340                 MALI_PRINT_ERROR(("Failed to create group object for MMU %s\n", resource_mmu->description));
341                 return _MALI_OSK_ERR_FAULT;
342         }
343
344         /* Create the MMU object inside group */
345         mmu = mali_mmu_create(resource_mmu, group, MALI_FALSE);
346         if (NULL == mmu)
347         {
348                 MALI_PRINT_ERROR(("Failed to create MMU object\n"));
349                 mali_group_delete(group);
350                 return _MALI_OSK_ERR_FAULT;
351         }
352
353         if (NULL != resource_gp)
354         {
355                 /* Create the GP core object inside this group */
356                 struct mali_gp_core *gp_core = mali_gp_create(resource_gp, group);
357                 if (NULL == gp_core)
358                 {
359                         /* No need to clean up now, as we will clean up everything linked in from the cluster when we fail this function */
360                         MALI_PRINT_ERROR(("Failed to create GP object\n"));
361                         mali_group_delete(group);
362                         return _MALI_OSK_ERR_FAULT;
363                 }
364         }
365
366         if (NULL != resource_pp)
367         {
368                 struct mali_pp_core *pp_core;
369
370                 /* Create the PP core object inside this group */
371                 pp_core = mali_pp_create(resource_pp, group, MALI_FALSE);
372                 if (NULL == pp_core)
373                 {
374                         /* No need to clean up now, as we will clean up everything linked in from the cluster when we fail this function */
375                         MALI_PRINT_ERROR(("Failed to create PP object\n"));
376                         mali_group_delete(group);
377                         return _MALI_OSK_ERR_FAULT;
378                 }
379         }
380
381         /* Reset group */
382         mali_group_reset(group);
383
384         return _MALI_OSK_ERR_OK;
385 }
386
387 static _mali_osk_errcode_t mali_create_virtual_group(_mali_osk_resource_t *resource_mmu_pp_bcast,
388                                                     _mali_osk_resource_t *resource_pp_bcast,
389                                                     _mali_osk_resource_t *resource_dlbu,
390                                                     _mali_osk_resource_t *resource_bcast)
391 {
392         struct mali_mmu_core *mmu_pp_bcast_core;
393         struct mali_pp_core *pp_bcast_core;
394         struct mali_dlbu_core *dlbu_core;
395         struct mali_bcast_unit *bcast_core;
396         struct mali_group *group;
397
398         MALI_DEBUG_PRINT(2, ("Starting new virtual group for MMU PP broadcast core %s\n", resource_mmu_pp_bcast->description));
399
400         /* Create the DLBU core object */
401         dlbu_core = mali_dlbu_create(resource_dlbu);
402         if (NULL == dlbu_core)
403         {
404                 MALI_PRINT_ERROR(("Failed to create DLBU object \n"));
405                 return _MALI_OSK_ERR_FAULT;
406         }
407
408         /* Create the Broadcast unit core */
409         bcast_core = mali_bcast_unit_create(resource_bcast);
410         if (NULL == bcast_core)
411         {
412                 MALI_PRINT_ERROR(("Failed to create Broadcast unit object!\n"));
413                 mali_dlbu_delete(dlbu_core);
414                 return _MALI_OSK_ERR_FAULT;
415         }
416
417         /* Create the group object */
418         group = mali_group_create(NULL, dlbu_core, bcast_core);
419         if (NULL == group)
420         {
421                 MALI_PRINT_ERROR(("Failed to create group object for MMU PP broadcast core %s\n", resource_mmu_pp_bcast->description));
422                 mali_bcast_unit_delete(bcast_core);
423                 mali_dlbu_delete(dlbu_core);
424                 return _MALI_OSK_ERR_FAULT;
425         }
426
427         /* Create the MMU object inside group */
428         mmu_pp_bcast_core = mali_mmu_create(resource_mmu_pp_bcast, group, MALI_TRUE);
429         if (NULL == mmu_pp_bcast_core)
430         {
431                 MALI_PRINT_ERROR(("Failed to create MMU PP broadcast object\n"));
432                 mali_group_delete(group);
433                 return _MALI_OSK_ERR_FAULT;
434         }
435
436         /* Create the PP core object inside this group */
437         pp_bcast_core = mali_pp_create(resource_pp_bcast, group, MALI_TRUE);
438         if (NULL == pp_bcast_core)
439         {
440                 /* No need to clean up now, as we will clean up everything linked in from the cluster when we fail this function */
441                 MALI_PRINT_ERROR(("Failed to create PP object\n"));
442                 mali_group_delete(group);
443                 return _MALI_OSK_ERR_FAULT;
444         }
445
446         return _MALI_OSK_ERR_OK;
447 }
448
449 static _mali_osk_errcode_t mali_parse_config_groups(void)
450 {
451         if (_MALI_PRODUCT_ID_MALI200 == global_product_id)
452         {
453                 _mali_osk_errcode_t err;
454                 _mali_osk_resource_t resource_gp;
455                 _mali_osk_resource_t resource_pp;
456                 _mali_osk_resource_t resource_mmu;
457
458                 MALI_DEBUG_ASSERT(1 == mali_l2_cache_core_get_glob_num_l2_cores());
459
460                 if (_MALI_OSK_ERR_OK != _mali_osk_resource_find(global_gpu_base_address + 0x02000, &resource_gp) ||
461                     _MALI_OSK_ERR_OK != _mali_osk_resource_find(global_gpu_base_address + 0x00000, &resource_pp) ||
462                     _MALI_OSK_ERR_OK != _mali_osk_resource_find(global_gpu_base_address + 0x03000, &resource_mmu))
463                 {
464                         /* Missing mandatory core(s) */
465                         return _MALI_OSK_ERR_FAULT;
466                 }
467
468                 err = mali_create_group(mali_l2_cache_core_get_glob_l2_core(0), &resource_mmu, &resource_gp, &resource_pp);
469                 if (err == _MALI_OSK_ERR_OK)
470                 {
471                         mali_inited_pp_cores_group_1++;
472                         mali_max_pp_cores_group_1 = mali_inited_pp_cores_group_1; /* always 1 */
473                         mali_max_pp_cores_group_2 = mali_inited_pp_cores_group_2; /* always zero */
474                 }
475
476                 return err;
477         }
478         else if (_MALI_PRODUCT_ID_MALI300 == global_product_id ||
479                  _MALI_PRODUCT_ID_MALI400 == global_product_id ||
480                  _MALI_PRODUCT_ID_MALI450 == global_product_id)
481         {
482                 _mali_osk_errcode_t err;
483                 int cluster_id_gp = 0;
484                 int cluster_id_pp_grp0 = 0;
485                 int cluster_id_pp_grp1 = 0;
486                 int i;
487
488                 _mali_osk_resource_t resource_gp;
489                 _mali_osk_resource_t resource_gp_mmu;
490                 _mali_osk_resource_t resource_pp[8];
491                 _mali_osk_resource_t resource_pp_mmu[8];
492                 _mali_osk_resource_t resource_pp_mmu_bcast;
493                 _mali_osk_resource_t resource_pp_bcast;
494                 _mali_osk_resource_t resource_dlbu;
495                 _mali_osk_resource_t resource_bcast;
496                 _mali_osk_errcode_t resource_gp_found;
497                 _mali_osk_errcode_t resource_gp_mmu_found;
498                 _mali_osk_errcode_t resource_pp_found[8];
499                 _mali_osk_errcode_t resource_pp_mmu_found[8];
500                 _mali_osk_errcode_t resource_pp_mmu_bcast_found;
501                 _mali_osk_errcode_t resource_pp_bcast_found;
502                 _mali_osk_errcode_t resource_dlbu_found;
503                 _mali_osk_errcode_t resource_bcast_found;
504
505                 if (_MALI_PRODUCT_ID_MALI450 == global_product_id)
506                 {
507                         /* Mali-450 have separate L2s for GP, and PP core group(s) */
508                         cluster_id_pp_grp0 = 1;
509                         cluster_id_pp_grp1 = 2;
510                 }
511
512                 resource_gp_found = _mali_osk_resource_find(global_gpu_base_address + 0x00000, &resource_gp);
513                 resource_gp_mmu_found = _mali_osk_resource_find(global_gpu_base_address + 0x03000, &resource_gp_mmu);
514                 resource_pp_found[0] = _mali_osk_resource_find(global_gpu_base_address + 0x08000, &(resource_pp[0]));
515                 resource_pp_found[1] = _mali_osk_resource_find(global_gpu_base_address + 0x0A000, &(resource_pp[1]));
516                 resource_pp_found[2] = _mali_osk_resource_find(global_gpu_base_address + 0x0C000, &(resource_pp[2]));
517                 resource_pp_found[3] = _mali_osk_resource_find(global_gpu_base_address + 0x0E000, &(resource_pp[3]));
518                 resource_pp_found[4] = _mali_osk_resource_find(global_gpu_base_address + 0x28000, &(resource_pp[4]));
519                 resource_pp_found[5] = _mali_osk_resource_find(global_gpu_base_address + 0x2A000, &(resource_pp[5]));
520                 resource_pp_found[6] = _mali_osk_resource_find(global_gpu_base_address + 0x2C000, &(resource_pp[6]));
521                 resource_pp_found[7] = _mali_osk_resource_find(global_gpu_base_address + 0x2E000, &(resource_pp[7]));
522                 resource_pp_mmu_found[0] = _mali_osk_resource_find(global_gpu_base_address + 0x04000, &(resource_pp_mmu[0]));
523                 resource_pp_mmu_found[1] = _mali_osk_resource_find(global_gpu_base_address + 0x05000, &(resource_pp_mmu[1]));
524                 resource_pp_mmu_found[2] = _mali_osk_resource_find(global_gpu_base_address + 0x06000, &(resource_pp_mmu[2]));
525                 resource_pp_mmu_found[3] = _mali_osk_resource_find(global_gpu_base_address + 0x07000, &(resource_pp_mmu[3]));
526                 resource_pp_mmu_found[4] = _mali_osk_resource_find(global_gpu_base_address + 0x1C000, &(resource_pp_mmu[4]));
527                 resource_pp_mmu_found[5] = _mali_osk_resource_find(global_gpu_base_address + 0x1D000, &(resource_pp_mmu[5]));
528                 resource_pp_mmu_found[6] = _mali_osk_resource_find(global_gpu_base_address + 0x1E000, &(resource_pp_mmu[6]));
529                 resource_pp_mmu_found[7] = _mali_osk_resource_find(global_gpu_base_address + 0x1F000, &(resource_pp_mmu[7]));
530
531
532                 if (_MALI_PRODUCT_ID_MALI450 == global_product_id)
533                 {
534                         resource_bcast_found = _mali_osk_resource_find(global_gpu_base_address + 0x13000, &resource_bcast);
535                         resource_dlbu_found = _mali_osk_resource_find(global_gpu_base_address + 0x14000, &resource_dlbu);
536                         resource_pp_mmu_bcast_found = _mali_osk_resource_find(global_gpu_base_address + 0x15000, &resource_pp_mmu_bcast);
537                         resource_pp_bcast_found = _mali_osk_resource_find(global_gpu_base_address + 0x16000, &resource_pp_bcast);
538
539                         if (_MALI_OSK_ERR_OK != resource_bcast_found ||
540                             _MALI_OSK_ERR_OK != resource_dlbu_found ||
541                             _MALI_OSK_ERR_OK != resource_pp_mmu_bcast_found ||
542                             _MALI_OSK_ERR_OK != resource_pp_bcast_found)
543                         {
544                                 /* Missing mandatory core(s) for Mali-450 */
545                                 MALI_DEBUG_PRINT(2, ("Missing mandatory resources, Mali-450 needs DLBU, Broadcast unit, virtual PP core and virtual MMU\n"));
546                                 return _MALI_OSK_ERR_FAULT;
547                         }
548                 }
549
550                 if (_MALI_OSK_ERR_OK != resource_gp_found ||
551                     _MALI_OSK_ERR_OK != resource_gp_mmu_found ||
552                     _MALI_OSK_ERR_OK != resource_pp_found[0] ||
553                     _MALI_OSK_ERR_OK != resource_pp_mmu_found[0])
554                 {
555                         /* Missing mandatory core(s) */
556                         MALI_DEBUG_PRINT(2, ("Missing mandatory resource, need at least one GP and one PP, both with a separate MMU\n"));
557                         return _MALI_OSK_ERR_FAULT;
558                 }
559
560                 MALI_DEBUG_ASSERT(1 <= mali_l2_cache_core_get_glob_num_l2_cores());
561                 err = mali_create_group(mali_l2_cache_core_get_glob_l2_core(cluster_id_gp), &resource_gp_mmu, &resource_gp, NULL);
562                 if (err != _MALI_OSK_ERR_OK)
563                 {
564                         return err;
565                 }
566
567                 /* Create group for first (and mandatory) PP core */
568                 MALI_DEBUG_ASSERT(mali_l2_cache_core_get_glob_num_l2_cores() >= (cluster_id_pp_grp0 + 1)); /* >= 1 on Mali-300 and Mali-400, >= 2 on Mali-450 */
569                 err = mali_create_group(mali_l2_cache_core_get_glob_l2_core(cluster_id_pp_grp0), &resource_pp_mmu[0], NULL, &resource_pp[0]);
570                 if (err != _MALI_OSK_ERR_OK)
571                 {
572                         return err;
573                 }
574
575                 mali_inited_pp_cores_group_1++;
576
577                 /* Create groups for rest of the cores in the first PP core group */
578                 for (i = 1; i < 4; i++) /* First half of the PP cores belong to first core group */
579                 {
580                         if (mali_inited_pp_cores_group_1 < mali_max_pp_cores_group_1)
581                         {
582                                 if (_MALI_OSK_ERR_OK == resource_pp_found[i] && _MALI_OSK_ERR_OK == resource_pp_mmu_found[i])
583                                 {
584                                         err = mali_create_group(mali_l2_cache_core_get_glob_l2_core(cluster_id_pp_grp0), &resource_pp_mmu[i], NULL, &resource_pp[i]);
585                                         if (err != _MALI_OSK_ERR_OK)
586                                         {
587                                                 return err;
588                                         }
589                                         mali_inited_pp_cores_group_1++;
590                                 }
591                         }
592                 }
593
594                 /* Create groups for cores in the second PP core group */
595                 for (i = 4; i < 8; i++) /* Second half of the PP cores belong to second core group */
596                 {
597                         if (mali_inited_pp_cores_group_2 < mali_max_pp_cores_group_2)
598                         {
599                                 if (_MALI_OSK_ERR_OK == resource_pp_found[i] && _MALI_OSK_ERR_OK == resource_pp_mmu_found[i])
600                                 {
601                                         MALI_DEBUG_ASSERT(mali_l2_cache_core_get_glob_num_l2_cores() >= 2); /* Only Mali-450 have a second core group */
602                                         err = mali_create_group(mali_l2_cache_core_get_glob_l2_core(cluster_id_pp_grp1), &resource_pp_mmu[i], NULL, &resource_pp[i]);
603                                         if (err != _MALI_OSK_ERR_OK)
604                                         {
605                                                 return err;
606                                         }
607                                         mali_inited_pp_cores_group_2++;
608                                 }
609                         }
610                 }
611
612                 if(_MALI_PRODUCT_ID_MALI450 == global_product_id)
613                 {
614                         err = mali_create_virtual_group(&resource_pp_mmu_bcast, &resource_pp_bcast, &resource_dlbu, &resource_bcast);
615                         if (_MALI_OSK_ERR_OK != err)
616                         {
617                                 return err;
618                         }
619                 }
620
621                 mali_max_pp_cores_group_1 = mali_inited_pp_cores_group_1;
622                 mali_max_pp_cores_group_2 = mali_inited_pp_cores_group_2;
623                 MALI_DEBUG_PRINT(2, ("%d+%d PP cores initialized\n", mali_inited_pp_cores_group_1, mali_inited_pp_cores_group_2));
624
625                 return _MALI_OSK_ERR_OK;
626         }
627
628         /* No known HW core */
629         return _MALI_OSK_ERR_FAULT;
630 }
631
632 static _mali_osk_errcode_t mali_parse_config_pmu(void)
633 {
634         _mali_osk_resource_t resource_pmu;
635
636         if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x02000, &resource_pmu))
637         {
638                 u32 number_of_pp_cores = 0;
639                 u32 number_of_l2_caches = 0;
640
641                 mali_resource_count(&number_of_pp_cores, &number_of_l2_caches);
642
643                 if (NULL == mali_pmu_create(&resource_pmu, number_of_pp_cores, number_of_l2_caches))
644                 {
645                         return _MALI_OSK_ERR_FAULT;
646                 }
647         }
648
649         /* It's ok if the PMU doesn't exist */
650         return _MALI_OSK_ERR_OK;
651 }
652
653 static _mali_osk_errcode_t mali_parse_config_memory(void)
654 {
655         _mali_osk_errcode_t ret;
656
657         if (0 == mali_dedicated_mem_start && 0 == mali_dedicated_mem_size && 0 == mali_shared_mem_size)
658         {
659                 /* Memory settings are not overridden by module parameters, so use device settings */
660                 struct _mali_osk_device_data data = { 0, };
661
662                 if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data))
663                 {
664                         /* Use device specific settings (if defined) */
665                         mali_dedicated_mem_start = data.dedicated_mem_start;
666                         mali_dedicated_mem_size = data.dedicated_mem_size;
667                         mali_shared_mem_size = data.shared_mem_size;
668                 }
669
670                 if (0 == mali_dedicated_mem_start && 0 == mali_dedicated_mem_size && 0 == mali_shared_mem_size)
671                 {
672                         /* No GPU memory specified */
673                         return _MALI_OSK_ERR_INVALID_ARGS;
674                 }
675
676                 MALI_DEBUG_PRINT(2, ("Using device defined memory settings (dedicated: 0x%08X@0x%08X, shared: 0x%08X)\n",
677                                      mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
678         }
679         else
680         {
681                 MALI_DEBUG_PRINT(2, ("Using module defined memory settings (dedicated: 0x%08X@0x%08X, shared: 0x%08X)\n",
682                                      mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
683         }
684
685         if (0 < mali_dedicated_mem_size && 0 != mali_dedicated_mem_start)
686         {
687                 /* Dedicated memory */
688                 ret = mali_memory_core_resource_dedicated_memory(mali_dedicated_mem_start, mali_dedicated_mem_size);
689                 if (_MALI_OSK_ERR_OK != ret)
690                 {
691                         MALI_PRINT_ERROR(("Failed to register dedicated memory\n"));
692                         mali_memory_terminate();
693                         return ret;
694                 }
695         }
696
697         if (0 < mali_shared_mem_size)
698         {
699                 /* Shared OS memory */
700                 ret = mali_memory_core_resource_os_memory(mali_shared_mem_size);
701                 if (_MALI_OSK_ERR_OK != ret)
702                 {
703                         MALI_PRINT_ERROR(("Failed to register shared OS memory\n"));
704                         mali_memory_terminate();
705                         return ret;
706                 }
707         }
708
709         if (0 == mali_fb_start && 0 == mali_fb_size)
710         {
711                 /* Frame buffer settings are not overridden by module parameters, so use device settings */
712                 struct _mali_osk_device_data data = { 0, };
713
714                 if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data))
715                 {
716                         /* Use device specific settings (if defined) */
717                         mali_fb_start = data.fb_start;
718                         mali_fb_size = data.fb_size;
719                 }
720
721                 MALI_DEBUG_PRINT(2, ("Using device defined frame buffer settings (0x%08X@0x%08X)\n",
722                                      mali_fb_size, mali_fb_start));
723         }
724         else
725         {
726                 MALI_DEBUG_PRINT(2, ("Using module defined frame buffer settings (0x%08X@0x%08X)\n",
727                                      mali_fb_size, mali_fb_start));
728         }
729
730         if (0 != mali_fb_size)
731         {
732                 /* Register frame buffer */
733                 ret = mali_mem_validation_add_range(mali_fb_start, mali_fb_size);
734                 if (_MALI_OSK_ERR_OK != ret)
735                 {
736                         MALI_PRINT_ERROR(("Failed to register frame buffer memory region\n"));
737                         mali_memory_terminate();
738                         return ret;
739                 }
740         }
741
742         return _MALI_OSK_ERR_OK;
743 }
744
745 _mali_osk_errcode_t mali_initialize_subsystems(void)
746 {
747         _mali_osk_errcode_t err;
748
749         err = mali_session_initialize();
750         if (_MALI_OSK_ERR_OK != err) goto session_init_failed;
751
752 #if defined(CONFIG_MALI400_PROFILING)
753         err = _mali_osk_profiling_init(mali_boot_profiling ? MALI_TRUE : MALI_FALSE);
754         if (_MALI_OSK_ERR_OK != err)
755         {
756                 /* No biggie if we wheren't able to initialize the profiling */
757                 MALI_PRINT_ERROR(("Failed to initialize profiling, feature will be unavailable\n"));
758         }
759 #endif
760
761         err = mali_memory_initialize();
762         if (_MALI_OSK_ERR_OK != err) goto memory_init_failed;
763
764         /* Configure memory early. Memory allocation needed for mali_mmu_initialize. */
765         err = mali_parse_config_memory();
766         if (_MALI_OSK_ERR_OK != err) goto parse_memory_config_failed;
767
768         /* Initialize the MALI PMU */
769         err = mali_parse_config_pmu();
770         if (_MALI_OSK_ERR_OK != err) goto parse_pmu_config_failed;
771
772         /* Initialize the power management module */
773         err = mali_pm_initialize();
774         if (_MALI_OSK_ERR_OK != err) goto pm_init_failed;
775
776         /* Make sure the power stays on for the rest of this function */
777         err = _mali_osk_pm_dev_ref_add();
778         if (_MALI_OSK_ERR_OK != err) goto pm_always_on_failed;
779
780         /* Detect which Mali GPU we are dealing with */
781         err = mali_parse_product_info();
782         if (_MALI_OSK_ERR_OK != err) goto product_info_parsing_failed;
783
784         /* The global_product_id is now populated with the correct Mali GPU */
785
786         /* Initialize MMU module */
787         err = mali_mmu_initialize();
788         if (_MALI_OSK_ERR_OK != err) goto mmu_init_failed;
789
790         if (_MALI_PRODUCT_ID_MALI450 == global_product_id)
791         {
792                 err = mali_dlbu_initialize();
793                 if (_MALI_OSK_ERR_OK != err) goto dlbu_init_failed;
794         }
795
796         /* Start configuring the actual Mali hardware. */
797         err = mali_parse_config_l2_cache();
798         if (_MALI_OSK_ERR_OK != err) goto config_parsing_failed;
799         err = mali_parse_config_groups();
800         if (_MALI_OSK_ERR_OK != err) goto config_parsing_failed;
801
802         /* Initialize the schedulers */
803         err = mali_scheduler_initialize();
804         if (_MALI_OSK_ERR_OK != err) goto scheduler_init_failed;
805         err = mali_gp_scheduler_initialize();
806         if (_MALI_OSK_ERR_OK != err) goto gp_scheduler_init_failed;
807         err = mali_pp_scheduler_initialize();
808         if (_MALI_OSK_ERR_OK != err) goto pp_scheduler_init_failed;
809
810         /* Initialize the GPU utilization tracking */
811         err = mali_utilization_init();
812         if (_MALI_OSK_ERR_OK != err) goto utilization_init_failed;
813
814         /* Allowing the system to be turned off */
815         _mali_osk_pm_dev_ref_dec();
816
817         MALI_SUCCESS; /* all ok */
818
819         /* Error handling */
820
821 utilization_init_failed:
822         mali_pp_scheduler_terminate();
823 pp_scheduler_init_failed:
824         mali_gp_scheduler_terminate();
825 gp_scheduler_init_failed:
826         mali_scheduler_terminate();
827 scheduler_init_failed:
828 config_parsing_failed:
829         mali_delete_l2_cache_cores(); /* Delete L2 cache cores even if config parsing failed. */
830 dlbu_init_failed:
831         mali_dlbu_terminate();
832 mmu_init_failed:
833         mali_mmu_terminate();
834         /* Nothing to roll back */
835 product_info_parsing_failed:
836         /* Allowing the system to be turned off */
837         _mali_osk_pm_dev_ref_dec();
838 pm_always_on_failed:
839         mali_pm_terminate();
840 pm_init_failed:
841         {
842                 struct mali_pmu_core *pmu = mali_pmu_get_global_pmu_core();
843                 if (NULL != pmu)
844                 {
845                         mali_pmu_delete(pmu);
846                 }
847         }
848 parse_pmu_config_failed:
849         /* undoing mali_parse_config_memory() is done by mali_memory_terminate() */
850 parse_memory_config_failed:
851         mali_memory_terminate();
852 memory_init_failed:
853 #if defined(CONFIG_MALI400_PROFILING)
854         _mali_osk_profiling_term();
855 #endif
856         mali_session_terminate();
857 session_init_failed:
858         return err;
859 }
860
861 void mali_terminate_subsystems(void)
862 {
863         struct mali_pmu_core *pmu = mali_pmu_get_global_pmu_core();
864
865         MALI_DEBUG_PRINT(2, ("terminate_subsystems() called\n"));
866
867         /* shut down subsystems in reverse order from startup */
868
869         /* We need the GPU to be powered up for the terminate sequence */
870         _mali_osk_pm_dev_ref_add();
871
872         mali_utilization_term();
873         mali_pp_scheduler_terminate();
874         mali_gp_scheduler_terminate();
875         mali_scheduler_terminate();
876         mali_delete_l2_cache_cores();
877         if (_MALI_PRODUCT_ID_MALI450 == global_product_id)
878         {
879                 mali_dlbu_terminate();
880         }
881         mali_mmu_terminate();
882         if (NULL != pmu)
883         {
884                 mali_pmu_delete(pmu);
885         }
886         mali_pm_terminate();
887         mali_memory_terminate();
888 #if defined(CONFIG_MALI400_PROFILING)
889         _mali_osk_profiling_term();
890 #endif
891
892         /* Allowing the system to be turned off */
893         _mali_osk_pm_dev_ref_dec();
894
895         mali_session_terminate();
896 }
897
898 _mali_product_id_t mali_kernel_core_get_product_id(void)
899 {
900         return global_product_id;
901 }
902
903 _mali_osk_errcode_t _mali_ukk_get_api_version( _mali_uk_get_api_version_s *args )
904 {
905         MALI_DEBUG_ASSERT_POINTER(args);
906         MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
907
908         /* check compatability */
909         if ( args->version == _MALI_UK_API_VERSION )
910         {
911                 args->compatible = 1;
912         }
913         else
914         {
915                 args->compatible = 0;
916         }
917
918         args->version = _MALI_UK_API_VERSION; /* report our version */
919
920         /* success regardless of being compatible or not */
921         MALI_SUCCESS;
922 }
923
924 _mali_osk_errcode_t _mali_ukk_wait_for_notification( _mali_uk_wait_for_notification_s *args )
925 {
926         _mali_osk_errcode_t err;
927         _mali_osk_notification_t * notification;
928         _mali_osk_notification_queue_t *queue;
929
930         /* check input */
931         MALI_DEBUG_ASSERT_POINTER(args);
932         MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
933
934         queue = ((struct mali_session_data *)args->ctx)->ioctl_queue;
935
936         /* if the queue does not exist we're currently shutting down */
937         if (NULL == queue)
938         {
939                 MALI_DEBUG_PRINT(1, ("No notification queue registered with the session. Asking userspace to stop querying\n"));
940                 args->type = _MALI_NOTIFICATION_CORE_SHUTDOWN_IN_PROGRESS;
941                 MALI_SUCCESS;
942         }
943
944         /* receive a notification, might sleep */
945         err = _mali_osk_notification_queue_receive(queue, &notification);
946         if (_MALI_OSK_ERR_OK != err)
947         {
948                 MALI_ERROR(err); /* errcode returned, pass on to caller */
949         }
950
951         /* copy the buffer to the user */
952         args->type = (_mali_uk_notification_type)notification->notification_type;
953         _mali_osk_memcpy(&args->data, notification->result_buffer, notification->result_buffer_size);
954
955         /* finished with the notification */
956         _mali_osk_notification_delete( notification );
957
958         MALI_SUCCESS; /* all ok */
959 }
960
961 _mali_osk_errcode_t _mali_ukk_post_notification( _mali_uk_post_notification_s *args )
962 {
963         _mali_osk_notification_t * notification;
964         _mali_osk_notification_queue_t *queue;
965
966         /* check input */
967         MALI_DEBUG_ASSERT_POINTER(args);
968         MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
969
970         queue = ((struct mali_session_data *)args->ctx)->ioctl_queue;
971
972         /* if the queue does not exist we're currently shutting down */
973         if (NULL == queue)
974         {
975                 MALI_DEBUG_PRINT(1, ("No notification queue registered with the session. Asking userspace to stop querying\n"));
976                 MALI_SUCCESS;
977         }
978
979         notification = _mali_osk_notification_create(args->type, 0);
980         if (NULL == notification)
981         {
982                 MALI_PRINT_ERROR( ("Failed to create notification object\n"));
983                 return _MALI_OSK_ERR_NOMEM;
984         }
985
986         _mali_osk_notification_queue_send(queue, notification);
987
988         MALI_SUCCESS; /* all ok */
989 }
990
991 _mali_osk_errcode_t _mali_ukk_open(void **context)
992 {
993         struct mali_session_data *session;
994
995         /* allocated struct to track this session */
996         session = (struct mali_session_data *)_mali_osk_calloc(1, sizeof(struct mali_session_data));
997         MALI_CHECK_NON_NULL(session, _MALI_OSK_ERR_NOMEM);
998
999         MALI_DEBUG_PRINT(3, ("Session starting\n"));
1000
1001         /* create a response queue for this session */
1002         session->ioctl_queue = _mali_osk_notification_queue_init();
1003         if (NULL == session->ioctl_queue)
1004         {
1005                 _mali_osk_free(session);
1006                 MALI_ERROR(_MALI_OSK_ERR_NOMEM);
1007         }
1008
1009         session->page_directory = mali_mmu_pagedir_alloc();
1010         if (NULL == session->page_directory)
1011         {
1012                 _mali_osk_notification_queue_term(session->ioctl_queue);
1013                 _mali_osk_free(session);
1014                 MALI_ERROR(_MALI_OSK_ERR_NOMEM);
1015         }
1016
1017         if (_MALI_OSK_ERR_OK != mali_mmu_pagedir_map(session->page_directory, MALI_DLBU_VIRT_ADDR, _MALI_OSK_MALI_PAGE_SIZE))
1018         {
1019                 MALI_PRINT_ERROR(("Failed to map DLBU page into session\n"));
1020                 _mali_osk_notification_queue_term(session->ioctl_queue);
1021                 _mali_osk_free(session);
1022                 MALI_ERROR(_MALI_OSK_ERR_NOMEM);
1023         }
1024
1025         if (0 != mali_dlbu_phys_addr)
1026         {
1027                 mali_mmu_pagedir_update(session->page_directory, MALI_DLBU_VIRT_ADDR, mali_dlbu_phys_addr,
1028                                         _MALI_OSK_MALI_PAGE_SIZE, MALI_CACHE_STANDARD);
1029         }
1030
1031         if (_MALI_OSK_ERR_OK != mali_memory_session_begin(session))
1032         {
1033                 mali_mmu_pagedir_free(session->page_directory);
1034                 _mali_osk_notification_queue_term(session->ioctl_queue);
1035                 _mali_osk_free(session);
1036                 MALI_ERROR(_MALI_OSK_ERR_NOMEM);
1037         }
1038
1039 #ifdef CONFIG_SYNC
1040 /* MALI_SEC */
1041 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3,4,0)
1042         _mali_osk_list_init(&session->pending_jobs);
1043         session->pending_jobs_lock = _mali_osk_lock_init(_MALI_OSK_LOCKFLAG_NONINTERRUPTABLE | _MALI_OSK_LOCKFLAG_ORDERED | _MALI_OSK_LOCKFLAG_SPINLOCK,
1044                                                          0, _MALI_OSK_LOCK_ORDER_SESSION_PENDING_JOBS);
1045         if (NULL == session->pending_jobs_lock)
1046         {
1047                 MALI_PRINT_ERROR(("Failed to create pending jobs lock\n"));
1048                 mali_memory_session_end(session);
1049                 mali_mmu_pagedir_free(session->page_directory);
1050                 _mali_osk_notification_queue_term(session->ioctl_queue);
1051                 _mali_osk_free(session);
1052                 MALI_ERROR(_MALI_OSK_ERR_NOMEM);
1053         }
1054 #endif
1055 #endif
1056
1057         *context = (void*)session;
1058
1059         /* Add session to the list of all sessions. */
1060         mali_session_add(session);
1061
1062         /* Initialize list of jobs on this session */
1063         _MALI_OSK_INIT_LIST_HEAD(&session->job_list);
1064
1065         MALI_DEBUG_PRINT(2, ("Session started\n"));
1066         MALI_SUCCESS;
1067 }
1068
1069 _mali_osk_errcode_t _mali_ukk_close(void **context)
1070 {
1071         struct mali_session_data *session;
1072         MALI_CHECK_NON_NULL(context, _MALI_OSK_ERR_INVALID_ARGS);
1073         session = (struct mali_session_data *)*context;
1074
1075         MALI_DEBUG_PRINT(3, ("Session ending\n"));
1076
1077         /* Remove session from list of all sessions. */
1078         mali_session_remove(session);
1079
1080         /* Abort pending jobs */
1081 #ifdef CONFIG_SYNC
1082 /* MALI_SEC */
1083 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3,4,0)
1084         {
1085                 _mali_osk_list_t tmp_job_list;
1086                 struct mali_pp_job *job, *tmp;
1087                 _MALI_OSK_INIT_LIST_HEAD(&tmp_job_list);
1088
1089                 _mali_osk_lock_wait(session->pending_jobs_lock, _MALI_OSK_LOCKMODE_RW);
1090                 /* Abort asynchronous wait on fence. */
1091                 _MALI_OSK_LIST_FOREACHENTRY(job, tmp, &session->pending_jobs, struct mali_pp_job, list)
1092                 {
1093                         MALI_DEBUG_PRINT(2, ("Sync: Aborting wait for session %x job %x\n", session, job));
1094                         if (sync_fence_cancel_async(job->pre_fence, &job->sync_waiter))
1095                         {
1096                                 MALI_DEBUG_PRINT(2, ("Sync: Failed to abort job %x\n", job));
1097                         }
1098                         _mali_osk_list_add(&job->list, &tmp_job_list);
1099                 }
1100                 _mali_osk_lock_signal(session->pending_jobs_lock, _MALI_OSK_LOCKMODE_RW);
1101
1102                 _mali_osk_wq_flush();
1103
1104                 _mali_osk_lock_term(session->pending_jobs_lock);
1105
1106                 /* Delete jobs */
1107                 _MALI_OSK_LIST_FOREACHENTRY(job, tmp, &tmp_job_list, struct mali_pp_job, list)
1108                 {
1109                         mali_pp_job_delete(job);
1110                 }
1111         }
1112 #endif
1113 #endif
1114
1115         /* Abort queued and running jobs */
1116         mali_gp_scheduler_abort_session(session);
1117         mali_pp_scheduler_abort_session(session);
1118
1119         /* Flush pending work.
1120          * Needed to make sure all bottom half processing related to this
1121          * session has been completed, before we free internal data structures.
1122          */
1123         _mali_osk_wq_flush();
1124
1125         /* Free remaining memory allocated to this session */
1126         mali_memory_session_end(session);
1127
1128         /* Free session data structures */
1129         mali_mmu_pagedir_free(session->page_directory);
1130         _mali_osk_notification_queue_term(session->ioctl_queue);
1131         _mali_osk_free(session);
1132
1133         *context = NULL;
1134
1135         MALI_DEBUG_PRINT(2, ("Session has ended\n"));
1136
1137         MALI_SUCCESS;
1138 }
1139
1140 #if MALI_STATE_TRACKING
1141 u32 _mali_kernel_core_dump_state(char* buf, u32 size)
1142 {
1143         int n = 0; /* Number of bytes written to buf */
1144
1145         n += mali_gp_scheduler_dump_state(buf + n, size - n);
1146         n += mali_pp_scheduler_dump_state(buf + n, size - n);
1147
1148         return n;
1149 }
1150 #endif