endif
OS_MEMORY_KERNEL_BUFFER_SIZE_IN_MB ?= 16
-
USING_GPU_UTILIZATION ?= 1
-
-PROFILING_SKIP_PP_JOBS ?= 0
-PROFILING_SKIP_PP_AND_GP_JOBS ?= 0
############## Kasin Added, for platform. ################
ifeq ($(CONFIG_MALI400_DEBUG),y)
BUILD ?= debug
mali-$(CONFIG_DMA_SHARED_BUFFER) += linux/mali_memory_dma_buf.o
mali-$(CONFIG_SYNC) += linux/mali_sync.o
+ccflags-$(CONFIG_SYNC) += -Idrivers/staging/android
mali-$(CONFIG_MALI400_UMP) += linux/mali_memory_ump.o
ccflags-y += $(EXTRA_DEFINES)
# Set up our defines, which will be passed to gcc
-ccflags-y += -DPROFILING_SKIP_PP_JOBS=$(PROFILING_SKIP_PP_JOBS)
-ccflags-y += -DPROFILING_SKIP_PP_AND_GP_JOBS=$(PROFILING_SKIP_PP_AND_GP_JOBS)
-
ccflags-y += -DMALI_PP_SCHEDULER_FORCE_NO_JOB_OVERLAP=$(MALI_PP_SCHEDULER_FORCE_NO_JOB_OVERLAP)
ccflags-y += -DMALI_PP_SCHEDULER_KEEP_SUB_JOB_STARTS_ALIGNED=$(MALI_PP_SCHEDULER_KEEP_SUB_JOB_STARTS_ALIGNED)
ccflags-y += -DMALI_PP_SCHEDULER_FORCE_NO_JOB_OVERLAP_BETWEEN_APPS=$(MALI_PP_SCHEDULER_FORCE_NO_JOB_OVERLAP_BETWEEN_APPS)
# Use our defines when compiling
ccflags-y += -I$(src) -I$(src)/include -I$(src)/common -I$(src)/linux -I$(src)/platform
-ccflags-y += -I$(srctree)/drivers/staging/android
# Get subversion revision number, fall back to only ${MALI_RELEASE_NAME} if no svn info is available
MALI_RELEASE_NAME=$(shell cat $(TOP_KBUILD_SRC)$(DRIVER_DIR)/.version 2> /dev/null)
powering up domains one by one, with a slight delay in between. Powering on all power
domains at the same time may cause peak currents higher than what some systems can handle.
These systems must not enable this option.
-
+
+config MALI_QUIET
+ bool "Make Mali driver very quiet"
+ depends on MALI400 && !MALI400_DEBUG
+ default n
+ ---help---
+ This forces the Mali driver to never print any messages.
+
+ If unsure, say N.
endmenu
#
-# Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+# Copyright (C) 2010-2014 ARM Limited. All rights reserved.
#
# This program is free software and is provided to you under the terms of the GNU General Public License version 2
# as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
endif
ifneq ($(BUILD),release)
+# Debug
export CONFIG_MALI400_DEBUG=y
+else
+# Release
+ifeq ($(MALI_QUIET),1)
+export CONFIG_MALI_QUIET=y
+export EXTRA_DEFINES += -DCONFIG_MALI_QUIET
+endif
+endif
+
+ifeq ($(MALI_SKIP_JOBS),1)
+EXTRA_DEFINES += -DPROFILING_SKIP_PP_JOBS=1 -DPROFILING_SKIP_GP_JOBS=1
endif
all: $(UMP_SYMVERS_FILE)
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_free(bcast_unit);
}
+/* Call this function to add the @group's id into bcast mask
+ * Note: redundant calling this function with same @group
+ * doesn't make any difference as calling it once
+ */
void mali_bcast_add_group(struct mali_bcast_unit *bcast_unit, struct mali_group *group)
{
u32 bcast_id;
bcast_unit->current_mask = broadcast_mask;
}
+/* Call this function to remove @group's id from bcast mask
+ * Note: redundant calling this function with same @group
+ * doesn't make any difference as calling it once
+ */
void mali_bcast_remove_group(struct mali_bcast_unit *bcast_unit, struct mali_group *group)
{
u32 bcast_id;
/* set broadcast mask */
mali_hw_core_register_write(&bcast_unit->hw_core,
- bcast_unit_addr_broadcast_mask,
- bcast_unit->current_mask);
+ bcast_unit_addr_broadcast_mask,
+ bcast_unit->current_mask);
/* set IRQ override mask */
mali_hw_core_register_write(&bcast_unit->hw_core,
- bcast_unit_addr_irq_override_mask,
- bcast_unit->current_mask & 0xFF);
+ bcast_unit_addr_irq_override_mask,
+ bcast_unit->current_mask & 0xFF);
}
void mali_bcast_disable(struct mali_bcast_unit *bcast_unit)
/* set broadcast mask */
mali_hw_core_register_write(&bcast_unit->hw_core,
- bcast_unit_addr_broadcast_mask,
- 0x0);
+ bcast_unit_addr_broadcast_mask,
+ 0x0);
/* set IRQ override mask */
mali_hw_core_register_write(&bcast_unit->hw_core,
- bcast_unit_addr_irq_override_mask,
- 0x0);
+ bcast_unit_addr_irq_override_mask,
+ 0x0);
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*/
#define MALI_DLBU_SIZE 0x400
-u32 mali_dlbu_phys_addr = 0;
-static mali_io_address mali_dlbu_cpu_addr = 0;
+mali_dma_addr mali_dlbu_phys_addr = 0;
+static mali_io_address mali_dlbu_cpu_addr = NULL;
/**
* DLBU register numbers
*/
typedef enum mali_dlbu_register {
MALI_DLBU_REGISTER_MASTER_TLLIST_PHYS_ADDR = 0x0000, /**< Master tile list physical base address;
- 31:12 Physical address to the page used for the DLBU
- 0 DLBU enable - set this bit to 1 enables the AXI bus
- between PPs and L2s, setting to 0 disables the router and
- no further transactions are sent to DLBU */
+ 31:12 Physical address to the page used for the DLBU
+ 0 DLBU enable - set this bit to 1 enables the AXI bus
+ between PPs and L2s, setting to 0 disables the router and
+ no further transactions are sent to DLBU */
MALI_DLBU_REGISTER_MASTER_TLLIST_VADDR = 0x0004, /**< Master tile list virtual base address;
- 31:12 Virtual address to the page used for the DLBU */
- MALI_DLBU_REGISTER_TLLIST_VBASEADDR = 0x0008, /**< Tile list virtual base address;
- 31:12 Virtual address to the tile list. This address is used when
- calculating the call address sent to PP.*/
- MALI_DLBU_REGISTER_FB_DIM = 0x000C, /**< Framebuffer dimension;
- 23:16 Number of tiles in Y direction-1
- 7:0 Number of tiles in X direction-1 */
- MALI_DLBU_REGISTER_TLLIST_CONF = 0x0010, /**< Tile list configuration;
- 29:28 select the size of each allocated block: 0=128 bytes, 1=256, 2=512, 3=1024
- 21:16 2^n number of tiles to be binned to one tile list in Y direction
- 5:0 2^n number of tiles to be binned to one tile list in X direction */
- MALI_DLBU_REGISTER_START_TILE_POS = 0x0014, /**< Start tile positions;
- 31:24 start position in Y direction for group 1
- 23:16 start position in X direction for group 1
- 15:8 start position in Y direction for group 0
- 7:0 start position in X direction for group 0 */
- MALI_DLBU_REGISTER_PP_ENABLE_MASK = 0x0018, /**< PP enable mask;
- 7 enable PP7 for load balancing
- 6 enable PP6 for load balancing
- 5 enable PP5 for load balancing
- 4 enable PP4 for load balancing
- 3 enable PP3 for load balancing
- 2 enable PP2 for load balancing
- 1 enable PP1 for load balancing
- 0 enable PP0 for load balancing */
+ 31:12 Virtual address to the page used for the DLBU */
+ MALI_DLBU_REGISTER_TLLIST_VBASEADDR = 0x0008, /**< Tile list virtual base address;
+ 31:12 Virtual address to the tile list. This address is used when
+ calculating the call address sent to PP.*/
+ MALI_DLBU_REGISTER_FB_DIM = 0x000C, /**< Framebuffer dimension;
+ 23:16 Number of tiles in Y direction-1
+ 7:0 Number of tiles in X direction-1 */
+ MALI_DLBU_REGISTER_TLLIST_CONF = 0x0010, /**< Tile list configuration;
+ 29:28 select the size of each allocated block: 0=128 bytes, 1=256, 2=512, 3=1024
+ 21:16 2^n number of tiles to be binned to one tile list in Y direction
+ 5:0 2^n number of tiles to be binned to one tile list in X direction */
+ MALI_DLBU_REGISTER_START_TILE_POS = 0x0014, /**< Start tile positions;
+ 31:24 start position in Y direction for group 1
+ 23:16 start position in X direction for group 1
+ 15:8 start position in Y direction for group 0
+ 7:0 start position in X direction for group 0 */
+ MALI_DLBU_REGISTER_PP_ENABLE_MASK = 0x0018, /**< PP enable mask;
+ 7 enable PP7 for load balancing
+ 6 enable PP6 for load balancing
+ 5 enable PP5 for load balancing
+ 4 enable PP4 for load balancing
+ 3 enable PP3 for load balancing
+ 2 enable PP2 for load balancing
+ 1 enable PP1 for load balancing
+ 0 enable PP0 for load balancing */
} mali_dlbu_register;
typedef enum {
struct mali_dlbu_core {
struct mali_hw_core hw_core; /**< Common for all HW cores */
u32 pp_cores_mask; /**< This is a mask for the PP cores whose operation will be controlled by LBU
- see MALI_DLBU_REGISTER_PP_ENABLE_MASK register */
+ see MALI_DLBU_REGISTER_PP_ENABLE_MASK register */
};
_mali_osk_errcode_t mali_dlbu_initialize(void)
mali_mmu_release_table_page(mali_dlbu_phys_addr, mali_dlbu_cpu_addr);
}
-struct mali_dlbu_core *mali_dlbu_create(const _mali_osk_resource_t * resource)
+struct mali_dlbu_core *mali_dlbu_create(const _mali_osk_resource_t *resource)
{
struct mali_dlbu_core *core = NULL;
struct mali_pp_core *pp_core;
u32 bcast_id;
- MALI_DEBUG_ASSERT_POINTER( dlbu );
- MALI_DEBUG_ASSERT_POINTER( group );
+ MALI_DEBUG_ASSERT_POINTER(dlbu);
+ MALI_DEBUG_ASSERT_POINTER(group);
pp_core = mali_group_get_pp_core(group);
bcast_id = mali_pp_core_get_bcast_id(pp_core);
struct mali_pp_core *pp_core;
u32 bcast_id;
- MALI_DEBUG_ASSERT_POINTER( dlbu );
- MALI_DEBUG_ASSERT_POINTER( group );
+ MALI_DEBUG_ASSERT_POINTER(dlbu);
+ MALI_DEBUG_ASSERT_POINTER(group);
pp_core = mali_group_get_pp_core(group);
bcast_id = mali_pp_core_get_bcast_id(pp_core);
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct mali_pp_job;
struct mali_group;
-
-extern u32 mali_dlbu_phys_addr;
-
struct mali_dlbu_core;
+extern mali_dma_addr mali_dlbu_phys_addr;
+
_mali_osk_errcode_t mali_dlbu_initialize(void);
void mali_dlbu_terminate(void);
-struct mali_dlbu_core *mali_dlbu_create(const _mali_osk_resource_t * resource);
+struct mali_dlbu_core *mali_dlbu_create(const _mali_osk_resource_t *resource);
void mali_dlbu_delete(struct mali_dlbu_core *dlbu);
_mali_osk_errcode_t mali_dlbu_reset(struct mali_dlbu_core *dlbu);
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct mali_dma_core *mali_dma_create(_mali_osk_resource_t *resource)
{
- struct mali_dma_core* dma;
+ struct mali_dma_core *dma;
_mali_osk_errcode_t err;
MALI_DEBUG_ASSERT(NULL == mali_global_dma_core);
u32 addr = mali_hw_core_register_read(&dma->hw_core, MALI450_DMA_REG_SOURCE_ADDRESS);
MALI_PRINT_ERROR(("Mali DMA: Bus error when reading command list from 0x%lx\n", addr));
+ MALI_IGNORE(addr);
/* Clear the bus error */
mali_hw_core_register_write(&dma->hw_core, MALI450_DMA_REG_SOURCE_SIZE, 0);
return dma_busy_flag;
}
-static void mali_dma_start_transfer(struct mali_dma_core* dma, mali_dma_cmd_buf *buf)
+static void mali_dma_start_transfer(struct mali_dma_core *dma, mali_dma_cmd_buf *buf)
{
u32 memsize = buf->size * 4;
u32 addr = buf->phys_addr;
{
MALI_DEBUG_ASSERT_POINTER(buf);
- buf->virt_addr = (u32*)mali_dma_pool_alloc(mali_global_dma_core->pool, &buf->phys_addr);
+ buf->virt_addr = (u32 *)mali_dma_pool_alloc(mali_global_dma_core->pool, &buf->phys_addr);
if (NULL == buf->virt_addr) {
return _MALI_OSK_ERR_NOMEM;
}
buf->virt_addr = NULL;
}
-_mali_osk_errcode_t mali_dma_start(struct mali_dma_core* dma, mali_dma_cmd_buf *buf)
+_mali_osk_errcode_t mali_dma_start(struct mali_dma_core *dma, mali_dma_cmd_buf *buf)
{
_mali_osk_errcode_t err = _MALI_OSK_ERR_OK;
{
MALI_DEBUG_ASSERT_POINTER(dma);
MALI_DEBUG_PRINT(1, ("DMA unit registers:\n\t%08x, %08x\n",
- mali_hw_core_register_read(&dma->hw_core, MALI450_DMA_REG_SOURCE_ADDRESS),
- mali_hw_core_register_read(&dma->hw_core, MALI450_DMA_REG_SOURCE_SIZE)
- ));
+ mali_hw_core_register_read(&dma->hw_core, MALI450_DMA_REG_SOURCE_ADDRESS),
+ mali_hw_core_register_read(&dma->hw_core, MALI450_DMA_REG_SOURCE_SIZE)
+ ));
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
typedef struct mali_dma_cmd_buf {
u32 *virt_addr; /**< CPU address of command buffer */
- u32 phys_addr; /**< Physical address of command buffer */
+ mali_dma_addr phys_addr; /**< Physical address of command buffer */
u32 size; /**< Number of prepared words in command buffer */
} mali_dma_cmd_buf;
* @return _MALI_OSK_ERR_OK if the buffer was started successfully,
* _MALI_OSK_ERR_BUSY if the DMA unit is busy.
*/
-_mali_osk_errcode_t mali_dma_start(struct mali_dma_core* dma, mali_dma_cmd_buf *buf);
+_mali_osk_errcode_t mali_dma_start(struct mali_dma_core *dma, mali_dma_cmd_buf *buf);
/**
* @brief Create a DMA command
* @param count Number of 4 byte words to write
*/
MALI_STATIC_INLINE void mali_dma_write_array(mali_dma_cmd_buf *buf, struct mali_hw_core *core,
- u32 reg, u32 *data, u32 count)
+ u32 reg, u32 *data, u32 count)
{
- MALI_DEBUG_ASSERT((buf->size + 1 + count ) < MALI_DMA_CMD_BUF_SIZE / 4);
+ MALI_DEBUG_ASSERT((buf->size + 1 + count) < MALI_DMA_CMD_BUF_SIZE / 4);
buf->virt_addr[buf->size++] = mali_dma_command_write(core, reg, count);
* @param ref Pointer to referance data that can be skipped if equal
*/
MALI_STATIC_INLINE void mali_dma_write_array_conditional(mali_dma_cmd_buf *buf, struct mali_hw_core *core,
- u32 reg, u32 *data, u32 count, const u32 *ref)
+ u32 reg, u32 *data, u32 count, const u32 *ref)
{
/* Do conditional array writes are not yet implemented, fallback to a
* normal array write. */
* @param ref Pointer to referance data that can be skipped if equal
*/
MALI_STATIC_INLINE void mali_dma_write_conditional(mali_dma_cmd_buf *buf, struct mali_hw_core *core,
- u32 reg, u32 data, const u32 ref)
+ u32 reg, u32 data, const u32 ref)
{
/* Skip write if reference value is equal to data. */
if (data == ref) return;
* @param data Pointer to data to write
*/
MALI_STATIC_INLINE void mali_dma_write(mali_dma_cmd_buf *buf, struct mali_hw_core *core,
- u32 reg, u32 data)
+ u32 reg, u32 data)
{
buf->virt_addr[buf->size++] = mali_dma_command_write(core, reg, 1);
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
static void mali_gp_irq_probe_trigger(void *data);
static _mali_osk_errcode_t mali_gp_irq_probe_ack(void *data);
-struct mali_gp_core *mali_gp_create(const _mali_osk_resource_t * resource, struct mali_group *group)
+struct mali_gp_core *mali_gp_create(const _mali_osk_resource_t *resource, struct mali_group *group)
{
- struct mali_gp_core* core = NULL;
+ struct mali_gp_core *core = NULL;
MALI_DEBUG_ASSERT(NULL == mali_global_gp_core);
MALI_DEBUG_PRINT(2, ("Mali GP: Creating Mali GP core: %s\n", resource->description));
if (_MALI_OSK_ERR_OK == ret) {
/* Setup IRQ handlers (which will do IRQ probing if needed) */
core->irq = _mali_osk_irq_init(resource->irq,
- mali_group_upper_half_gp,
- group,
- mali_gp_irq_probe_trigger,
- mali_gp_irq_probe_ack,
- core,
- resource->description);
+ mali_group_upper_half_gp,
+ group,
+ mali_gp_irq_probe_trigger,
+ mali_gp_irq_probe_ack,
+ core,
+ resource->description);
if (NULL != core->irq) {
MALI_DEBUG_PRINT(4, ("Mali GP: set global gp core from 0x%08X to 0x%08X\n", mali_global_gp_core, core));
mali_global_gp_core = core;
if (i == MALI_REG_POLL_COUNT_FAST) {
MALI_PRINT_ERROR(("Mali GP: Failed to reset core %s, rawstat: 0x%08x\n",
- core->hw_core.description, rawstat));
+ core->hw_core.description, rawstat));
return _MALI_OSK_ERR_FAULT;
}
/* Barrier to make sure the previous register write is finished */
_mali_osk_write_mem_barrier();
- /* This is the command that starts the core. */
+ /* This is the command that starts the core.
+ *
+ * Don't actually run the job if PROFILING_SKIP_PP_JOBS are set, just
+ * force core to assert the completion interrupt.
+ */
+#if !defined(PROFILING_SKIP_GP_JOBS)
mali_hw_core_register_write_relaxed(&core->hw_core, MALIGP2_REG_ADDR_MGMT_CMD, startcmd);
+#else
+ {
+ u32 bits = 0;
+
+ if (mali_gp_job_has_vs_job(job))
+ bits = MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST;
+ if (mali_gp_job_has_plbu_job(job))
+ bits |= MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST;
+
+ mali_hw_core_register_write_relaxed(&core->hw_core,
+ MALIGP2_REG_ADDR_MGMT_INT_RAWSTAT, bits);
+ }
+#endif
/* Barrier to make sure the previous register write is finished */
_mali_osk_write_mem_barrier();
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_errcode_t mali_gp_initialize(void);
void mali_gp_terminate(void);
-struct mali_gp_core *mali_gp_create(const _mali_osk_resource_t * resource, struct mali_group *group);
+struct mali_gp_core *mali_gp_create(const _mali_osk_resource_t *resource, struct mali_group *group);
void mali_gp_delete(struct mali_gp_core *core);
void mali_gp_stop_bus(struct mali_gp_core *core);
{
/* Enable all interrupts, except those specified in irq_exceptions */
mali_hw_core_register_write(&core->hw_core, MALIGP2_REG_ADDR_MGMT_INT_MASK,
- MALIGP2_REG_VAL_IRQ_MASK_USED & ~irq_exceptions);
+ MALIGP2_REG_VAL_IRQ_MASK_USED & ~irq_exceptions);
}
MALI_STATIC_INLINE u32 mali_gp_read_plbu_alloc_start_addr(struct mali_gp_core *core)
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_uk_types.h"
static u32 gp_counter_src0 = MALI_HW_CORE_NO_COUNTER; /**< Performance counter 0, MALI_HW_CORE_NO_COUNTER for disabled */
-static u32 gp_counter_src1 = MALI_HW_CORE_NO_COUNTER; /**< Performance counter 1, MALI_HW_CORE_NO_COUNTER for disabled */
+static u32 gp_counter_src1 = MALI_HW_CORE_NO_COUNTER; /**< Performance counter 1, MALI_HW_CORE_NO_COUNTER for disabled */
struct mali_gp_job *mali_gp_job_create(struct mali_session_data *session, _mali_uk_gp_start_job_s *uargs, u32 id, struct mali_timeline_tracker *pp_tracker)
{
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
return (NULL == job) ? 0 : job->cache_order;
}
-MALI_STATIC_INLINE u32 mali_gp_job_get_user_id(struct mali_gp_job *job)
+MALI_STATIC_INLINE u64 mali_gp_job_get_user_id(struct mali_gp_job *job)
{
return job->uargs.user_job_ptr;
}
return job->tid;
}
-MALI_STATIC_INLINE u32* mali_gp_job_get_frame_registers(struct mali_gp_job *job)
+MALI_STATIC_INLINE u32 *mali_gp_job_get_frame_registers(struct mali_gp_job *job)
{
return job->uargs.frame_registers;
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
void mali_gp_scheduler_terminate(void)
{
- MALI_DEBUG_ASSERT( MALI_GP_SLOT_STATE_IDLE == slot.state
- || MALI_GP_SLOT_STATE_DISABLED == slot.state);
+ MALI_DEBUG_ASSERT(MALI_GP_SLOT_STATE_IDLE == slot.state
+ || MALI_GP_SLOT_STATE_DISABLED == slot.state);
MALI_DEBUG_ASSERT_POINTER(slot.group);
mali_group_delete(slot.group);
mali_gp_scheduler_unlock();
mali_group_unlock(slot.group);
MALI_DEBUG_PRINT(4, ("Mali GP scheduler: Nothing to schedule (paused=%u, idle slots=%u)\n",
- pause_count, MALI_GP_SLOT_STATE_IDLE == slot.state ? 1 : 0));
+ pause_count, MALI_GP_SLOT_STATE_IDLE == slot.state ? 1 : 0));
#if defined(CONFIG_GPU_TRACEPOINTS) && defined(CONFIG_TRACEPOINTS)
trace_gpu_sched_switch(mali_gp_get_hw_core_desc(group->gp_core), sched_clock(), 0, 0, 0);
#endif
void mali_gp_scheduler_oom(struct mali_group *group, struct mali_gp_job *job)
{
- _mali_uk_gp_job_suspended_s * jobres;
- _mali_osk_notification_t * notification;
+ _mali_uk_gp_job_suspended_s *jobres;
+ _mali_osk_notification_t *notification;
mali_gp_scheduler_lock();
MALI_DEBUG_ASSERT_POINTER(session);
MALI_DEBUG_ASSERT_POINTER(job);
- mali_gp_scheduler_job_queued();
+ /* We hold a PM reference for every job we hold queued (and running) */
+ _mali_osk_pm_dev_ref_add();
/* Add job to Timeline system. */
point = mali_timeline_system_add_tracker(session->timeline_system, &job->tracker, MALI_TIMELINE_GP);
MALI_DEBUG_ASSERT_POINTER(uargs);
MALI_DEBUG_ASSERT_POINTER(ctx);
- session = (struct mali_session_data*)ctx;
+ session = (struct mali_session_data *)ctx;
job = mali_gp_job_create(session, uargs, mali_scheduler_get_new_id(), NULL);
if (NULL == job) {
return _MALI_OSK_ERR_NOMEM;
}
- timeline_point_ptr = (u32 __user *) job->uargs.timeline_point_ptr;
+ timeline_point_ptr = (u32 __user *)(uintptr_t)job->uargs.timeline_point_ptr;
point = mali_gp_scheduler_submit_job(session, job);
_mali_osk_errcode_t _mali_ukk_get_gp_number_of_cores(_mali_uk_get_gp_number_of_cores_s *args)
{
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT_POINTER((struct mali_session_data *)(uintptr_t)args->ctx);
+
args->number_of_cores = 1;
return _MALI_OSK_ERR_OK;
}
_mali_osk_errcode_t _mali_ukk_get_gp_core_version(_mali_uk_get_gp_core_version_s *args)
{
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT_POINTER((struct mali_session_data *)(uintptr_t)args->ctx);
+
args->version = gp_version;
return _MALI_OSK_ERR_OK;
}
_mali_osk_errcode_t _mali_ukk_gp_suspend_response(_mali_uk_gp_suspend_response_s *args)
{
- struct mali_session_data *session;
struct mali_gp_job *resumed_job;
- _mali_osk_notification_t *new_notification = 0;
+ _mali_osk_notification_t *new_notification = NULL;
MALI_DEBUG_ASSERT_POINTER(args);
- if (NULL == args->ctx) {
- return _MALI_OSK_ERR_INVALID_ARGS;
- }
-
- session = (struct mali_session_data*)args->ctx;
- if (NULL == session) {
- return _MALI_OSK_ERR_FAULT;
- }
-
if (_MALIGP_JOB_RESUME_WITH_NEW_HEAP == args->code) {
new_notification = _mali_osk_notification_create(_MALI_NOTIFICATION_GP_STALLED, sizeof(_mali_uk_gp_job_suspended_s));
mali_group_lock(group);
mali_gp_scheduler_lock();
- MALI_DEBUG_ASSERT( MALI_GROUP_STATE_IDLE == group->state
- || MALI_GROUP_STATE_DISABLED == group->state);
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_IDLE == group->state
+ || MALI_GROUP_STATE_DISABLED == group->state);
if (MALI_GROUP_STATE_DISABLED == group->state) {
MALI_DEBUG_ASSERT(MALI_GP_SLOT_STATE_DISABLED == slot.state);
schedule_mask |= MALI_SCHEDULER_MASK_GP;
}
+ mali_gp_scheduler_job_queued();
+
#if defined(CONFIG_GPU_TRACEPOINTS) && defined(CONFIG_TRACEPOINTS)
trace_gpu_job_enqueue(mali_gp_job_get_tid(job), mali_gp_job_get_id(job), "GP");
#endif
mali_timeline_tracker_release(&job->tracker);
mali_gp_job_signal_pp_tracker(job, MALI_FALSE);
mali_gp_job_delete(job);
- mali_gp_scheduler_job_completed();
+
+ /* Release the PM ref taken in mali_gp_scheduler_submit_job */
+ _mali_osk_pm_dev_ref_dec();
/* Since we are aborting we ignore the scheduler mask. */
return MALI_SCHEDULER_MASK_EMPTY;
static void mali_gp_scheduler_job_queued(void)
{
- /* We hold a PM reference for every job we hold queued (and running) */
- _mali_osk_pm_dev_ref_add();
-
if (mali_utilization_enabled()) {
/*
* We cheat a little bit by counting the PP as busy from the time a GP job is queued.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
return NULL;
}
-_mali_osk_errcode_t mali_group_add_mmu_core(struct mali_group *group, struct mali_mmu_core* mmu_core)
+_mali_osk_errcode_t mali_group_add_mmu_core(struct mali_group *group, struct mali_mmu_core *mmu_core)
{
/* This group object now owns the MMU core object */
- group->mmu= mmu_core;
+ group->mmu = mmu_core;
group->bottom_half_work_mmu = _mali_osk_wq_create_work(mali_group_bottom_half_mmu, group);
if (NULL == group->bottom_half_work_mmu) {
return _MALI_OSK_ERR_FAULT;
}
}
-_mali_osk_errcode_t mali_group_add_gp_core(struct mali_group *group, struct mali_gp_core* gp_core)
+_mali_osk_errcode_t mali_group_add_gp_core(struct mali_group *group, struct mali_gp_core *gp_core)
{
/* This group object now owns the GP core object */
group->gp_core = gp_core;
}
}
-_mali_osk_errcode_t mali_group_add_pp_core(struct mali_group *group, struct mali_pp_core* pp_core)
+_mali_osk_errcode_t mali_group_add_pp_core(struct mali_group *group, struct mali_pp_core *pp_core)
{
/* This group object now owns the PP core object */
group->pp_core = pp_core;
}
}
- /* Update HW only if power is on */
- mali_bcast_reset(parent->bcast_core);
mali_dlbu_update_mask(parent->dlbu_core);
/* Start job on child when parent is active */
if (NULL != parent->pp_running_job) {
struct mali_pp_job *job = parent->pp_running_job;
- MALI_DEBUG_PRINT(3, ("Group %x joining running job %d on virtual group %x\n",
- child, mali_pp_job_get_id(job), parent));
- MALI_DEBUG_ASSERT(MALI_GROUP_STATE_WORKING == parent->state);
- mali_pp_job_start(child->pp_core, job, mali_pp_core_get_id(child->pp_core), MALI_TRUE);
+ u32 subjob = -1;
+
+ if (mali_pp_job_is_with_dlbu(parent->pp_running_job)) {
+ subjob = mali_pp_core_get_id(child->pp_core);
+ }
+
+ /* Take the next unstarted sub job directly without scheduler lock should be
+ * safe here. Because: 1) Virtual group is the only consumer of this job.
+ * 2) Taking next unstarted sub job doesn't do any change to the job queue itself
+ */
+ if (mali_pp_job_has_unstarted_sub_jobs(job)) {
+ subjob = mali_pp_job_get_first_unstarted_sub_job(job);
+ mali_pp_job_mark_sub_job_started(job, subjob);
+ }
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core))|
- MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
- mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
+ if (-1 != subjob) {
+ MALI_DEBUG_PRINT(3, ("Group %x joining running job %d on virtual group %x\n",
+ child, mali_pp_job_get_id(job), parent));
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_WORKING == parent->state);
+ /* Reset broadcast unit only when it will help run subjob */
+ mali_bcast_reset(parent->bcast_core);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core))|
- MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
- mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+ mali_group_start_job_on_group(child, job, subjob);
+
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
+
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
+ mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_pp_job_get_pid(job), 1 /* active */, 0 /* PP */, mali_pp_core_get_id(child->pp_core),
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job));
+#endif
+ }
}
MALI_DEBUG_CODE(mali_group_print_virtual(parent);)
}
}
-struct mali_gp_core* mali_group_get_gp_core(struct mali_group *group)
+/* This function is called before running a job on virtual group
+ * Remove some child group from the bcast mask necessarily
+ * Set child groups particular registers respectively etc
+ */
+static void mali_group_job_prepare_virtual(struct mali_group *group, struct mali_pp_job *job,
+ u32 first_subjob, u32 last_subjob)
+{
+ struct mali_group *child;
+ struct mali_group *temp;
+ u32 subjob = first_subjob;
+
+ MALI_DEBUG_ASSERT_POINTER(job);
+ MALI_DEBUG_ASSERT(mali_pp_job_is_virtual_group_job(job));
+
+ MALI_DEBUG_ASSERT_POINTER(group);
+ MALI_DEBUG_ASSERT(mali_group_is_virtual(group));
+ MALI_ASSERT_GROUP_LOCKED(group);
+
+ MALI_DEBUG_ASSERT(first_subjob <= last_subjob);
+
+ /* Set each core specific registers:
+ * 1. Renderer List Address
+ * 2. Fragment Shader Stack Address
+ * Other general registers are set through Broadcast Unit in one go.
+ * Note: for Addtional temporary unused group core in virtual group
+ * we need to remove it from Broadcast Unit before start the job in
+ * this virtual group, otherwise, we may never get Frame_end interrupt.
+ */
+ if (!mali_pp_job_is_with_dlbu(job)) {
+ _MALI_OSK_LIST_FOREACHENTRY(child, temp, &group->group_list, struct mali_group, group_list) {
+ if (subjob <= last_subjob) {
+ /* Write specific Renderer List Address for each group */
+ mali_pp_write_addr_renderer_list(child->pp_core, job, subjob);
+ /* Write specific stack address for each child group */
+ mali_pp_write_addr_stack(child->pp_core, job, subjob);
+ subjob++;
+ MALI_DEBUG_PRINT(4, ("Mali Virtual Group: Virtual group job %u (0x%08X) part %u/%u started.\n",
+ mali_pp_job_get_id(job), job, subjob,
+ mali_pp_job_get_sub_job_count(job)));
+ } else {
+ /* Some physical group are just redundant for this run
+ * remove it from broadcast
+ */
+ mali_bcast_remove_group(group->bcast_core, child);
+ MALI_DEBUG_PRINT(4, ("Mali Virtual Group: Remained PP group %p remove from bcast_core\n", child));
+ }
+ }
+
+ /* Reset broadcast */
+ mali_bcast_reset(group->bcast_core);
+ } else {
+ /* Write stack address for each child group */
+ _MALI_OSK_LIST_FOREACHENTRY(child, temp, &group->group_list, struct mali_group, group_list) {
+ mali_pp_write_addr_stack(child->pp_core, job, child->pp_core->core_id);
+ mali_bcast_add_group(group->bcast_core, child);
+ }
+
+ /* Reset broadcast */
+ mali_bcast_reset(group->bcast_core);
+
+ mali_dlbu_config_job(group->dlbu_core, job);
+
+ /* Write Renderer List Address for each child group */
+ mali_pp_write_addr_renderer_list(group->pp_core, job, 0);
+
+ MALI_DEBUG_PRINT(4, ("Mali Virtual Group: Virtual job %u (0x%08X) part %u/%u started (from schedule).\n",
+ mali_pp_job_get_id(job), job, 1,
+ mali_pp_job_get_sub_job_count(job)));
+ }
+}
+
+/* Call this function to make sure group->group_list are consistent with the group->broad_core mask */
+void mali_group_non_dlbu_job_done_virtual(struct mali_group *group)
+{
+ struct mali_group *child, *temp;
+
+ MALI_ASSERT_GROUP_LOCKED(group);
+ MALI_DEBUG_ASSERT(mali_group_is_virtual(group));
+
+ _MALI_OSK_LIST_FOREACHENTRY(child, temp,
+ &group->group_list, struct mali_group, group_list) {
+ mali_bcast_add_group(group->bcast_core, child);
+ }
+
+ MALI_DEBUG_PRINT(3, ("Mali group: New physical groups added in virtual group at non dlbu job done"));
+ /**
+ * When new physical groups added in the virtual groups, they may have different
+ * page directory with the virtual group. Here just activate the empty page directory
+ * for the virtual group to avoid potential inconsistent page directory.
+ */
+ mali_mmu_activate_empty_page_directory(group->mmu);
+ group->session = NULL;
+}
+
+struct mali_gp_core *mali_group_get_gp_core(struct mali_group *group)
{
return group->gp_core;
}
-struct mali_pp_core* mali_group_get_pp_core(struct mali_group *group)
+struct mali_pp_core *mali_group_get_pp_core(struct mali_group *group)
{
return group->pp_core;
}
mali_gp_job_start(group->gp_core, job);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0) |
- MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
- mali_gp_job_get_frame_builder_id(job), mali_gp_job_get_flush_id(job), 0, 0, 0);
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0) |
+ MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
+ mali_gp_job_get_frame_builder_id(job), mali_gp_job_get_flush_id(job), 0, 0, 0);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
- MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
- mali_gp_job_get_pid(job), mali_gp_job_get_tid(job), 0, 0, 0);
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
+ mali_gp_job_get_pid(job), mali_gp_job_get_tid(job), 0, 0, 0);
+
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_gp_job_get_pid(job), 1 /* active */, 1 /* GP */, 0 /* core */,
+ mali_gp_job_get_frame_builder_id(job), mali_gp_job_get_flush_id(job));
+#endif
+
#if defined(CONFIG_MALI400_PROFILING)
if ((MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src0(group->l2_cache_core[0])) &&
(MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src1(group->l2_cache_core[0])))
#if defined(CONFIG_GPU_TRACEPOINTS) && defined(CONFIG_TRACEPOINTS)
trace_gpu_sched_switch(mali_gp_get_hw_core_desc(group->gp_core), sched_clock(),
- mali_gp_job_get_pid(job), 0, mali_gp_job_get_id(job));
+ mali_gp_job_get_pid(job), 0, mali_gp_job_get_id(job));
#endif
group->gp_running_job = job;
_mali_osk_timer_mod(group->timeout_timer, _mali_osk_time_mstoticks(mali_max_job_runtime));
}
-void mali_group_start_pp_job(struct mali_group *group, struct mali_pp_job *job, u32 sub_job)
+/* Used to set all the registers except frame renderer list address and fragment shader stack address
+ * It means the caller must set these two registers properly before calling this function
+ */
+static void mali_group_start_pp_job(struct mali_group *group, struct mali_pp_job *job, u32 sub_job)
{
struct mali_session_data *session;
mali_group_activate_page_directory(group, session);
if (mali_group_is_virtual(group)) {
- struct mali_group *child;
- struct mali_group *temp;
- u32 core_num = 0;
-
- MALI_DEBUG_ASSERT( mali_pp_job_is_virtual(job));
-
- /* Configure DLBU for the job */
- mali_dlbu_config_job(group->dlbu_core, job);
-
- /* Write stack address for each child group */
- _MALI_OSK_LIST_FOREACHENTRY(child, temp, &group->group_list, struct mali_group, group_list) {
- mali_pp_write_addr_stack(child->pp_core, job);
- core_num++;
- }
+ MALI_DEBUG_ASSERT(mali_pp_job_is_virtual_group_job(job));
/* Try to use DMA unit to start job, fallback to writing directly to the core */
MALI_DEBUG_ASSERT(mali_dma_cmd_buf_is_valid(&job->dma_cmd_buf));
if (_MALI_OSK_ERR_OK != mali_dma_start(mali_dma_get_global_dma_core(), &job->dma_cmd_buf)) {
- mali_pp_job_start(group->pp_core, job, sub_job, MALI_FALSE);
+ mali_pp_job_start(group->pp_core, job, sub_job);
}
} else {
- mali_pp_job_start(group->pp_core, job, sub_job, MALI_FALSE);
+ mali_pp_job_start(group->pp_core, job, sub_job);
}
/* if the group is virtual, loop through physical groups which belong to this group
struct mali_group *temp;
_MALI_OSK_LIST_FOREACHENTRY(child, temp, &group->group_list, struct mali_group, group_list) {
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core))|
- MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
- mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
-
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core))|
- MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
- mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
+
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
+ mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_pp_job_get_pid(job), 1 /* active */, 0 /* PP */, mali_pp_core_get_id(child->pp_core),
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job));
+#endif
}
#if defined(CONFIG_MALI400_PROFILING)
if (0 != group->l2_cache_core_ref_count[0]) {
}
#endif /* #if defined(CONFIG_MALI400_PROFILING) */
} else { /* group is physical - call profiling events for physical cores */
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core))|
- MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
- mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
-
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core))|
- MALI_PROFILING_EVENT_REASON_START_STOP_HW_PHYSICAL,
- mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_SINGLE_HW_FLUSH,
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job), 0, 0, 0);
+
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_START_STOP_HW_PHYSICAL,
+ mali_pp_job_get_pid(job), mali_pp_job_get_tid(job), 0, 0, 0);
+
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_pp_job_get_pid(job), 1 /* active */, 0 /* PP */, mali_pp_core_get_id(group->pp_core),
+ mali_pp_job_get_frame_builder_id(job), mali_pp_job_get_flush_id(job));
+#endif
+
#if defined(CONFIG_MALI400_PROFILING)
if ((MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src0(group->l2_cache_core[0])) &&
(MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src1(group->l2_cache_core[0]))) {
_mali_osk_timer_mod(group->timeout_timer, _mali_osk_time_mstoticks(mali_max_job_runtime));
}
+void mali_group_start_job_on_virtual(struct mali_group *group, struct mali_pp_job *job,
+ u32 first_subjob, u32 last_subjob)
+{
+ MALI_DEBUG_ASSERT_POINTER(job);
+ MALI_DEBUG_ASSERT(mali_pp_job_is_virtual_group_job(job));
+
+ MALI_DEBUG_ASSERT_POINTER(group);
+ MALI_DEBUG_ASSERT(mali_group_is_virtual(group));
+ MALI_ASSERT_GROUP_LOCKED(group);
+
+ MALI_DEBUG_ASSERT(first_subjob <= last_subjob);
+
+ /* Prepare the group for running this job */
+ mali_group_job_prepare_virtual(group, job, first_subjob, last_subjob);
+
+ /* Start job. General setting for all the PP cores */
+ mali_group_start_pp_job(group, job, first_subjob);
+}
+
+void mali_group_start_job_on_group(struct mali_group *group, struct mali_pp_job *job, u32 subjob)
+{
+ MALI_DEBUG_ASSERT_POINTER(group);
+ MALI_DEBUG_ASSERT(!mali_group_is_virtual(group));
+ MALI_DEBUG_ASSERT_POINTER(job);
+
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_IDLE == group->state || MALI_GROUP_STATE_IN_VIRTUAL == group->state);
+
+ /*
+ * There are two frame registers which are different for each sub job:
+ * 1. The Renderer List Address Register (MALI200_REG_ADDR_FRAME)
+ * 2. The FS Stack Address Register (MALI200_REG_ADDR_STACK)
+ */
+ mali_pp_write_addr_renderer_list(group->pp_core, job, subjob);
+
+ /* Write specific stack address for each child group */
+ mali_pp_write_addr_stack(group->pp_core, job, subjob);
+
+ /* For start a job in a group which is just joining the virtual group
+ * just start the job directly, all the accouting information and state
+ * updates have been covered by virtual group state
+ */
+ if (MALI_GROUP_STATE_IN_VIRTUAL == group->state) {
+ mali_pp_job_start(group->pp_core, job, subjob);
+ return;
+ }
+
+ /* Start job. General setting for all the PP cores */
+ mali_group_start_pp_job(group, job, subjob);
+}
+
+
+
struct mali_gp_job *mali_group_resume_gp_with_new_heap(struct mali_group *group, u32 job_id, u32 start_addr, u32 end_addr)
{
MALI_ASSERT_GROUP_LOCKED(group);
mali_gp_resume_with_new_heap(group->gp_core, start_addr, end_addr);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_RESUME|MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0), 0, 0, 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_RESUME | MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0), 0, 0, 0, 0, 0);
+
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_gp_job_get_pid(group->gp_running_job), 1 /* active */, 1 /* GP */, 0 /* core */,
+ mali_gp_job_get_frame_builder_id(group->gp_running_job), mali_gp_job_get_flush_id(group->gp_running_job));
+#endif
group->state = MALI_GROUP_STATE_WORKING;
struct mali_group *mali_group_get_glob_group(u32 index)
{
- if(mali_global_num_groups > index) {
+ if (mali_global_num_groups > index) {
return mali_global_groups[index];
}
{
MALI_DEBUG_ASSERT_POINTER(group);
MALI_DEBUG_ASSERT_LOCK_HELD(group->lock);
- MALI_DEBUG_ASSERT( MALI_GROUP_STATE_IDLE == group->state
- || MALI_GROUP_STATE_IN_VIRTUAL == group->state
- || MALI_GROUP_STATE_JOINING_VIRTUAL == group->state
- || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
- || MALI_GROUP_STATE_DISABLED == group->state);
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_IDLE == group->state
+ || MALI_GROUP_STATE_IN_VIRTUAL == group->state
+ || MALI_GROUP_STATE_JOINING_VIRTUAL == group->state
+ || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
+ || MALI_GROUP_STATE_DISABLED == group->state);
MALI_DEBUG_PRINT(3, ("Group %p powered on\n", group));
{
MALI_DEBUG_ASSERT_POINTER(group);
MALI_DEBUG_ASSERT_LOCK_HELD(group->lock);
- MALI_DEBUG_ASSERT( MALI_GROUP_STATE_IDLE == group->state
- || MALI_GROUP_STATE_IN_VIRTUAL == group->state
- || MALI_GROUP_STATE_JOINING_VIRTUAL == group->state
- || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
- || MALI_GROUP_STATE_DISABLED == group->state);
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_IDLE == group->state
+ || MALI_GROUP_STATE_IN_VIRTUAL == group->state
+ || MALI_GROUP_STATE_JOINING_VIRTUAL == group->state
+ || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
+ || MALI_GROUP_STATE_DISABLED == group->state);
MALI_DEBUG_PRINT(3, ("Group %p powered off\n", group));
if (group->pp_core) {
n += mali_pp_dump_state(group->pp_core, buf + n, size - n);
n += _mali_osk_snprintf(buf + n, size - n, "\tPP job: %p, subjob %d \n",
- group->pp_running_job, group->pp_running_sub_job);
+ group->pp_running_job, group->pp_running_sub_job);
}
return n;
MALI_SUCCESS;
}
#endif
+#if defined(CONFIG_MALI_SHARED_INTERRUPTS)
+ if (MALI_FALSE == mali_pm_domain_lock_state(group->pm_domain)) {
+ goto out;
+ }
+#endif
/* Check if it was our device which caused the interrupt (we could be sharing the IRQ line) */
int_stat = mali_mmu_get_int_status(mmu);
return err;
}
-static void mali_group_bottom_half_mmu(void * data)
+static void mali_group_bottom_half_mmu(void *data)
{
struct mali_group *group = (struct mali_group *)data;
struct mali_mmu_core *mmu = group->mmu;
MALI_DEBUG_ASSERT(NULL == group->parent_group);
- if ( MALI_FALSE == mali_group_power_is_on(group) ) {
+ if (MALI_FALSE == mali_group_power_is_on(group)) {
MALI_PRINT_ERROR(("Interrupt bottom half of %s when core is OFF.", mmu->hw_core.description));
mali_group_unlock(group);
return;
/* An actual page fault has occurred. */
#ifdef DEBUG
u32 fault_address = mali_mmu_get_page_fault_addr(mmu);
- MALI_DEBUG_PRINT(2,("Mali MMU: Page fault detected at 0x%x from bus id %d of type %s on %s\n",
- (void*)fault_address,
- (status >> 6) & 0x1F,
- (status & 32) ? "write" : "read",
- mmu->hw_core.description));
+ MALI_DEBUG_PRINT(2, ("Mali MMU: Page fault detected at 0x%08x from bus id %d of type %s on %s\n",
+ fault_address,
+ (status >> 6) & 0x1F,
+ (status & 32) ? "write" : "read",
+ mmu->hw_core.description));
+ mali_mmu_pagedir_diag(group->session->page_directory, fault_address);
#endif
mali_group_mmu_page_fault_and_unlock(group);
/* Mask out all IRQs from this core until IRQ is handled */
mali_gp_mask_all_interrupts(core);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE|MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0)|MALI_PROFILING_EVENT_REASON_SINGLE_HW_INTERRUPT, irq_readout, 0, 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE | MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0) | MALI_PROFILING_EVENT_REASON_SINGLE_HW_INTERRUPT, irq_readout, 0, 0, 0, 0);
/* We do need to handle this in a bottom half */
_mali_osk_wq_schedule_work(group->bottom_half_work_gp);
u32 irq_readout;
u32 irq_errors;
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START|MALI_PROFILING_EVENT_CHANNEL_SOFTWARE|MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), MALI_PROFILING_MAKE_EVENT_DATA_CORE_GP(0), 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START | MALI_PROFILING_EVENT_CHANNEL_SOFTWARE | MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), MALI_PROFILING_MAKE_EVENT_DATA_CORE_GP(0), 0, 0);
mali_group_lock(group);
- if ( MALI_FALSE == mali_group_power_is_on(group) ) {
+ if (MALI_FALSE == mali_group_power_is_on(group)) {
MALI_PRINT_ERROR(("Mali group: Interrupt bottom half of %s when core is OFF.", mali_gp_get_hw_core_desc(group->gp_core)));
mali_group_unlock(group);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|MALI_PROFILING_EVENT_CHANNEL_SOFTWARE|MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP | MALI_PROFILING_EVENT_CHANNEL_SOFTWARE | MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
MALI_DEBUG_PRINT(4, ("Mali group: GP bottom half IRQ 0x%08X from core %s\n", irq_readout, mali_gp_get_hw_core_desc(group->gp_core)));
- if (irq_readout & (MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST|MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST)) {
+ if (irq_readout & (MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST)) {
u32 core_status = mali_gp_read_core_status(group->gp_core);
if (0 == (core_status & MALIGP2_REG_VAL_STATUS_MASK_ACTIVE)) {
MALI_DEBUG_PRINT(4, ("Mali group: GP job completed, calling group handler\n"));
group->core_timed_out = MALI_FALSE;
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
mali_group_complete_gp_and_unlock(group, MALI_TRUE);
return;
* Now lets look at the possible error cases (IRQ indicating error or timeout)
* END_CMD_LST, HANG and PLBU_OOM interrupts are not considered error.
*/
- irq_errors = irq_readout & ~(MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST|MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST|MALIGP2_REG_VAL_IRQ_HANG|MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM);
+ irq_errors = irq_readout & ~(MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | MALIGP2_REG_VAL_IRQ_HANG | MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM);
if (0 != irq_errors) {
MALI_PRINT_ERROR(("Mali group: Unknown interrupt 0x%08X from core %s, aborting job\n", irq_readout, mali_gp_get_hw_core_desc(group->gp_core)));
group->core_timed_out = MALI_FALSE;
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
mali_group_complete_gp_and_unlock(group, MALI_FALSE);
return;
group->state = MALI_GROUP_STATE_OOM;
mali_group_unlock(group); /* Nothing to do on the HW side, so just release group lock right away */
mali_gp_scheduler_oom(group, group->gp_running_job);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|MALI_PROFILING_EVENT_CHANNEL_SOFTWARE|MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP | MALI_PROFILING_EVENT_CHANNEL_SOFTWARE | MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
* interrupts. Enable all but not the complete interrupt that has been
* received and continue to run.
*/
- mali_gp_enable_interrupts(group->gp_core, irq_readout & (MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST|MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST));
+ mali_gp_enable_interrupts(group->gp_core, irq_readout & (MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST));
mali_group_unlock(group);
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|MALI_PROFILING_EVENT_CHANNEL_SOFTWARE|MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP | MALI_PROFILING_EVENT_CHANNEL_SOFTWARE | MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF, 0, _mali_osk_get_tid(), 0, 0, 0);
}
static void mali_group_post_process_job_gp(struct mali_group *group, mali_bool suspend)
#if defined(CONFIG_MALI400_PROFILING)
if (suspend) {
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SUSPEND|MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
- mali_gp_job_get_perf_counter_value0(group->gp_running_job),
- mali_gp_job_get_perf_counter_value1(group->gp_running_job),
- mali_gp_job_get_perf_counter_src0(group->gp_running_job) | (mali_gp_job_get_perf_counter_src1(group->gp_running_job) << 8),
- 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SUSPEND | MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
+ mali_gp_job_get_perf_counter_value0(group->gp_running_job),
+ mali_gp_job_get_perf_counter_value1(group->gp_running_job),
+ mali_gp_job_get_perf_counter_src0(group->gp_running_job) | (mali_gp_job_get_perf_counter_src1(group->gp_running_job) << 8),
+ 0, 0);
} else {
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
- mali_gp_job_get_perf_counter_value0(group->gp_running_job),
- mali_gp_job_get_perf_counter_value1(group->gp_running_job),
- mali_gp_job_get_perf_counter_src0(group->gp_running_job) | (mali_gp_job_get_perf_counter_src1(group->gp_running_job) << 8),
- 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP | MALI_PROFILING_MAKE_EVENT_CHANNEL_GP(0),
+ mali_gp_job_get_perf_counter_value0(group->gp_running_job),
+ mali_gp_job_get_perf_counter_value1(group->gp_running_job),
+ mali_gp_job_get_perf_counter_src0(group->gp_running_job) | (mali_gp_job_get_perf_counter_src1(group->gp_running_job) << 8),
+ 0, 0);
if ((MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src0(group->l2_cache_core[0])) &&
(MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src1(group->l2_cache_core[0])))
}
#endif
+#if defined(CONFIG_MALI400_PROFILING)
+ trace_mali_core_active(mali_gp_job_get_pid(group->gp_running_job), 0 /* active */, 1 /* GP */, 0 /* core */,
+ mali_gp_job_get_frame_builder_id(group->gp_running_job), mali_gp_job_get_flush_id(group->gp_running_job));
+#endif
+
mali_gp_job_set_current_heap_addr(group->gp_running_job,
- mali_gp_read_plbu_alloc_start_addr(group->gp_core));
+ mali_gp_read_plbu_alloc_start_addr(group->gp_core));
}
_mali_osk_errcode_t mali_group_upper_half_pp(void *data)
/* Currently no support for this interrupt event for the virtual PP core */
if (!mali_group_is_virtual(group)) {
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(core->core_id) |
- MALI_PROFILING_EVENT_REASON_SINGLE_HW_INTERRUPT,
- irq_readout, 0, 0, 0, 0);
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(core->core_id) |
+ MALI_PROFILING_EVENT_REASON_SINGLE_HW_INTERRUPT,
+ irq_readout, 0, 0, 0, 0);
}
#endif
/* Check if job is complete without errors */
if (MALI200_REG_VAL_IRQ_END_OF_FRAME == irq_readout) {
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
- 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
+ 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
MALI_DEBUG_PRINT(3, ("Mali PP: Job completed, calling group handler from upper half\n"));
mali_pp_enable_interrupts(core);
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
- 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
+ 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
err = _MALI_OSK_ERR_OK;
goto out;
}
mali_pp_enable_interrupts(core);
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
- 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
+ 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
err = _MALI_OSK_ERR_OK;
goto out;
}
mali_pp_enable_interrupts(core);
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
- 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
+ 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
err = _MALI_OSK_ERR_FAULT;
goto out;
}
MALI_DEBUG_PRINT(6, ("Mali PP: Upper half job done\n"));
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
- 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_UPPER_HALF,
+ 0, 0, MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
err = _MALI_OSK_ERR_OK;
goto out;
u32 irq_errors;
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_START |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), MALI_PROFILING_MAKE_EVENT_DATA_CORE_PP(core->core_id), 0, 0);
mali_group_lock(group);
mali_pp_enable_interrupts(core);
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
- if ( MALI_FALSE == mali_group_power_is_on(group) ) {
+ if (MALI_FALSE == mali_group_power_is_on(group)) {
MALI_PRINT_ERROR(("Interrupt bottom half of %s when core is OFF.", mali_pp_get_hw_core_desc(core)));
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
}
mali_group_complete_pp_and_unlock(group, MALI_TRUE, MALI_FALSE);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
}
* Now lets look at the possible error cases (IRQ indicating error or timeout)
* END_OF_FRAME and HANG interrupts are not considered error.
*/
- irq_errors = irq_readout & ~(MALI200_REG_VAL_IRQ_END_OF_FRAME|MALI200_REG_VAL_IRQ_HANG);
+ irq_errors = irq_readout & ~(MALI200_REG_VAL_IRQ_END_OF_FRAME | MALI200_REG_VAL_IRQ_HANG);
if (0 != irq_errors) {
MALI_PRINT_ERROR(("Mali PP: Unexpected interrupt 0x%08X from core %s, aborting job\n",
- irq_readout, mali_pp_get_hw_core_desc(group->pp_core)));
+ irq_readout, mali_pp_get_hw_core_desc(group->pp_core)));
group->core_timed_out = MALI_FALSE;
mali_group_complete_pp_and_unlock(group, MALI_FALSE, MALI_FALSE);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
} else if (group->core_timed_out) { /* SW timeout */
group->core_timed_out = MALI_FALSE;
if (!_mali_osk_timer_pending(group->timeout_timer) && NULL != group->pp_running_job) {
MALI_PRINT(("Mali PP: Job %d timed out on core %s\n",
- mali_pp_job_get_id(group->pp_running_job), mali_pp_get_hw_core_desc(core)));
+ mali_pp_job_get_id(group->pp_running_job), mali_pp_get_hw_core_desc(core)));
mali_group_complete_pp_and_unlock(group, MALI_FALSE, MALI_FALSE);
} else {
}
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
return;
}
*/
if (0 == irq_readout) {
MALI_DEBUG_PRINT(3, ("Mali group: No interrupt found on core %s\n",
- mali_pp_get_hw_core_desc(group->pp_core)));
+ mali_pp_get_hw_core_desc(group->pp_core)));
} else {
MALI_PRINT_ERROR(("Mali group: Unhandled PP interrupt 0x%08X on %s\n", irq_readout,
- mali_pp_get_hw_core_desc(group->pp_core)));
+ mali_pp_get_hw_core_desc(group->pp_core)));
}
mali_pp_enable_interrupts(core);
mali_group_unlock(group);
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
- 0, _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_START_STOP_SW_BOTTOM_HALF,
+ 0, _mali_osk_get_tid(), 0, 0, 0);
}
static void mali_group_post_process_job_pp(struct mali_group *group)
#if defined(CONFIG_MALI400_PROFILING)
/* send profiling data per physical core */
_MALI_OSK_LIST_FOREACHENTRY(child, temp, &group->group_list, struct mali_group, group_list) {
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core))|
- MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
- mali_pp_job_get_perf_counter_value0(group->pp_running_job, mali_pp_core_get_id(child->pp_core)),
- mali_pp_job_get_perf_counter_value1(group->pp_running_job, mali_pp_core_get_id(child->pp_core)),
- mali_pp_job_get_perf_counter_src0(group->pp_running_job, group->pp_running_sub_job) | (mali_pp_job_get_perf_counter_src1(group->pp_running_job, group->pp_running_sub_job) << 8),
- 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(child->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_START_STOP_HW_VIRTUAL,
+ mali_pp_job_get_perf_counter_value0(group->pp_running_job, mali_pp_core_get_id(child->pp_core)),
+ mali_pp_job_get_perf_counter_value1(group->pp_running_job, mali_pp_core_get_id(child->pp_core)),
+ mali_pp_job_get_perf_counter_src0(group->pp_running_job, group->pp_running_sub_job) | (mali_pp_job_get_perf_counter_src1(group->pp_running_job, group->pp_running_sub_job) << 8),
+ 0, 0);
+
+ trace_mali_core_active(mali_pp_job_get_pid(group->pp_running_job),
+ 0 /* active */, 0 /* PP */, mali_pp_core_get_id(child->pp_core),
+ mali_pp_job_get_frame_builder_id(group->pp_running_job),
+ mali_pp_job_get_flush_id(group->pp_running_job));
}
if (0 != group->l2_cache_core_ref_count[0]) {
if ((MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src0(group->l2_cache_core[0])) &&
mali_pp_update_performance_counters(group->pp_core, group->pp_core, group->pp_running_job, group->pp_running_sub_job);
#if defined(CONFIG_MALI400_PROFILING)
- _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP|
- MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core))|
- MALI_PROFILING_EVENT_REASON_START_STOP_HW_PHYSICAL,
- mali_pp_job_get_perf_counter_value0(group->pp_running_job, group->pp_running_sub_job),
- mali_pp_job_get_perf_counter_value1(group->pp_running_job, group->pp_running_sub_job),
- mali_pp_job_get_perf_counter_src0(group->pp_running_job, group->pp_running_sub_job) | (mali_pp_job_get_perf_counter_src1(group->pp_running_job, group->pp_running_sub_job) << 8),
- 0, 0);
+ _mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_STOP |
+ MALI_PROFILING_MAKE_EVENT_CHANNEL_PP(mali_pp_core_get_id(group->pp_core)) |
+ MALI_PROFILING_EVENT_REASON_START_STOP_HW_PHYSICAL,
+ mali_pp_job_get_perf_counter_value0(group->pp_running_job, group->pp_running_sub_job),
+ mali_pp_job_get_perf_counter_value1(group->pp_running_job, group->pp_running_sub_job),
+ mali_pp_job_get_perf_counter_src0(group->pp_running_job, group->pp_running_sub_job) | (mali_pp_job_get_perf_counter_src1(group->pp_running_job, group->pp_running_sub_job) << 8),
+ 0, 0);
+
+ trace_mali_core_active(mali_pp_job_get_pid(group->pp_running_job), 0 /* active */, 0 /* PP */, mali_pp_core_get_id(group->pp_core),
+ mali_pp_job_get_frame_builder_id(group->pp_running_job), mali_pp_job_get_flush_id(group->pp_running_job));
if ((MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src0(group->l2_cache_core[0])) &&
(MALI_HW_CORE_NO_COUNTER != mali_l2_cache_core_get_counter_src1(group->l2_cache_core[0]))) {
u32 value1 = 0;
u32 profiling_channel = 0;
- switch(core_num) {
+ switch (core_num) {
case 0:
profiling_channel = MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_EVENT_CHANNEL_GPU |
- MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L20_COUNTERS;
+ MALI_PROFILING_EVENT_CHANNEL_GPU |
+ MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L20_COUNTERS;
break;
case 1:
profiling_channel = MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_EVENT_CHANNEL_GPU |
- MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L21_COUNTERS;
+ MALI_PROFILING_EVENT_CHANNEL_GPU |
+ MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L21_COUNTERS;
break;
case 2:
profiling_channel = MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_EVENT_CHANNEL_GPU |
- MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L22_COUNTERS;
+ MALI_PROFILING_EVENT_CHANNEL_GPU |
+ MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L22_COUNTERS;
break;
default:
profiling_channel = MALI_PROFILING_EVENT_TYPE_SINGLE |
- MALI_PROFILING_EVENT_CHANNEL_GPU |
- MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L20_COUNTERS;
+ MALI_PROFILING_EVENT_CHANNEL_GPU |
+ MALI_PROFILING_EVENT_REASON_SINGLE_GPU_L20_COUNTERS;
break;
}
void mali_group_enable(struct mali_group *group)
{
MALI_DEBUG_ASSERT_POINTER(group);
- MALI_DEBUG_ASSERT( NULL != mali_group_get_pp_core(group)
- || NULL != mali_group_get_gp_core(group));
+ MALI_DEBUG_ASSERT(NULL != mali_group_get_pp_core(group)
+ || NULL != mali_group_get_gp_core(group));
if (NULL != mali_group_get_pp_core(group)) {
mali_pp_scheduler_enable_group(group);
void mali_group_disable(struct mali_group *group)
{
MALI_DEBUG_ASSERT_POINTER(group);
- MALI_DEBUG_ASSERT( NULL != mali_group_get_pp_core(group)
- || NULL != mali_group_get_gp_core(group));
+ MALI_DEBUG_ASSERT(NULL != mali_group_get_pp_core(group)
+ || NULL != mali_group_get_gp_core(group));
if (NULL != mali_group_get_pp_core(group)) {
mali_pp_scheduler_disable_group(group);
}
}
-static struct mali_pm_domain* mali_group_get_l2_domain(struct mali_group *group)
+static struct mali_pm_domain *mali_group_get_l2_domain(struct mali_group *group)
{
MALI_DEBUG_ASSERT(NULL == group->l2_cache_core[1]);
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct mali_bcast_unit *bcast_core;
#ifdef MALI_UPPER_HALF_SCHEDULING
- _mali_osk_spinlock_irq_t *lock;
+ _mali_osk_spinlock_irq_t *lock;
#else
- _mali_osk_spinlock_t *lock;
+ _mali_osk_spinlock_t *lock;
#endif
_mali_osk_list_t pp_scheduler_list;
* @return A pointer to a new group object
*/
struct mali_group *mali_group_create(struct mali_l2_cache_core *core,
- struct mali_dlbu_core *dlbu,
- struct mali_bcast_unit *bcast);
+ struct mali_dlbu_core *dlbu,
+ struct mali_bcast_unit *bcast);
-_mali_osk_errcode_t mali_group_add_mmu_core(struct mali_group *group, struct mali_mmu_core* mmu_core);
+_mali_osk_errcode_t mali_group_add_mmu_core(struct mali_group *group, struct mali_mmu_core *mmu_core);
void mali_group_remove_mmu_core(struct mali_group *group);
-_mali_osk_errcode_t mali_group_add_gp_core(struct mali_group *group, struct mali_gp_core* gp_core);
+_mali_osk_errcode_t mali_group_add_gp_core(struct mali_group *group, struct mali_gp_core *gp_core);
void mali_group_remove_gp_core(struct mali_group *group);
-_mali_osk_errcode_t mali_group_add_pp_core(struct mali_group *group, struct mali_pp_core* pp_core);
+_mali_osk_errcode_t mali_group_add_pp_core(struct mali_group *group, struct mali_pp_core *pp_core);
void mali_group_remove_pp_core(struct mali_group *group);
void mali_group_set_pm_domain(struct mali_group *group, struct mali_pm_domain *domain);
{
#if defined(CONFIG_MALI450)
return (MALI_GROUP_STATE_IN_VIRTUAL == group->state ||
- MALI_GROUP_STATE_JOINING_VIRTUAL == group->state ||
- MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state);
+ MALI_GROUP_STATE_JOINING_VIRTUAL == group->state ||
+ MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state);
#else
return MALI_FALSE;
#endif
*
* Zap TLB on group if \a session is active.
*/
-void mali_group_zap_session(struct mali_group* group, struct mali_session_data *session);
+void mali_group_zap_session(struct mali_group *group, struct mali_session_data *session);
/** @brief Get pointer to GP core object
*/
-struct mali_gp_core* mali_group_get_gp_core(struct mali_group *group);
+struct mali_gp_core *mali_group_get_gp_core(struct mali_group *group);
/** @brief Get pointer to PP core object
*/
-struct mali_pp_core* mali_group_get_pp_core(struct mali_group *group);
+struct mali_pp_core *mali_group_get_pp_core(struct mali_group *group);
/** @brief Lock group object
*
/** @brief Start GP job
*/
void mali_group_start_gp_job(struct mali_group *group, struct mali_gp_job *job);
-/** @brief Start fragment of PP job
+
+/** @brief Start virtual group Job on a virtual group
+*/
+void mali_group_start_job_on_virtual(struct mali_group *group, struct mali_pp_job *job, u32 first_subjob, u32 last_subjob);
+
+
+/** @brief Start a subjob from a particular on a specific PP group
+*/
+void mali_group_start_job_on_group(struct mali_group *group, struct mali_pp_job *job, u32 subjob);
+
+
+/** @brief remove all the unused groups in tmp_unused group list, so that the group is in consistent status.
*/
-void mali_group_start_pp_job(struct mali_group *group, struct mali_pp_job *job, u32 sub_job);
+void mali_group_non_dlbu_job_done_virtual(struct mali_group *group);
+
/** @brief Resume GP job that suspended waiting for more heap memory
*/
u32 mali_group_dump_state(struct mali_group *group, char *buf, u32 size);
/* MMU-related functions */
-_mali_osk_errcode_t mali_group_upper_half_mmu(void * data);
+_mali_osk_errcode_t mali_group_upper_half_mmu(void *data);
/* GP-related functions */
_mali_osk_errcode_t mali_group_upper_half_gp(void *data);
return empty;
}
+
/* Get group used l2 domain and core domain ref */
void mali_group_get_pm_domain_ref(struct mali_group *group);
/* Put group used l2 domain and core domain ref */
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
u32 phys_offset; /**< Offset from start of Mali to registers */
u32 size; /**< Size of registers */
mali_io_address mapped_registers; /**< Virtual mapping of the registers */
- const char* description; /**< Name of unit (as specified in device configuration) */
+ const char *description; /**< Name of unit (as specified in device configuration) */
};
#define MALI_REG_POLL_COUNT_FAST 1000
u32 read_val;
read_val = _mali_osk_mem_ioread32(core->mapped_registers, relative_address);
MALI_DEBUG_PRINT(6, ("register_read for core %s, relative addr=0x%04X, val=0x%08X\n",
- core->description, relative_address, read_val));
+ core->description, relative_address, read_val));
return read_val;
}
MALI_STATIC_INLINE void mali_hw_core_register_write_relaxed(struct mali_hw_core *core, u32 relative_address, u32 new_val)
{
MALI_DEBUG_PRINT(6, ("register_write_relaxed for core %s, relative addr=0x%04X, val=0x%08X\n",
- core->description, relative_address, new_val));
+ core->description, relative_address, new_val));
_mali_osk_mem_iowrite32_relaxed(core->mapped_registers, relative_address, new_val);
}
MALI_STATIC_INLINE void mali_hw_core_register_write_relaxed_conditional(struct mali_hw_core *core, u32 relative_address, u32 new_val, const u32 old_val)
{
MALI_DEBUG_PRINT(6, ("register_write_relaxed for core %s, relative addr=0x%04X, val=0x%08X\n",
- core->description, relative_address, new_val));
- if(old_val != new_val) {
+ core->description, relative_address, new_val));
+ if (old_val != new_val) {
_mali_osk_mem_iowrite32_relaxed(core->mapped_registers, relative_address, new_val);
}
}
MALI_STATIC_INLINE void mali_hw_core_register_write(struct mali_hw_core *core, u32 relative_address, u32 new_val)
{
MALI_DEBUG_PRINT(6, ("register_write for core %s, relative addr=0x%04X, val=0x%08X\n",
- core->description, relative_address, new_val));
+ core->description, relative_address, new_val));
_mali_osk_mem_iowrite32(core->mapped_registers, relative_address, new_val);
}
{
u32 i;
MALI_DEBUG_PRINT(6, ("register_write_array: for core %s, relative addr=0x%04X, nr of regs=%u\n",
- core->description,relative_address, nr_of_regs));
+ core->description, relative_address, nr_of_regs));
/* Do not use burst writes against the registers */
- for (i = 0; i< nr_of_regs; i++) {
- mali_hw_core_register_write_relaxed(core, relative_address + i*4, write_array[i]);
+ for (i = 0; i < nr_of_regs; i++) {
+ mali_hw_core_register_write_relaxed(core, relative_address + i * 4, write_array[i]);
}
}
/* Conditionally write a set of registers.
* The register will only be written if the new value is different from the old_value.
* If the new value is different, the old value will also be updated */
-MALI_STATIC_INLINE void mali_hw_core_register_write_array_relaxed_conditional(struct mali_hw_core *core, u32 relative_address, u32 *write_array, u32 nr_of_regs, const u32* old_array)
+MALI_STATIC_INLINE void mali_hw_core_register_write_array_relaxed_conditional(struct mali_hw_core *core, u32 relative_address, u32 *write_array, u32 nr_of_regs, const u32 *old_array)
{
u32 i;
MALI_DEBUG_PRINT(6, ("register_write_array: for core %s, relative addr=0x%04X, nr of regs=%u\n",
- core->description,relative_address, nr_of_regs));
+ core->description, relative_address, nr_of_regs));
/* Do not use burst writes against the registers */
- for (i = 0; i< nr_of_regs; i++) {
- if(old_array[i] != write_array[i]) {
- mali_hw_core_register_write_relaxed(core, relative_address + i*4, write_array[i]);
+ for (i = 0; i < nr_of_regs; i++) {
+ if (old_array[i] != write_array[i]) {
+ mali_hw_core_register_write_relaxed(core, relative_address + i * 4, write_array[i]);
}
}
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_SUCCESS MALI_ERROR(_MALI_OSK_ERR_OK)
/**
- * Basic error macro. This checks whether the given condition is true, and if not returns
- * from this function with the supplied error code. This is a macro so that we can override it
- * for stress testing.
+ * Basic error macro. This checks whether the given condition is true, and if not returns
+ * from this function with the supplied error code. This is a macro so that we can override it
+ * for stress testing.
*
- * Note that this uses the do-while-0 wrapping to ensure that we don't get problems with dangling
- * else clauses. Note also no closing semicolon - this is supplied in typical usage:
+ * Note that this uses the do-while-0 wrapping to ensure that we don't get problems with dangling
+ * else clauses. Note also no closing semicolon - this is supplied in typical usage:
*
- * MALI_CHECK((p!=NULL), ERROR_NO_OBJECT);
+ * MALI_CHECK((p!=NULL), ERROR_NO_OBJECT);
*/
#define MALI_CHECK(condition, error_code) do { if(!(condition)) MALI_ERROR(error_code); } while(0)
/**
- * Error propagation macro. If the expression given is anything other than _MALI_OSK_NO_ERROR,
- * then the value is returned from the enclosing function as an error code. This effectively
- * acts as a guard clause, and propagates error values up the call stack. This uses a
- * temporary value to ensure that the error expression is not evaluated twice.
- * If the counter for forcing a failure has been set using _mali_force_error, this error will be
- * returned without evaluating the expression in MALI_CHECK_NO_ERROR
+ * Error propagation macro. If the expression given is anything other than
+ * _MALI_OSK_NO_ERROR, then the value is returned from the enclosing function
+ * as an error code. This effectively acts as a guard clause, and propagates
+ * error values up the call stack. This uses a temporary value to ensure that
+ * the error expression is not evaluated twice.
+ * If the counter for forcing a failure has been set using _mali_force_error,
+ * this error will be returned without evaluating the expression in
+ * MALI_CHECK_NO_ERROR
*/
#define MALI_CHECK_NO_ERROR(expression) \
- do { _mali_osk_errcode_t _check_no_error_result=(expression); \
- if(_check_no_error_result != _MALI_OSK_ERR_OK) \
- MALI_ERROR(_check_no_error_result); \
- } while(0)
+ do { _mali_osk_errcode_t _check_no_error_result=(expression); \
+ if(_check_no_error_result != _MALI_OSK_ERR_OK) \
+ MALI_ERROR(_check_no_error_result); \
+ } while(0)
/**
* Pointer check macro. Checks non-null pointer.
#define MALI_CHECK_NON_NULL(pointer, error_code) MALI_CHECK( ((pointer)!=NULL), (error_code) )
/**
- * Error macro with goto. This checks whether the given condition is true, and if not jumps
- * to the specified label using a goto. The label must therefore be local to the function in
- * which this macro appears. This is most usually used to execute some clean-up code before
- * exiting with a call to ERROR.
+ * Error macro with goto. This checks whether the given condition is true, and if not jumps
+ * to the specified label using a goto. The label must therefore be local to the function in
+ * which this macro appears. This is most usually used to execute some clean-up code before
+ * exiting with a call to ERROR.
*
- * Like the other macros, this is a macro to allow us to override the condition if we wish,
- * e.g. to force an error during stress testing.
+ * Like the other macros, this is a macro to allow us to override the condition if we wish,
+ * e.g. to force an error during stress testing.
*/
#define MALI_CHECK_GOTO(condition, label) do { if(!(condition)) goto label; } while(0)
*/
#define MALI_IGNORE(x) x=x
+#if defined(CONFIG_MALI_QUIET)
+#define MALI_PRINTF(args)
+#else
#define MALI_PRINTF(args) _mali_osk_dbgmsg args;
+#endif
#define MALI_PRINT_ERROR(args) do{ \
- MALI_PRINTF(("Mali: ERR: %s\n" ,__FILE__)); \
- MALI_PRINTF((" %s()%4d\n ", __FUNCTION__, __LINE__)) ; \
- MALI_PRINTF(args); \
- MALI_PRINTF(("\n")); \
+ MALI_PRINTF(("Mali: ERR: %s\n" ,__FILE__)); \
+ MALI_PRINTF((" %s()%4d\n ", __FUNCTION__, __LINE__)) ; \
+ MALI_PRINTF(args); \
+ MALI_PRINTF(("\n")); \
} while(0)
#define MALI_PRINT(args) do{ \
- MALI_PRINTF(("Mali: ")); \
- MALI_PRINTF(args); \
+ MALI_PRINTF(("Mali: ")); \
+ MALI_PRINTF(args); \
} while (0)
#ifdef DEBUG
#define MALI_DEBUG_CODE(code) code
#define MALI_DEBUG_PRINT(level, args) do { \
- if((level) <= mali_debug_level)\
- {MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); } \
+ if((level) <= mali_debug_level)\
+ {MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); } \
} while (0)
#define MALI_DEBUG_PRINT_ERROR(args) MALI_PRINT_ERROR(args)
#define MALI_DEBUG_PRINT_IF(level,condition,args) \
if((condition)&&((level) <= mali_debug_level))\
- {MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); }
+ {MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); }
#define MALI_DEBUG_PRINT_ELSE(level, args)\
else if((level) <= mali_debug_level)\
- { MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); }
+ { MALI_PRINTF(("Mali<" #level ">: ")); MALI_PRINTF(args); }
/**
* @note these variants of DEBUG ASSERTS will cause a debugger breakpoint
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
}
static struct mali_group *mali_create_group(struct mali_l2_cache_core *cache,
- _mali_osk_resource_t *resource_mmu,
- _mali_osk_resource_t *resource_gp,
- _mali_osk_resource_t *resource_pp)
+ _mali_osk_resource_t *resource_mmu,
+ _mali_osk_resource_t *resource_gp,
+ _mali_osk_resource_t *resource_pp)
{
struct mali_mmu_core *mmu;
struct mali_group *group;
}
static _mali_osk_errcode_t mali_create_virtual_group(_mali_osk_resource_t *resource_mmu_pp_bcast,
- _mali_osk_resource_t *resource_pp_bcast,
- _mali_osk_resource_t *resource_dlbu,
- _mali_osk_resource_t *resource_bcast)
+ _mali_osk_resource_t *resource_pp_bcast,
+ _mali_osk_resource_t *resource_dlbu,
+ _mali_osk_resource_t *resource_bcast)
{
struct mali_mmu_core *mmu_pp_bcast_core;
struct mali_pp_core *pp_bcast_core;
}
/* Create the group object */
+#if defined(DEBUG)
+ /* Get a physical PP group to temporarily add to broadcast unit. IRQ
+ * verification needs a physical group in the broadcast unit to test
+ * the broadcast unit interrupt line. */
+ {
+ struct mali_group *phys_group = NULL;
+ int i;
+ for (i = 0; i < mali_group_get_glob_num_groups(); i++) {
+ phys_group = mali_group_get_glob_group(i);
+ if (NULL != mali_group_get_pp_core(phys_group)) break;
+ }
+ MALI_DEBUG_ASSERT(NULL != mali_group_get_pp_core(phys_group));
+
+ /* Add the group temporarily to the broadcast, and update the
+ * broadcast HW. Since the HW is not updated when removing the
+ * group the IRQ check will work when the virtual PP is created
+ * later.
+ *
+ * When the virtual group gets populated, the actually used
+ * groups will be added to the broadcast unit and the HW will
+ * be updated.
+ */
+ mali_bcast_add_group(bcast_core, phys_group);
+ mali_bcast_reset(bcast_core);
+ mali_bcast_remove_group(bcast_core, phys_group);
+ }
+#endif /* DEBUG */
group = mali_group_create(NULL, dlbu_core, bcast_core);
if (NULL == group) {
MALI_PRINT_ERROR(("Failed to create group object for MMU PP broadcast core %s\n", resource_mmu_pp_bcast->description));
if (MALI_MAX_JOB_RUNTIME_DEFAULT == mali_max_job_runtime) {
/* Group settings are not overridden by module parameters, so use device settings */
- struct _mali_osk_device_data data = { 0, };
+ _mali_osk_device_data data = { 0, };
if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data)) {
/* Use device specific settings (if defined) */
}
}
- if(mali_is_mali450()) {
+ if (mali_is_mali450()) {
_mali_osk_errcode_t err = mali_create_virtual_group(&resource_pp_mmu_bcast, &resource_pp_bcast, &resource_dlbu, &resource_bcast);
if (_MALI_OSK_ERR_OK != err) {
return err;
++pp_count_gr1;
if (mali_is_mali400()) {
- mali_pmu_set_domain_mask(MALI_PP0_DOMAIN_INDEX, 0x01<<2);
+ mali_pmu_set_domain_mask(MALI_PP0_DOMAIN_INDEX, 0x01 << 2);
} else if (mali_is_mali450()) {
- mali_pmu_set_domain_mask(MALI_PP0_DOMAIN_INDEX, 0x01<<1);
+ mali_pmu_set_domain_mask(MALI_PP0_DOMAIN_INDEX, 0x01 << 1);
}
}
++pp_count_gr1;
if (mali_is_mali400()) {
- mali_pmu_set_domain_mask(MALI_PP1_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_PP1_DOMAIN_INDEX, 0x01 << 3);
} else if (mali_is_mali450()) {
- mali_pmu_set_domain_mask(MALI_PP1_DOMAIN_INDEX, 0x01<<2);
+ mali_pmu_set_domain_mask(MALI_PP1_DOMAIN_INDEX, 0x01 << 2);
}
}
++pp_count_gr1;
if (mali_is_mali400()) {
- mali_pmu_set_domain_mask(MALI_PP2_DOMAIN_INDEX, 0x01<<4);
+ mali_pmu_set_domain_mask(MALI_PP2_DOMAIN_INDEX, 0x01 << 4);
} else if (mali_is_mali450()) {
- mali_pmu_set_domain_mask(MALI_PP2_DOMAIN_INDEX, 0x01<<2);
+ mali_pmu_set_domain_mask(MALI_PP2_DOMAIN_INDEX, 0x01 << 2);
}
}
++pp_count_gr1;
if (mali_is_mali400()) {
- mali_pmu_set_domain_mask(MALI_PP3_DOMAIN_INDEX, 0x01<<5);
+ mali_pmu_set_domain_mask(MALI_PP3_DOMAIN_INDEX, 0x01 << 5);
} else if (mali_is_mali450()) {
- mali_pmu_set_domain_mask(MALI_PP3_DOMAIN_INDEX, 0x01<<2);
+ mali_pmu_set_domain_mask(MALI_PP3_DOMAIN_INDEX, 0x01 << 2);
}
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x28000, NULL)) {
++pp_count_gr2;
- mali_pmu_set_domain_mask(MALI_PP4_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_PP4_DOMAIN_INDEX, 0x01 << 3);
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2A000, NULL)) {
++pp_count_gr2;
- mali_pmu_set_domain_mask(MALI_PP5_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_PP5_DOMAIN_INDEX, 0x01 << 3);
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2C000, NULL)) {
++pp_count_gr2;
- mali_pmu_set_domain_mask(MALI_PP6_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_PP6_DOMAIN_INDEX, 0x01 << 3);
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x2E000, NULL)) {
++pp_count_gr2;
- mali_pmu_set_domain_mask(MALI_PP7_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_PP7_DOMAIN_INDEX, 0x01 << 3);
}
/* L2gp/L2PP0/L2PP4 */
++l2_count;
if (mali_is_mali400()) {
- mali_pmu_set_domain_mask(MALI_L20_DOMAIN_INDEX, 0x01<<1);
+ mali_pmu_set_domain_mask(MALI_L20_DOMAIN_INDEX, 0x01 << 1);
} else if (mali_is_mali450()) {
- mali_pmu_set_domain_mask(MALI_L20_DOMAIN_INDEX, 0x01<<0);
+ mali_pmu_set_domain_mask(MALI_L20_DOMAIN_INDEX, 0x01 << 0);
}
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x1000, NULL)) {
++l2_count;
- mali_pmu_set_domain_mask(MALI_L21_DOMAIN_INDEX, 0x01<<1);
+ mali_pmu_set_domain_mask(MALI_L21_DOMAIN_INDEX, 0x01 << 1);
}
if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x11000, NULL)) {
++l2_count;
- mali_pmu_set_domain_mask(MALI_L22_DOMAIN_INDEX, 0x01<<3);
+ mali_pmu_set_domain_mask(MALI_L22_DOMAIN_INDEX, 0x01 << 3);
}
MALI_DEBUG_PRINT(2, ("Using default PMU domain config: (%d) gr1_pp_cores, (%d) gr2_pp_cores, (%d) l2_count. \n", pp_count_gr1, pp_count_gr2, l2_count));
static void mali_set_pmu_global_domain_config(void)
{
- struct _mali_osk_device_data data = { 0, };
+ _mali_osk_device_data data = { 0, };
int i = 0;
if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data)) {
if (0 == mali_dedicated_mem_start && 0 == mali_dedicated_mem_size && 0 == mali_shared_mem_size) {
/* Memory settings are not overridden by module parameters, so use device settings */
- struct _mali_osk_device_data data = { 0, };
+ _mali_osk_device_data data = { 0, };
if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data)) {
/* Use device specific settings (if defined) */
}
MALI_DEBUG_PRINT(2, ("Using device defined memory settings (dedicated: 0x%08X@0x%08X, shared: 0x%08X)\n",
- mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
+ mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
} else {
MALI_DEBUG_PRINT(2, ("Using module defined memory settings (dedicated: 0x%08X@0x%08X, shared: 0x%08X)\n",
- mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
+ mali_dedicated_mem_size, mali_dedicated_mem_start, mali_shared_mem_size));
}
if (0 < mali_dedicated_mem_size && 0 != mali_dedicated_mem_start) {
if (0 == mali_fb_start && 0 == mali_fb_size) {
/* Frame buffer settings are not overridden by module parameters, so use device settings */
- struct _mali_osk_device_data data = { 0, };
+ _mali_osk_device_data data = { 0, };
if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data)) {
/* Use device specific settings (if defined) */
}
MALI_DEBUG_PRINT(2, ("Using device defined frame buffer settings (0x%08X@0x%08X)\n",
- mali_fb_size, mali_fb_start));
+ mali_fb_size, mali_fb_start));
} else {
MALI_DEBUG_PRINT(2, ("Using module defined frame buffer settings (0x%08X@0x%08X)\n",
- mali_fb_size, mali_fb_start));
+ mali_fb_size, mali_fb_start));
}
if (0 != mali_fb_size) {
}
}
+static _mali_osk_errcode_t mali_init_hw_reset(void)
+{
+#if defined(CONFIG_MALI450)
+ _mali_osk_resource_t resource_bcast;
+
+ /* Ensure broadcast unit is in a good state before we start creating
+ * groups and cores.
+ */
+ if (_MALI_OSK_ERR_OK == _mali_osk_resource_find(global_gpu_base_address + 0x13000, &resource_bcast)) {
+ struct mali_bcast_unit *bcast_core;
+
+ bcast_core = mali_bcast_unit_create(&resource_bcast);
+ if (NULL == bcast_core) {
+ MALI_PRINT_ERROR(("Failed to create Broadcast unit object!\n"));
+ return _MALI_OSK_ERR_FAULT;
+ }
+ mali_bcast_unit_delete(bcast_core);
+ }
+#endif /* CONFIG_MALI450 */
+
+ return _MALI_OSK_ERR_OK;
+}
+
_mali_osk_errcode_t mali_initialize_subsystems(void)
{
_mali_osk_errcode_t err;
if (_MALI_OSK_ERR_OK != err) goto pmu_reset_failed;
}
+ /* Ensure HW is in a good state before starting to access cores. */
+ err = mali_init_hw_reset();
+ if (_MALI_OSK_ERR_OK != err) goto init_hw_reset_failed;
+
/* Detect which Mali GPU we are dealing with */
err = mali_parse_product_info();
if (_MALI_OSK_ERR_OK != err) goto product_info_parsing_failed;
/* Nothing to roll back */
product_info_parsing_failed:
/* Nothing to roll back */
+init_hw_reset_failed:
+ /* Nothing to roll back */
pmu_reset_failed:
/* Allowing the system to be turned off */
_mali_osk_pm_dev_ref_dec();
return global_gpu_minor_version;
}
-_mali_osk_errcode_t _mali_ukk_get_api_version( _mali_uk_get_api_version_s *args )
+_mali_osk_errcode_t _mali_ukk_get_api_version(_mali_uk_get_api_version_s *args)
+{
+ MALI_DEBUG_ASSERT_POINTER(args);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
+
+ /* check compatability */
+ if (args->version == _MALI_UK_API_VERSION) {
+ args->compatible = 1;
+ } else {
+ args->compatible = 0;
+ }
+
+ args->version = _MALI_UK_API_VERSION; /* report our version */
+
+ /* success regardless of being compatible or not */
+ MALI_SUCCESS;
+}
+
+_mali_osk_errcode_t _mali_ukk_get_api_version_v2(_mali_uk_get_api_version_v2_s *args)
{
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
/* check compatability */
- if ( args->version == _MALI_UK_API_VERSION ) {
+ if (args->version == _MALI_UK_API_VERSION) {
args->compatible = 1;
} else {
args->compatible = 0;
MALI_SUCCESS;
}
-_mali_osk_errcode_t _mali_ukk_wait_for_notification( _mali_uk_wait_for_notification_s *args )
+_mali_osk_errcode_t _mali_ukk_wait_for_notification(_mali_uk_wait_for_notification_s *args)
{
_mali_osk_errcode_t err;
- _mali_osk_notification_t * notification;
+ _mali_osk_notification_t *notification;
_mali_osk_notification_queue_t *queue;
+ struct mali_session_data *session;
/* check input */
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
- queue = ((struct mali_session_data *)args->ctx)->ioctl_queue;
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
+ queue = session->ioctl_queue;
/* if the queue does not exist we're currently shutting down */
if (NULL == queue) {
_mali_osk_memcpy(&args->data, notification->result_buffer, notification->result_buffer_size);
/* finished with the notification */
- _mali_osk_notification_delete( notification );
+ _mali_osk_notification_delete(notification);
MALI_SUCCESS; /* all ok */
}
-_mali_osk_errcode_t _mali_ukk_post_notification( _mali_uk_post_notification_s *args )
+_mali_osk_errcode_t _mali_ukk_post_notification(_mali_uk_post_notification_s *args)
{
- _mali_osk_notification_t * notification;
+ _mali_osk_notification_t *notification;
_mali_osk_notification_queue_t *queue;
+ struct mali_session_data *session;
/* check input */
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
- queue = ((struct mali_session_data *)args->ctx)->ioctl_queue;
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
+ queue = session->ioctl_queue;
/* if the queue does not exist we're currently shutting down */
if (NULL == queue) {
notification = _mali_osk_notification_create(args->type, 0);
if (NULL == notification) {
- MALI_PRINT_ERROR( ("Failed to create notification object\n"));
+ MALI_PRINT_ERROR(("Failed to create notification object\n"));
return _MALI_OSK_ERR_NOMEM;
}
MALI_SUCCESS; /* all ok */
}
-_mali_osk_errcode_t _mali_ukk_request_high_priority( _mali_uk_request_high_priority_s *args )
+_mali_osk_errcode_t _mali_ukk_request_high_priority(_mali_uk_request_high_priority_s *args)
{
struct mali_session_data *session;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
- session = (struct mali_session_data *) args->ctx;
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
if (!session->use_high_priority_job_queue) {
session->use_high_priority_job_queue = MALI_TRUE;
if (0 != mali_dlbu_phys_addr) {
mali_mmu_pagedir_update(session->page_directory, MALI_DLBU_VIRT_ADDR, mali_dlbu_phys_addr,
- _MALI_OSK_MALI_PAGE_SIZE, MALI_MMU_FLAGS_DEFAULT);
+ _MALI_OSK_MALI_PAGE_SIZE, MALI_MMU_FLAGS_DEFAULT);
}
if (_MALI_OSK_ERR_OK != mali_memory_session_begin(session)) {
}
#if defined(CONFIG_MALI400_POWER_PERFORMANCE_POLICY)
- if ( _MALI_OSK_ERR_OK != _mali_osk_atomic_init(&session->number_of_window_jobs, 0)) {
+ if (_MALI_OSK_ERR_OK != _mali_osk_atomic_init(&session->number_of_window_jobs, 0)) {
MALI_DEBUG_PRINT_ERROR(("Initialization of atomic number_of_window_jobs failed.\n"));
mali_timeline_system_destroy(session->timeline_system);
mali_soft_job_system_destroy(session->soft_job_system);
_MALI_OSK_INIT_LIST_HEAD(&session->pp_job_fb_lookup_list[i]);
}
- *context = (void*)session;
+ *context = (void *)session;
/* Add session to the list of all sessions. */
mali_session_add(session);
mali_soft_job_system_destroy(session->soft_job_system);
session->soft_job_system = NULL;
- MALI_DEBUG_CODE( {
+ MALI_DEBUG_CODE({
/* Check that the pp_job_fb_lookup_list array is empty. */
u32 i;
for (i = 0; i < MALI_PP_JOB_FB_LOOKUP_LIST_SIZE; ++i)
}
#if MALI_STATE_TRACKING
-u32 _mali_kernel_core_dump_state(char* buf, u32 size)
+u32 _mali_kernel_core_dump_state(char *buf, u32 size)
{
int n = 0; /* Number of bytes written to buf */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
u32 mali_kernel_core_get_gpu_minor_version(void);
-u32 _mali_kernel_core_dump_state(char* buf, u32 size);
+u32 _mali_kernel_core_dump_state(char *buf, u32 size);
MALI_STATIC_INLINE mali_bool mali_is_mali450(void)
{
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @param count Number of mappings in the table
* @return Pointer to a new table, NULL on error
*/
-static mali_descriptor_table * descriptor_table_alloc(int count);
+static mali_descriptor_table *descriptor_table_alloc(int count);
/**
* Free a descriptor table
* @param table The table to free
*/
-static void descriptor_table_free(mali_descriptor_table * table);
+static void descriptor_table_free(mali_descriptor_table *table);
-mali_descriptor_mapping * mali_descriptor_mapping_create(int init_entries, int max_entries)
+mali_descriptor_mapping *mali_descriptor_mapping_create(int init_entries, int max_entries)
{
- mali_descriptor_mapping * map = _mali_osk_calloc(1, sizeof(mali_descriptor_mapping));
+ mali_descriptor_mapping *map = _mali_osk_calloc(1, sizeof(mali_descriptor_mapping));
init_entries = MALI_PAD_INT(init_entries);
max_entries = MALI_PAD_INT(max_entries);
return NULL;
}
-void mali_descriptor_mapping_destroy(mali_descriptor_mapping * map)
+void mali_descriptor_mapping_destroy(mali_descriptor_mapping *map)
{
descriptor_table_free(map->table);
_mali_osk_mutex_rw_term(map->lock);
_mali_osk_free(map);
}
-_mali_osk_errcode_t mali_descriptor_mapping_allocate_mapping(mali_descriptor_mapping * map, void * target, int *odescriptor)
+_mali_osk_errcode_t mali_descriptor_mapping_allocate_mapping(mali_descriptor_mapping *map, void *target, int *odescriptor)
{
_mali_osk_errcode_t err = _MALI_OSK_ERR_FAULT;
int new_descriptor;
new_descriptor = _mali_osk_find_first_zero_bit(map->table->usage, map->current_nr_mappings);
if (new_descriptor == map->current_nr_mappings) {
/* no free descriptor, try to expand the table */
- mali_descriptor_table * new_table, * old_table;
+ mali_descriptor_table *new_table, * old_table;
if (map->current_nr_mappings >= map->max_nr_mappings_allowed) goto unlock_and_exit;
map->current_nr_mappings += BITS_PER_LONG;
old_table = map->table;
_mali_osk_memcpy(new_table->usage, old_table->usage, (sizeof(unsigned long)*map->current_nr_mappings) / BITS_PER_LONG);
- _mali_osk_memcpy(new_table->mappings, old_table->mappings, map->current_nr_mappings * sizeof(void*));
+ _mali_osk_memcpy(new_table->mappings, old_table->mappings, map->current_nr_mappings * sizeof(void *));
map->table = new_table;
descriptor_table_free(old_table);
}
MALI_ERROR(err);
}
-void mali_descriptor_mapping_call_for_each(mali_descriptor_mapping * map, void (*callback)(int, void*))
+void mali_descriptor_mapping_call_for_each(mali_descriptor_mapping *map, void (*callback)(int, void *))
{
int i;
_mali_osk_mutex_rw_signal(map->lock, _MALI_OSK_LOCKMODE_RO);
}
-_mali_osk_errcode_t mali_descriptor_mapping_get(mali_descriptor_mapping * map, int descriptor, void** target)
+_mali_osk_errcode_t mali_descriptor_mapping_get(mali_descriptor_mapping *map, int descriptor, void **target)
{
_mali_osk_errcode_t result = _MALI_OSK_ERR_FAULT;
MALI_DEBUG_ASSERT_POINTER(map);
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RO);
- if ( (descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage) ) {
+ if ((descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage)) {
*target = map->table->mappings[descriptor];
result = _MALI_OSK_ERR_OK;
} else *target = NULL;
MALI_ERROR(result);
}
-_mali_osk_errcode_t mali_descriptor_mapping_set(mali_descriptor_mapping * map, int descriptor, void * target)
+_mali_osk_errcode_t mali_descriptor_mapping_set(mali_descriptor_mapping *map, int descriptor, void *target)
{
_mali_osk_errcode_t result = _MALI_OSK_ERR_FAULT;
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RO);
- if ( (descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage) ) {
+ if ((descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage)) {
map->table->mappings[descriptor] = target;
result = _MALI_OSK_ERR_OK;
}
MALI_ERROR(result);
}
-void *mali_descriptor_mapping_free(mali_descriptor_mapping * map, int descriptor)
+void *mali_descriptor_mapping_free(mali_descriptor_mapping *map, int descriptor)
{
void *old_value = NULL;
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RW);
- if ( (descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage) ) {
+ if ((descriptor >= 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage)) {
old_value = map->table->mappings[descriptor];
map->table->mappings[descriptor] = NULL;
_mali_osk_clear_nonatomic_bit(descriptor, map->table->usage);
return old_value;
}
-static mali_descriptor_table * descriptor_table_alloc(int count)
+static mali_descriptor_table *descriptor_table_alloc(int count)
{
- mali_descriptor_table * table;
+ mali_descriptor_table *table;
- table = _mali_osk_calloc(1, sizeof(mali_descriptor_table) + ((sizeof(unsigned long) * count)/BITS_PER_LONG) + (sizeof(void*) * count));
+ table = _mali_osk_calloc(1, sizeof(mali_descriptor_table) + ((sizeof(unsigned long) * count) / BITS_PER_LONG) + (sizeof(void *) * count));
if (NULL != table) {
- table->usage = (u32*)((u8*)table + sizeof(mali_descriptor_table));
- table->mappings = (void**)((u8*)table + sizeof(mali_descriptor_table) + ((sizeof(unsigned long) * count)/BITS_PER_LONG));
+ table->usage = (u32 *)((u8 *)table + sizeof(mali_descriptor_table));
+ table->mappings = (void **)((u8 *)table + sizeof(mali_descriptor_table) + ((sizeof(unsigned long) * count) / BITS_PER_LONG));
}
return table;
}
-static void descriptor_table_free(mali_descriptor_table * table)
+static void descriptor_table_free(mali_descriptor_table *table)
{
_mali_osk_free(table);
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* The actual descriptor mapping table, never directly accessed by clients
*/
typedef struct mali_descriptor_table {
- u32 * usage; /**< Pointer to bitpattern indicating if a descriptor is valid/used or not */
- void** mappings; /**< Array of the pointers the descriptors map to */
+ u32 *usage; /**< Pointer to bitpattern indicating if a descriptor is valid/used or not */
+ void **mappings; /**< Array of the pointers the descriptors map to */
} mali_descriptor_table;
/**
_mali_osk_mutex_rw_t *lock; /**< Lock protecting access to the mapping object */
int max_nr_mappings_allowed; /**< Max number of mappings to support in this namespace */
int current_nr_mappings; /**< Current number of possible mappings */
- mali_descriptor_table * table; /**< Pointer to the current mapping table */
+ mali_descriptor_table *table; /**< Pointer to the current mapping table */
} mali_descriptor_mapping;
/**
* @param max_entries Number of entries to max support
* @return Pointer to a descriptor mapping object, NULL on failure
*/
-mali_descriptor_mapping * mali_descriptor_mapping_create(int init_entries, int max_entries);
+mali_descriptor_mapping *mali_descriptor_mapping_create(int init_entries, int max_entries);
/**
* Destroy a descriptor mapping object
* @param map The map to free
*/
-void mali_descriptor_mapping_destroy(mali_descriptor_mapping * map);
+void mali_descriptor_mapping_destroy(mali_descriptor_mapping *map);
/**
* Allocate a new mapping entry (descriptor ID)
* @param target The value to map to
* @return The descriptor allocated, a negative value on error
*/
-_mali_osk_errcode_t mali_descriptor_mapping_allocate_mapping(mali_descriptor_mapping * map, void * target, int *descriptor);
+_mali_osk_errcode_t mali_descriptor_mapping_allocate_mapping(mali_descriptor_mapping *map, void *target, int *descriptor);
/**
* Get the value mapped to by a descriptor ID
* @param target Pointer to a pointer which will receive the stored value
* @return 0 on successful lookup, negative on error
*/
-_mali_osk_errcode_t mali_descriptor_mapping_get(mali_descriptor_mapping * map, int descriptor, void** target);
+_mali_osk_errcode_t mali_descriptor_mapping_get(mali_descriptor_mapping *map, int descriptor, void **target);
/**
* Set the value mapped to by a descriptor ID
* @param target Pointer to replace the current value with
* @return 0 on successful lookup, negative on error
*/
-_mali_osk_errcode_t mali_descriptor_mapping_set(mali_descriptor_mapping * map, int descriptor, void * target);
+_mali_osk_errcode_t mali_descriptor_mapping_set(mali_descriptor_mapping *map, int descriptor, void *target);
/**
* Call the specified callback function for each descriptor in map.
* @param map The map to do callbacks for
* @param callback A callback function which will be calle for each entry in map
*/
-void mali_descriptor_mapping_call_for_each(mali_descriptor_mapping * map, void (*callback)(int, void*));
+void mali_descriptor_mapping_call_for_each(mali_descriptor_mapping *map, void (*callback)(int, void *));
/**
* Free the descriptor ID
*
* @return old value of descriptor mapping
*/
-void *mali_descriptor_mapping_free(mali_descriptor_mapping * map, int descriptor);
+void *mali_descriptor_mapping_free(mali_descriptor_mapping *map, int descriptor);
#endif /* __MALI_KERNEL_DESCRIPTOR_MAPPING_H__ */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
}
#endif /* defined(CONFIG_MALI400_POWER_PERFORMANCE_POLICY) */
-static void calculate_gpu_utilization(void* arg)
+static void calculate_gpu_utilization(void *arg)
{
u64 time_now;
u64 time_period;
_mali_osk_errcode_t mali_utilization_init(void)
{
#if USING_GPU_UTILIZATION
- struct _mali_osk_device_data data;
+ _mali_osk_device_data data;
+
if (_MALI_OSK_ERR_OK == _mali_osk_device_data_get(&data)) {
/* Use device specific settings (if defined) */
if (0 != data.utilization_interval) {
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* This saves user space from calling kernel space twice in this case.
* We just need to remember to add pid and tid manually.
*/
- if ( event==_MALI_UK_VSYNC_EVENT_BEGIN_WAIT) {
+ if (event == _MALI_UK_VSYNC_EVENT_BEGIN_WAIT) {
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_SUSPEND |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_SUSPEND_RESUME_SW_VSYNC,
- _mali_osk_get_pid(), _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_SUSPEND_RESUME_SW_VSYNC,
+ _mali_osk_get_pid(), _mali_osk_get_tid(), 0, 0, 0);
}
- if (event==_MALI_UK_VSYNC_EVENT_END_WAIT) {
+ if (event == _MALI_UK_VSYNC_EVENT_END_WAIT) {
_mali_osk_profiling_add_event(MALI_PROFILING_EVENT_TYPE_RESUME |
- MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
- MALI_PROFILING_EVENT_REASON_SUSPEND_RESUME_SW_VSYNC,
- _mali_osk_get_pid(), _mali_osk_get_tid(), 0, 0, 0);
+ MALI_PROFILING_EVENT_CHANNEL_SOFTWARE |
+ MALI_PROFILING_EVENT_REASON_SUSPEND_RESUME_SW_VSYNC,
+ _mali_osk_get_pid(), _mali_osk_get_tid(), 0, 0, 0);
}
#endif
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
if (_MALI_OSK_ERR_OK == mali_hw_core_create(&cache->hw_core, resource, MALI400_L2_CACHE_REGISTERS_SIZE)) {
MALI_DEBUG_CODE(u32 cache_size = mali_hw_core_register_read(&cache->hw_core, MALI400_L2_CACHE_REGISTER_SIZE));
MALI_DEBUG_PRINT(2, ("Mali L2 cache: Created %s: % 3uK, %u-way, % 2ubyte cache line, % 3ubit external bus\n",
- resource->description,
- 1 << (((cache_size >> 16) & 0xff) - 10),
- 1 << ((cache_size >> 8) & 0xff),
- 1 << (cache_size & 0xff),
- 1 << ((cache_size >> 24) & 0xff)));
+ resource->description,
+ 1 << (((cache_size >> 16) & 0xff) - 10),
+ 1 << ((cache_size >> 8) & 0xff),
+ 1 << (cache_size & 0xff),
+ 1 << ((cache_size >> 24) & 0xff)));
#ifdef MALI_UPPER_HALF_SCHEDULING
cache->command_lock = _mali_osk_spinlock_irq_init(_MALI_OSK_LOCKFLAG_ORDERED, _MALI_OSK_LOCK_ORDER_L2_COMMAND);
for (i = 0; i < num_cores; i++) {
cache = mali_l2_cache_core_get_glob_l2_core(i);
- if (MALI_TRUE == mali_l2_cache_lock_power_state(cache)) {
+ if (!cache)
+ continue;
+
+ if (mali_l2_cache_lock_power_state(cache)) {
mali_l2_cache_counter_lock(cache);
if (MALI_L2_PAUSE == cache->mali_l2_status) {
value = cache->counter_src0;
}
mali_hw_core_register_write(&cache->hw_core,
- MALI400_L2_CACHE_REGISTER_PERFCNT_SRC0, value);
+ MALI400_L2_CACHE_REGISTER_PERFCNT_SRC0, value);
if (MALI_HW_CORE_NO_COUNTER == cache->counter_src1) {
value = 0;
value = cache->counter_src1;
}
mali_hw_core_register_write(&cache->hw_core,
- MALI400_L2_CACHE_REGISTER_PERFCNT_SRC1, value);
+ MALI400_L2_CACHE_REGISTER_PERFCNT_SRC1, value);
mali_l2_cache_counter_unlock(cache);
}
void mali_l2_cache_reset(struct mali_l2_cache_core *cache)
{
+ /* Kasin Added, skip off power domain. */
if (cache && cache->pm_domain && cache->pm_domain->state == MALI_PM_DOMAIN_OFF) {
return;
}
if (MALI_L2_PAUSE == cache->mali_l2_status) {
mali_l2_cache_command_unlock(cache);
- MALI_DEBUG_PRINT(1, ( "Mali L2 cache: aborting wait for L2 come back\n"));
+ MALI_DEBUG_PRINT(1, ("Mali L2 cache: aborting wait for L2 come back\n"));
- MALI_ERROR( _MALI_OSK_ERR_BUSY );
+ MALI_ERROR(_MALI_OSK_ERR_BUSY);
}
/* First, wait for L2 cache command handler to go idle */
if (i == loop_count) {
mali_l2_cache_command_unlock(cache);
- MALI_DEBUG_PRINT(1, ( "Mali L2 cache: aborting wait for command interface to go idle\n"));
- MALI_ERROR( _MALI_OSK_ERR_FAULT );
+ MALI_DEBUG_PRINT(1, ("Mali L2 cache: aborting wait for command interface to go idle\n"));
+ MALI_ERROR(_MALI_OSK_ERR_FAULT);
}
/* then issue the command */
void mali_l2_cache_pause_all(mali_bool pause)
{
int i;
- struct mali_l2_cache_core * cache;
+ struct mali_l2_cache_core *cache;
u32 num_cores = mali_l2_cache_core_get_glob_num_l2_cores();
mali_l2_power_status status = MALI_L2_NORMAL;
* loss of cache operation during the pause period to make sure the SW
* status is consistent with L2 cache status.
*/
- if(!pause) {
+ if (!pause) {
mali_l2_cache_invalidate_all();
mali_l2_cache_reset_counters_all();
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* L2 pause is just a status that the L2 can't be accessed temporarily.
*/
void mali_l2_cache_pause_all(mali_bool pause);
-struct mali_l2_cache_core *mali_l2_cache_create(_mali_osk_resource_t * resource);
+struct mali_l2_cache_core *mali_l2_cache_create(_mali_osk_resource_t *resource);
void mali_l2_cache_delete(struct mali_l2_cache_core *cache);
MALI_STATIC_INLINE void mali_l2_cache_set_pm_domain(struct mali_l2_cache_core *cache, struct mali_pm_domain *domain)
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
mali_mem_validator.phys_base = start;
mali_mem_validator.size = size;
MALI_DEBUG_PRINT(2, ("Memory Validator installed for Mali physical address base=0x%08X, size=0x%08X\n",
- mali_mem_validator.phys_base, mali_mem_validator.size));
+ mali_mem_validator.phys_base, mali_mem_validator.size));
return _MALI_OSK_ERR_OK;
}
{
#if 0
if (phys_addr < (phys_addr + size)) { /* Don't allow overflow (or zero size) */
- if ((0 == ( phys_addr & (~_MALI_OSK_CPU_PAGE_MASK))) &&
- (0 == ( size & (~_MALI_OSK_CPU_PAGE_MASK)))) {
+ if ((0 == (phys_addr & (~_MALI_OSK_CPU_PAGE_MASK))) &&
+ (0 == (size & (~_MALI_OSK_CPU_PAGE_MASK)))) {
if ((phys_addr >= mali_mem_validator.phys_base) &&
((phys_addr + (size - 1)) >= mali_mem_validator.phys_base) &&
(phys_addr <= (mali_mem_validator.phys_base + (mali_mem_validator.size - 1))) &&
- ((phys_addr + (size - 1)) <= (mali_mem_validator.phys_base + (mali_mem_validator.size - 1))) ) {
+ ((phys_addr + (size - 1)) <= (mali_mem_validator.phys_base + (mali_mem_validator.size - 1)))) {
MALI_DEBUG_PRINT(3, ("Accepted range 0x%08X + size 0x%08X (= 0x%08X)\n", phys_addr, size, (phys_addr + size - 1)));
return _MALI_OSK_ERR_OK;
}
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/* page fault queue flush helper pages
* note that the mapping pointers are currently unused outside of the initialization functions */
-static u32 mali_page_fault_flush_page_directory = MALI_INVALID_PAGE;
+static mali_dma_addr mali_page_fault_flush_page_directory = MALI_INVALID_PAGE;
static mali_io_address mali_page_fault_flush_page_directory_mapping = NULL;
-static u32 mali_page_fault_flush_page_table = MALI_INVALID_PAGE;
+static mali_dma_addr mali_page_fault_flush_page_table = MALI_INVALID_PAGE;
static mali_io_address mali_page_fault_flush_page_table_mapping = NULL;
-static u32 mali_page_fault_flush_data_page = MALI_INVALID_PAGE;
+static mali_dma_addr mali_page_fault_flush_data_page = MALI_INVALID_PAGE;
static mali_io_address mali_page_fault_flush_data_page_mapping = NULL;
/* an empty page directory (no address valid) which is active on any MMU not currently marked as in use */
-static u32 mali_empty_page_directory_phys = MALI_INVALID_PAGE;
+static mali_dma_addr mali_empty_page_directory_phys = MALI_INVALID_PAGE;
static mali_io_address mali_empty_page_directory_virt = NULL;
{
/* allocate the helper pages */
mali_empty_page_directory_phys = mali_allocate_empty_page(&mali_empty_page_directory_virt);
- if(0 == mali_empty_page_directory_phys) {
+ if (0 == mali_empty_page_directory_phys) {
MALI_DEBUG_PRINT_ERROR(("Mali MMU: Could not allocate empty page directory.\n"));
mali_empty_page_directory_phys = MALI_INVALID_PAGE;
return _MALI_OSK_ERR_NOMEM;
}
if (_MALI_OSK_ERR_OK != mali_create_fault_flush_pages(&mali_page_fault_flush_page_directory,
- &mali_page_fault_flush_page_directory_mapping,
- &mali_page_fault_flush_page_table,
- &mali_page_fault_flush_page_table_mapping,
- &mali_page_fault_flush_data_page,
- &mali_page_fault_flush_data_page_mapping)) {
+ &mali_page_fault_flush_page_directory_mapping,
+ &mali_page_fault_flush_page_table,
+ &mali_page_fault_flush_page_table_mapping,
+ &mali_page_fault_flush_data_page,
+ &mali_page_fault_flush_data_page_mapping)) {
MALI_DEBUG_PRINT_ERROR(("Mali MMU: Could not allocate fault flush pages\n"));
mali_free_empty_page(mali_empty_page_directory_phys, mali_empty_page_directory_virt);
mali_empty_page_directory_phys = MALI_INVALID_PAGE;
mali_empty_page_directory_virt = NULL;
/* Free the page fault flush pages */
- mali_destroy_fault_flush_pages(&mali_page_fault_flush_page_directory, &mali_page_fault_flush_page_directory_mapping,
- &mali_page_fault_flush_page_table, &mali_page_fault_flush_page_table_mapping,
- &mali_page_fault_flush_data_page, &mali_page_fault_flush_data_page_mapping);
+ mali_destroy_fault_flush_pages(&mali_page_fault_flush_page_directory,
+ &mali_page_fault_flush_page_directory_mapping,
+ &mali_page_fault_flush_page_table,
+ &mali_page_fault_flush_page_table_mapping,
+ &mali_page_fault_flush_data_page,
+ &mali_page_fault_flush_data_page_mapping);
}
struct mali_mmu_core *mali_mmu_create(_mali_osk_resource_t *resource, struct mali_group *group, mali_bool is_virtual)
{
- struct mali_mmu_core* mmu = NULL;
+ struct mali_mmu_core *mmu = NULL;
MALI_DEBUG_ASSERT_POINTER(resource);
MALI_DEBUG_PRINT(2, ("Mali MMU: Creating Mali MMU: %s\n", resource->description));
- mmu = _mali_osk_calloc(1,sizeof(struct mali_mmu_core));
- if (NULL != mmu)
- {
+ mmu = _mali_osk_calloc(1, sizeof(struct mali_mmu_core));
+ if (NULL != mmu) {
if (_MALI_OSK_ERR_OK == mali_hw_core_create(&mmu->hw_core, resource, MALI_MMU_REGISTERS_SIZE)) {
if (_MALI_OSK_ERR_OK == mali_group_add_mmu_core(group, mmu)) {
if (is_virtual) {
if (_MALI_OSK_ERR_OK == mali_mmu_reset(mmu)) {
/* Setup IRQ handlers (which will do IRQ probing if needed) */
mmu->irq = _mali_osk_irq_init(resource->irq,
- mali_group_upper_half_mmu,
- group,
- mali_mmu_probe_trigger,
- mali_mmu_probe_ack,
- mmu,
- resource->description);
+ mali_group_upper_half_mmu,
+ group,
+ mali_mmu_probe_trigger,
+ mali_mmu_probe_ack,
+ mmu,
+ resource->description);
if (NULL != mmu->irq) {
return mmu;
} else {
int i;
u32 mmu_status = mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS);
- if ( 0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED) ) {
+ if (0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED)) {
MALI_DEBUG_PRINT(4, ("MMU stall is implicit when Paging is not enabled.\n"));
return MALI_TRUE;
}
- if ( mmu_status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE ) {
+ if (mmu_status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE) {
MALI_DEBUG_PRINT(3, ("Aborting MMU stall request since it is in pagefault state.\n"));
return MALI_FALSE;
}
if ((mmu_status & MALI_MMU_STATUS_BIT_STALL_ACTIVE) && (0 == (mmu_status & MALI_MMU_STATUS_BIT_STALL_NOT_ACTIVE))) {
break;
}
- if (0 == (mmu_status & ( MALI_MMU_STATUS_BIT_PAGING_ENABLED ))) {
+ if (0 == (mmu_status & (MALI_MMU_STATUS_BIT_PAGING_ENABLED))) {
break;
}
}
return MALI_FALSE;
}
- if ( mmu_status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE ) {
+ if (mmu_status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE) {
MALI_DEBUG_PRINT(2, ("Aborting MMU stall request since it has a pagefault.\n"));
return MALI_FALSE;
}
int i;
u32 mmu_status = mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS);
- if ( 0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED )) {
+ if (0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED)) {
MALI_DEBUG_PRINT(3, ("MMU disable skipped since it was not enabled.\n"));
return;
}
for (i = 0; i < MALI_REG_POLL_COUNT_FAST; ++i) {
u32 status = mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS);
- if ( 0 == (status & MALI_MMU_STATUS_BIT_STALL_ACTIVE) ) {
+ if (0 == (status & MALI_MMU_STATUS_BIT_STALL_ACTIVE)) {
break;
}
- if ( status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE ) {
+ if (status & MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE) {
break;
}
- if ( 0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED )) {
+ if (0 == (mmu_status & MALI_MMU_STATUS_BIT_PAGING_ENABLED)) {
break;
}
}
- if (MALI_REG_POLL_COUNT_FAST == i) MALI_DEBUG_PRINT(1,("Disable stall request failed, MMU status is 0x%08X\n", mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS)));
+ if (MALI_REG_POLL_COUNT_FAST == i) MALI_DEBUG_PRINT(1, ("Disable stall request failed, MMU status is 0x%08X\n", mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS)));
}
void mali_mmu_page_fault_done(struct mali_mmu_core *mmu)
static void mali_mmu_activate_address_space(struct mali_mmu_core *mmu, u32 page_directory)
{
/* The MMU must be in stalled or page fault mode, for this writing to work */
- MALI_DEBUG_ASSERT( 0 != ( mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS)
- & (MALI_MMU_STATUS_BIT_STALL_ACTIVE|MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE) ) );
+ MALI_DEBUG_ASSERT(0 != (mali_hw_core_register_read(&mmu->hw_core, MALI_MMU_REGISTER_STATUS)
+ & (MALI_MMU_STATUS_BIT_STALL_ACTIVE | MALI_MMU_STATUS_BIT_PAGE_FAULT_ACTIVE)));
mali_hw_core_register_write(&mmu->hw_core, MALI_MMU_REGISTER_DTE_ADDR, page_directory);
mali_hw_core_register_write(&mmu->hw_core, MALI_MMU_REGISTER_COMMAND, MALI_MMU_COMMAND_ZAP_CACHE);
mali_mmu_disable_stall(mmu);
}
-void mali_mmu_activate_empty_page_directory(struct mali_mmu_core* mmu)
+void mali_mmu_activate_empty_page_directory(struct mali_mmu_core *mmu)
{
mali_bool stall_success;
mali_mmu_disable_stall(mmu);
}
-void mali_mmu_activate_fault_flush_page_directory(struct mali_mmu_core* mmu)
+void mali_mmu_activate_fault_flush_page_directory(struct mali_mmu_core *mmu)
{
mali_bool stall_success;
MALI_DEBUG_ASSERT_POINTER(mmu);
stall_success = mali_mmu_enable_stall(mmu);
/* This function is expect to fail the stalling, since it might be in PageFault mode when it is called */
mali_mmu_activate_address_space(mmu, mali_page_fault_flush_page_directory);
- if ( MALI_TRUE==stall_success ) mali_mmu_disable_stall(mmu);
+ if (MALI_TRUE == stall_success) mali_mmu_disable_stall(mmu);
}
/* Is called when we want the mmu to give an interrupt */
static void mali_mmu_probe_trigger(void *data)
{
struct mali_mmu_core *mmu = (struct mali_mmu_core *)data;
- mali_hw_core_register_write(&mmu->hw_core, MALI_MMU_REGISTER_INT_RAWSTAT, MALI_MMU_INTERRUPT_PAGE_FAULT|MALI_MMU_INTERRUPT_READ_BUS_ERROR);
+ mali_hw_core_register_write(&mmu->hw_core, MALI_MMU_REGISTER_INT_RAWSTAT, MALI_MMU_INTERRUPT_PAGE_FAULT | MALI_MMU_INTERRUPT_READ_BUS_ERROR);
}
/* Is called when the irq probe wants the mmu to acknowledge an interrupt from the hw */
MALI_DEBUG_PRINT(1, ("Probe: Bus read error detect: FAILED\n"));
}
- if ( (int_stat & (MALI_MMU_INTERRUPT_PAGE_FAULT|MALI_MMU_INTERRUPT_READ_BUS_ERROR)) ==
- (MALI_MMU_INTERRUPT_PAGE_FAULT|MALI_MMU_INTERRUPT_READ_BUS_ERROR)) {
+ if ((int_stat & (MALI_MMU_INTERRUPT_PAGE_FAULT | MALI_MMU_INTERRUPT_READ_BUS_ERROR)) ==
+ (MALI_MMU_INTERRUPT_PAGE_FAULT | MALI_MMU_INTERRUPT_READ_BUS_ERROR)) {
return _MALI_OSK_ERR_OK;
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_mmu_page_directory.h"
#include "mali_hw_core.h"
-#include <linux/kernel.h>
-#include <asm/io.h>
-#include <mach/am_regs.h>
-#include <linux/module.h>
-#if MESON_CPU_TYPE == MESON_CPU_TYPE_MESON6
-#include "meson_m400/mali_fix.h"
-#endif
-
-
/* Forward declaration from mali_group.h */
struct mali_group;
void mali_mmu_zap_tlb_without_stall(struct mali_mmu_core *mmu);
void mali_mmu_invalidate_page(struct mali_mmu_core *mmu, u32 mali_address);
-void mali_mmu_activate_page_directory(struct mali_mmu_core* mmu, struct mali_page_directory *pagedir);
-void mali_mmu_activate_empty_page_directory(struct mali_mmu_core* mmu);
-void mali_mmu_activate_fault_flush_page_directory(struct mali_mmu_core* mmu);
+void mali_mmu_activate_page_directory(struct mali_mmu_core *mmu, struct mali_page_directory *pagedir);
+void mali_mmu_activate_empty_page_directory(struct mali_mmu_core *mmu);
+void mali_mmu_activate_fault_flush_page_directory(struct mali_mmu_core *mmu);
void mali_mmu_page_fault_done(struct mali_mmu_core *mmu);
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_kernel_common.h"
#include "mali_osk.h"
+#include "mali_ukk.h"
#include "mali_uk_types.h"
#include "mali_mmu_page_directory.h"
#include "mali_memory.h"
{
_mali_osk_errcode_t err;
mali_io_address mapping;
- u32 address;
+ mali_dma_addr address;
- if(_MALI_OSK_ERR_OK != mali_mmu_get_table_page(&address, &mapping)) {
+ if (_MALI_OSK_ERR_OK != mali_mmu_get_table_page(&address, &mapping)) {
/* Allocation failed */
MALI_DEBUG_PRINT(2, ("Mali MMU: Failed to get table page for empty pgdir\n"));
return 0;
}
- MALI_DEBUG_ASSERT_POINTER( mapping );
+ MALI_DEBUG_ASSERT_POINTER(mapping);
err = fill_page(mapping, 0);
if (_MALI_OSK_ERR_OK != err) {
return address;
}
-void mali_free_empty_page(u32 address, mali_io_address virt_addr)
+void mali_free_empty_page(mali_dma_addr address, mali_io_address virt_addr)
{
if (MALI_INVALID_PAGE != address) {
mali_mmu_release_table_page(address, virt_addr);
}
}
-_mali_osk_errcode_t mali_create_fault_flush_pages(u32 *page_directory, mali_io_address *page_directory_mapping,
- u32 *page_table, mali_io_address *page_table_mapping,
- u32 *data_page, mali_io_address *data_page_mapping)
+_mali_osk_errcode_t mali_create_fault_flush_pages(mali_dma_addr *page_directory,
+ mali_io_address *page_directory_mapping,
+ mali_dma_addr *page_table, mali_io_address *page_table_mapping,
+ mali_dma_addr *data_page, mali_io_address *data_page_mapping)
{
_mali_osk_errcode_t err;
return err;
}
-void mali_destroy_fault_flush_pages(u32 *page_directory, mali_io_address *page_directory_mapping,
- u32 *page_table, mali_io_address *page_table_mapping,
- u32 *data_page, mali_io_address *data_page_mapping)
+void mali_destroy_fault_flush_pages(
+ mali_dma_addr *page_directory, mali_io_address *page_directory_mapping,
+ mali_dma_addr *page_table, mali_io_address *page_table_mapping,
+ mali_dma_addr *data_page, mali_io_address *data_page_mapping)
{
if (MALI_INVALID_PAGE != *page_directory) {
mali_mmu_release_table_page(*page_directory, *page_directory_mapping);
static _mali_osk_errcode_t fill_page(mali_io_address mapping, u32 data)
{
int i;
- MALI_DEBUG_ASSERT_POINTER( mapping );
+ MALI_DEBUG_ASSERT_POINTER(mapping);
- for(i = 0; i < MALI_MMU_PAGE_SIZE/4; i++) {
- _mali_osk_mem_iowrite32_relaxed( mapping, i * sizeof(u32), data);
+ for (i = 0; i < MALI_MMU_PAGE_SIZE / 4; i++) {
+ _mali_osk_mem_iowrite32_relaxed(mapping, i * sizeof(u32), data);
}
_mali_osk_mem_barrier();
MALI_SUCCESS;
const int last_pde = MALI_MMU_PDE_ENTRY(mali_address + size - 1);
_mali_osk_errcode_t err;
mali_io_address pde_mapping;
- u32 pde_phys;
+ mali_dma_addr pde_phys;
int i;
- if (last_pde < first_pde) {
- MALI_ERROR(_MALI_OSK_ERR_INVALID_ARGS);
- }
+ if (last_pde < first_pde)
+ return _MALI_OSK_ERR_INVALID_ARGS;
- for(i = first_pde; i <= last_pde; i++) {
- if(0 == (_mali_osk_mem_ioread32(pagedir->page_directory_mapped, i*sizeof(u32)) & MALI_MMU_FLAGS_PRESENT)) {
+ for (i = first_pde; i <= last_pde; i++) {
+ if (0 == (_mali_osk_mem_ioread32(pagedir->page_directory_mapped,
+ i * sizeof(u32)) & MALI_MMU_FLAGS_PRESENT)) {
/* Page table not present */
MALI_DEBUG_ASSERT(0 == pagedir->page_entries_usage_count[i]);
MALI_DEBUG_ASSERT(NULL == pagedir->page_entries_mapped[i]);
err = mali_mmu_get_table_page(&pde_phys, &pde_mapping);
- if(_MALI_OSK_ERR_OK != err) {
+ if (_MALI_OSK_ERR_OK != err) {
MALI_PRINT_ERROR(("Failed to allocate page table page.\n"));
return err;
}
pagedir->page_entries_mapped[i] = pde_mapping;
/* Update PDE, mark as present */
- _mali_osk_mem_iowrite32_relaxed(pagedir->page_directory_mapped, i*sizeof(u32),
- pde_phys | MALI_MMU_FLAGS_PRESENT);
+ _mali_osk_mem_iowrite32_relaxed(pagedir->page_directory_mapped, i * sizeof(u32),
+ pde_phys | MALI_MMU_FLAGS_PRESENT);
MALI_DEBUG_ASSERT(0 == pagedir->page_entries_usage_count[i]);
pagedir->page_entries_usage_count[i] = 1;
}
_mali_osk_write_mem_barrier();
- MALI_SUCCESS;
+ return _MALI_OSK_ERR_OK;
}
MALI_STATIC_INLINE void mali_mmu_zero_pte(mali_io_address page_table, u32 mali_address, u32 size)
}
}
+static u32 mali_page_directory_get_phys_address(struct mali_page_directory *pagedir, u32 index)
+{
+ return (_mali_osk_mem_ioread32(pagedir->page_directory_mapped,
+ index * sizeof(u32)) & ~MALI_MMU_FLAGS_MASK);
+}
+
+
_mali_osk_errcode_t mali_mmu_pagedir_unmap(struct mali_page_directory *pagedir, u32 mali_address, u32 size)
{
const int first_pde = MALI_MMU_PDE_ENTRY(mali_address);
MALI_DEBUG_PRINT(4, ("Releasing page table as this is the last reference\n"));
/* last reference removed, no need to zero out each PTE */
- page_phys = MALI_MMU_ENTRY_ADDRESS(_mali_osk_mem_ioread32(pagedir->page_directory_mapped, i*sizeof(u32)));
+ page_phys = MALI_MMU_ENTRY_ADDRESS(_mali_osk_mem_ioread32(pagedir->page_directory_mapped, i * sizeof(u32)));
page_virt = pagedir->page_entries_mapped[i];
pagedir->page_entries_mapped[i] = NULL;
- _mali_osk_mem_iowrite32_relaxed(pagedir->page_directory_mapped, i*sizeof(u32), 0);
+ _mali_osk_mem_iowrite32_relaxed(pagedir->page_directory_mapped, i * sizeof(u32), 0);
mali_mmu_release_table_page(page_phys, page_virt);
pd_changed = MALI_TRUE;
struct mali_page_directory *mali_mmu_pagedir_alloc(void)
{
struct mali_page_directory *pagedir;
+ _mali_osk_errcode_t err;
+ mali_dma_addr phys;
pagedir = _mali_osk_calloc(1, sizeof(struct mali_page_directory));
- if(NULL == pagedir) {
+ if (NULL == pagedir) {
return NULL;
}
- if(_MALI_OSK_ERR_OK != mali_mmu_get_table_page(&pagedir->page_directory, &pagedir->page_directory_mapped)) {
+ err = mali_mmu_get_table_page(&phys, &pagedir->page_directory_mapped);
+ if (_MALI_OSK_ERR_OK != err) {
_mali_osk_free(pagedir);
return NULL;
}
+ pagedir->page_directory = (u32)phys;
+
/* Zero page directory */
fill_page(pagedir->page_directory_mapped, 0);
/* Free referenced page tables and zero PDEs. */
for (i = 0; i < num_page_table_entries; i++) {
- if (pagedir->page_directory_mapped && (_mali_osk_mem_ioread32(pagedir->page_directory_mapped, sizeof(u32)*i) & MALI_MMU_FLAGS_PRESENT)) {
- u32 phys = _mali_osk_mem_ioread32(pagedir->page_directory_mapped, i*sizeof(u32)) & ~MALI_MMU_FLAGS_MASK;
+ if (pagedir->page_directory_mapped && (_mali_osk_mem_ioread32(
+ pagedir->page_directory_mapped,
+ sizeof(u32)*i) & MALI_MMU_FLAGS_PRESENT)) {
+ mali_dma_addr phys = _mali_osk_mem_ioread32(pagedir->page_directory_mapped,
+ i * sizeof(u32)) & ~MALI_MMU_FLAGS_MASK;
_mali_osk_mem_iowrite32_relaxed(pagedir->page_directory_mapped, i * sizeof(u32), 0);
mali_mmu_release_table_page(phys, pagedir->page_entries_mapped[i]);
}
}
-void mali_mmu_pagedir_update(struct mali_page_directory *pagedir, u32 mali_address, u32 phys_address, u32 size, u32 permission_bits)
+void mali_mmu_pagedir_update(struct mali_page_directory *pagedir, u32 mali_address,
+ mali_dma_addr phys_address, u32 size, u32 permission_bits)
{
u32 end_address = mali_address + size;
+ u32 mali_phys = (u32)phys_address;
/* Map physical pages into MMU page tables */
- for ( ; mali_address < end_address; mali_address += MALI_MMU_PAGE_SIZE, phys_address += MALI_MMU_PAGE_SIZE) {
+ for (; mali_address < end_address; mali_address += MALI_MMU_PAGE_SIZE, mali_phys += MALI_MMU_PAGE_SIZE) {
MALI_DEBUG_ASSERT_POINTER(pagedir->page_entries_mapped[MALI_MMU_PDE_ENTRY(mali_address)]);
_mali_osk_mem_iowrite32_relaxed(pagedir->page_entries_mapped[MALI_MMU_PDE_ENTRY(mali_address)],
- MALI_MMU_PTE_ENTRY(mali_address) * sizeof(u32),
- phys_address | permission_bits);
+ MALI_MMU_PTE_ENTRY(mali_address) * sizeof(u32),
+ mali_phys | permission_bits);
}
}
-u32 mali_page_directory_get_phys_address(struct mali_page_directory *pagedir, u32 index)
+void mali_mmu_pagedir_diag(struct mali_page_directory *pagedir, u32 fault_addr)
{
- return (_mali_osk_mem_ioread32(pagedir->page_directory_mapped, index*sizeof(u32)) & ~MALI_MMU_FLAGS_MASK);
+#if defined(DEBUG)
+ u32 pde_index, pte_index;
+ u32 pde, pte;
+
+ pde_index = MALI_MMU_PDE_ENTRY(fault_addr);
+ pte_index = MALI_MMU_PTE_ENTRY(fault_addr);
+
+
+ pde = _mali_osk_mem_ioread32(pagedir->page_directory_mapped,
+ pde_index * sizeof(u32));
+
+
+ if (pde & MALI_MMU_FLAGS_PRESENT) {
+ u32 pte_addr = MALI_MMU_ENTRY_ADDRESS(pde);
+
+ pte = _mali_osk_mem_ioread32(pagedir->page_entries_mapped[pde_index],
+ pte_index * sizeof(u32));
+
+ MALI_DEBUG_PRINT(2, ("\tMMU: %08x: Page table present: %08x\n"
+ "\t\tPTE: %08x, page %08x is %s\n",
+ fault_addr, pte_addr, pte,
+ MALI_MMU_ENTRY_ADDRESS(pte),
+ pte & MALI_MMU_FLAGS_DEFAULT ? "rw" : "not present"));
+ } else {
+ MALI_DEBUG_PRINT(2, ("\tMMU: %08x: Page table not present: %08x\n",
+ fault_addr, pde));
+ }
+#else
+ MALI_IGNORE(pagedir);
+ MALI_IGNORE(fault_addr);
+#endif
}
/* For instrumented */
static _mali_osk_errcode_t writereg(u32 where, u32 what, const char *comment, struct dump_info *info)
{
if (NULL != info) {
- info->register_writes_size += sizeof(u32)*2; /* two 32-bit words */
+ info->register_writes_size += sizeof(u32) * 2; /* two 32-bit words */
if (NULL != info->buffer) {
/* check that we have enough space */
- if (info->buffer_left < sizeof(u32)*2) MALI_ERROR(_MALI_OSK_ERR_NOMEM);
+ if (info->buffer_left < sizeof(u32) * 2) MALI_ERROR(_MALI_OSK_ERR_NOMEM);
*info->buffer = where;
info->buffer++;
*info->buffer = what;
info->buffer++;
- info->buffer_left -= sizeof(u32)*2;
+ info->buffer_left -= sizeof(u32) * 2;
}
}
MALI_SUCCESS;
}
-static _mali_osk_errcode_t mali_mmu_dump_page(mali_io_address page, u32 phys_addr, struct dump_info * info)
+static _mali_osk_errcode_t mali_mmu_dump_page(mali_io_address page, u32 phys_addr, struct dump_info *info)
{
if (NULL != info) {
/* 4096 for the page and 4 bytes for the address */
MALI_SUCCESS;
}
-static _mali_osk_errcode_t dump_mmu_page_table(struct mali_page_directory *pagedir, struct dump_info * info)
+static _mali_osk_errcode_t dump_mmu_page_table(struct mali_page_directory *pagedir, struct dump_info *info)
{
MALI_DEBUG_ASSERT_POINTER(pagedir);
MALI_DEBUG_ASSERT_POINTER(info);
int i;
MALI_CHECK_NO_ERROR(
- mali_mmu_dump_page(pagedir->page_directory_mapped, pagedir->page_directory, info)
+ mali_mmu_dump_page(pagedir->page_directory_mapped, pagedir->page_directory, info)
);
for (i = 0; i < 1024; i++) {
if (NULL != pagedir->page_entries_mapped[i]) {
MALI_CHECK_NO_ERROR(
- mali_mmu_dump_page(pagedir->page_entries_mapped[i],
- _mali_osk_mem_ioread32(pagedir->page_directory_mapped,
- i * sizeof(u32)) & ~MALI_MMU_FLAGS_MASK, info)
+ mali_mmu_dump_page(pagedir->page_entries_mapped[i],
+ _mali_osk_mem_ioread32(pagedir->page_directory_mapped,
+ i * sizeof(u32)) & ~MALI_MMU_FLAGS_MASK, info)
);
}
}
MALI_SUCCESS;
}
-static _mali_osk_errcode_t dump_mmu_registers(struct mali_page_directory *pagedir, struct dump_info * info)
+static _mali_osk_errcode_t dump_mmu_registers(struct mali_page_directory *pagedir, struct dump_info *info)
{
MALI_CHECK_NO_ERROR(writereg(0x00000000, pagedir->page_directory,
- "set the page directory address", info));
+ "set the page directory address", info));
MALI_CHECK_NO_ERROR(writereg(0x00000008, 4, "zap???", info));
MALI_CHECK_NO_ERROR(writereg(0x00000008, 0, "enable paging", info));
MALI_SUCCESS;
}
-_mali_osk_errcode_t _mali_ukk_query_mmu_page_table_dump_size( _mali_uk_query_mmu_page_table_dump_size_s *args )
+_mali_osk_errcode_t _mali_ukk_query_mmu_page_table_dump_size(_mali_uk_query_mmu_page_table_dump_size_s *args)
{
struct dump_info info = { 0, 0, 0, NULL };
- struct mali_session_data * session_data;
+ struct mali_session_data *session_data;
+ session_data = (struct mali_session_data *)(uintptr_t)(args->ctx);
+ MALI_DEBUG_ASSERT_POINTER(session_data);
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
-
- session_data = (struct mali_session_data *)(args->ctx);
MALI_CHECK_NO_ERROR(dump_mmu_registers(session_data->page_directory, &info));
MALI_CHECK_NO_ERROR(dump_mmu_page_table(session_data->page_directory, &info));
MALI_SUCCESS;
}
-_mali_osk_errcode_t _mali_ukk_dump_mmu_page_table( _mali_uk_dump_mmu_page_table_s * args )
+_mali_osk_errcode_t _mali_ukk_dump_mmu_page_table(_mali_uk_dump_mmu_page_table_s *args)
{
struct dump_info info = { 0, 0, 0, NULL };
- struct mali_session_data * session_data;
+ struct mali_session_data *session_data;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
- MALI_CHECK_NON_NULL(args->buffer, _MALI_OSK_ERR_INVALID_ARGS);
- session_data = (struct mali_session_data *)(args->ctx);
+ session_data = (struct mali_session_data *)(uintptr_t)(args->ctx);
+ MALI_DEBUG_ASSERT_POINTER(session_data);
info.buffer_left = args->size;
- info.buffer = args->buffer;
+ info.buffer = (u32 *)(uintptr_t)args->buffer;
- args->register_writes = info.buffer;
+ args->register_writes = (uintptr_t)info.buffer;
MALI_CHECK_NO_ERROR(dump_mmu_registers(session_data->page_directory, &info));
- args->page_table_dump = info.buffer;
+ args->page_table_dump = (uintptr_t)info.buffer;
MALI_CHECK_NO_ERROR(dump_mmu_page_table(session_data->page_directory, &info));
args->register_writes_size = info.register_writes_size;
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_MMU_FLAGS_FORCE_GP_READ_ALLOCATE ( \
-MALI_MMU_FLAGS_PRESENT | \
- MALI_MMU_FLAGS_READ_PERMISSION | \
- MALI_MMU_FLAGS_WRITE_PERMISSION | \
- MALI_MMU_FLAGS_OVERRIDE_CACHE | \
- MALI_MMU_FLAGS_WRITE_CACHEABLE | \
- MALI_MMU_FLAGS_WRITE_BUFFERABLE | \
- MALI_MMU_FLAGS_READ_CACHEABLE | \
- MALI_MMU_FLAGS_READ_ALLOCATE )
+ MALI_MMU_FLAGS_PRESENT | \
+ MALI_MMU_FLAGS_READ_PERMISSION | \
+ MALI_MMU_FLAGS_WRITE_PERMISSION | \
+ MALI_MMU_FLAGS_OVERRIDE_CACHE | \
+ MALI_MMU_FLAGS_WRITE_CACHEABLE | \
+ MALI_MMU_FLAGS_WRITE_BUFFERABLE | \
+ MALI_MMU_FLAGS_READ_CACHEABLE | \
+ MALI_MMU_FLAGS_READ_ALLOCATE )
#define MALI_MMU_FLAGS_DEFAULT ( \
- MALI_MMU_FLAGS_PRESENT | \
- MALI_MMU_FLAGS_READ_PERMISSION | \
- MALI_MMU_FLAGS_WRITE_PERMISSION )
+ MALI_MMU_FLAGS_PRESENT | \
+ MALI_MMU_FLAGS_READ_PERMISSION | \
+ MALI_MMU_FLAGS_WRITE_PERMISSION )
struct mali_page_directory {
_mali_osk_errcode_t mali_mmu_pagedir_unmap(struct mali_page_directory *pagedir, u32 mali_address, u32 size);
/* Back virtual address space with actual pages. Assumes input is contiguous and 4k aligned. */
-void mali_mmu_pagedir_update(struct mali_page_directory *pagedir, u32 mali_address, u32 phys_address, u32 size, u32 cache_settings);
-
-u32 mali_page_directory_get_phys_address(struct mali_page_directory *pagedir, u32 index);
+void mali_mmu_pagedir_update(struct mali_page_directory *pagedir, u32 mali_address,
+ mali_dma_addr phys_address, u32 size, u32 permission_bits);
u32 mali_allocate_empty_page(mali_io_address *virtual);
-void mali_free_empty_page(u32 address, mali_io_address virtual);
-_mali_osk_errcode_t mali_create_fault_flush_pages(u32 *page_directory, mali_io_address *page_directory_mapping,
- u32 *page_table, mali_io_address *page_table_mapping,
- u32 *data_page, mali_io_address *data_page_mapping);
-void mali_destroy_fault_flush_pages(u32 *page_directory, mali_io_address *page_directory_mapping,
- u32 *page_table, mali_io_address *page_table_mapping,
- u32 *data_page, mali_io_address *data_page_mapping);
+void mali_free_empty_page(mali_dma_addr address, mali_io_address virt_addr);
+_mali_osk_errcode_t mali_create_fault_flush_pages(mali_dma_addr *page_directory,
+ mali_io_address *page_directory_mapping,
+ mali_dma_addr *page_table, mali_io_address *page_table_mapping,
+ mali_dma_addr *data_page, mali_io_address *data_page_mapping);
+void mali_destroy_fault_flush_pages(
+ mali_dma_addr *page_directory, mali_io_address *page_directory_mapping,
+ mali_dma_addr *page_table, mali_io_address *page_table_mapping,
+ mali_dma_addr *data_page, mali_io_address *data_page_mapping);
struct mali_page_directory *mali_mmu_pagedir_alloc(void);
void mali_mmu_pagedir_free(struct mali_page_directory *pagedir);
+void mali_mmu_pagedir_diag(struct mali_page_directory *pagedir, u32 fault_addr);
+
#endif /* __MALI_MMU_PAGE_DIRECTORY_H__ */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* to by \a ptr.
*/
#define _MALI_OSK_CONTAINER_OF(ptr, type, member) \
- ((type *)( ((char *)ptr) - offsetof(type,member) ))
+ ((type *)( ((char *)ptr) - offsetof(type,member) ))
/** @addtogroup _mali_osk_wq
* @{ */
* The returned pointer must be freed with \ref _mali_osk_wq_delete_work()
* when no longer needed.
*/
-_mali_osk_wq_work_t *_mali_osk_wq_create_work( _mali_osk_wq_work_handler_t handler, void *data );
+_mali_osk_wq_work_t *_mali_osk_wq_create_work(_mali_osk_wq_work_handler_t handler, void *data);
/** @brief A high priority version of \a _mali_osk_wq_create_work()
*
*
* Start the high priority work with: \a _mali_osk_wq_schedule_work_high_pri()
*/
-_mali_osk_wq_work_t *_mali_osk_wq_create_work_high_pri( _mali_osk_wq_work_handler_t handler, void *data );
+_mali_osk_wq_work_t *_mali_osk_wq_create_work_high_pri(_mali_osk_wq_work_handler_t handler, void *data);
/** @brief Delete a work object
*
* This will flush the work queue to ensure that the work handler will not
* be called after deletion.
*/
-void _mali_osk_wq_delete_work( _mali_osk_wq_work_t *work );
+void _mali_osk_wq_delete_work(_mali_osk_wq_work_t *work);
/** @brief Delete a work object
*
* This will NOT flush the work queue, so only call this if you are sure that the work handler will
* not be called after deletion.
*/
-void _mali_osk_wq_delete_work_nonflush( _mali_osk_wq_work_t *work );
+void _mali_osk_wq_delete_work_nonflush(_mali_osk_wq_work_t *work);
/** @brief Cause a queued, deferred call of the work handler
*
* @param work a pointer to the _mali_osk_wq_work_t object corresponding to the
* work to begin processing.
*/
-void _mali_osk_wq_schedule_work( _mali_osk_wq_work_t *work );
+void _mali_osk_wq_schedule_work(_mali_osk_wq_work_t *work);
/** @brief Cause a queued, deferred call of the high priority work handler
*
* This is allowed to sleep, but the work should be small since it will block
* all other applications.
*/
-void _mali_osk_wq_schedule_work_high_pri( _mali_osk_wq_work_t *work );
+void _mali_osk_wq_schedule_work_high_pri(_mali_osk_wq_work_t *work);
/** @brief Flush the work queue
*
* @return on success, a pointer to a _mali_osk_irq_t object, which represents
* the IRQ handling on this resource. NULL on failure.
*/
-_mali_osk_irq_t *_mali_osk_irq_init( u32 irqnum, _mali_osk_irq_uhandler_t uhandler, void *int_data, _mali_osk_irq_trigger_t trigger_func, _mali_osk_irq_ack_t ack_func, void *probe_data, const char *description );
+_mali_osk_irq_t *_mali_osk_irq_init(u32 irqnum, _mali_osk_irq_uhandler_t uhandler, void *int_data, _mali_osk_irq_trigger_t trigger_func, _mali_osk_irq_ack_t ack_func, void *probe_data, const char *description);
/** @brief Terminate IRQ handling on a resource.
*
* @param irq a pointer to the _mali_osk_irq_t object corresponding to the
* resource whose IRQ handling is to be terminated.
*/
-void _mali_osk_irq_term( _mali_osk_irq_t *irq );
+void _mali_osk_irq_term(_mali_osk_irq_t *irq);
/** @} */ /* end group _mali_osk_irq */
* @note It is an error to decrement the counter beyond -(1<<23)
*
* @param atom pointer to an atomic counter */
-void _mali_osk_atomic_dec( _mali_osk_atomic_t *atom );
+void _mali_osk_atomic_dec(_mali_osk_atomic_t *atom);
/** @brief Decrement an atomic counter, return new value
*
* @param atom pointer to an atomic counter
* @return The new value, after decrement */
-u32 _mali_osk_atomic_dec_return( _mali_osk_atomic_t *atom );
+u32 _mali_osk_atomic_dec_return(_mali_osk_atomic_t *atom);
/** @brief Increment an atomic counter
*
* @note It is an error to increment the counter beyond (1<<23)-1
*
* @param atom pointer to an atomic counter */
-void _mali_osk_atomic_inc( _mali_osk_atomic_t *atom );
+void _mali_osk_atomic_inc(_mali_osk_atomic_t *atom);
/** @brief Increment an atomic counter, return new value
*
* @param atom pointer to an atomic counter */
-u32 _mali_osk_atomic_inc_return( _mali_osk_atomic_t *atom );
+u32 _mali_osk_atomic_inc_return(_mali_osk_atomic_t *atom);
/** @brief Initialize an atomic counter
*
* @return _MALI_OSK_ERR_OK on success, otherwise, a suitable
* _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_osk_atomic_init( _mali_osk_atomic_t *atom, u32 val );
+_mali_osk_errcode_t _mali_osk_atomic_init(_mali_osk_atomic_t *atom, u32 val);
/** @brief Read a value from an atomic counter
*
*
* @param atom pointer to an atomic counter
*/
-u32 _mali_osk_atomic_read( _mali_osk_atomic_t *atom );
+u32 _mali_osk_atomic_read(_mali_osk_atomic_t *atom);
/** @brief Terminate an atomic counter
*
* @param atom pointer to an atomic counter
*/
-void _mali_osk_atomic_term( _mali_osk_atomic_t *atom );
+void _mali_osk_atomic_term(_mali_osk_atomic_t *atom);
/** @brief Assign a new val to atomic counter, and return the old atomic counter
*
* @param val the new value assign to the atomic counter
* @return the old value of the atomic counter
*/
-u32 _mali_osk_atomic_xchg( _mali_osk_atomic_t *atom, u32 val );
+u32 _mali_osk_atomic_xchg(_mali_osk_atomic_t *atom, u32 val);
/** @} */ /* end group _mali_osk_atomic */
* @param size Size of each element
* @return On success, the zero-initialized buffer allocated. NULL on failure
*/
-void *_mali_osk_calloc( u32 n, u32 size );
+void *_mali_osk_calloc(u32 n, u32 size);
/** @brief Allocate memory.
*
* @param size Number of bytes to allocate
* @return On success, the buffer allocated. NULL on failure.
*/
-void *_mali_osk_malloc( u32 size );
+void *_mali_osk_malloc(u32 size);
/** @brief Free memory.
*
*
* @param ptr Pointer to buffer to free
*/
-void _mali_osk_free( void *ptr );
+void _mali_osk_free(void *ptr);
/** @brief Allocate memory.
*
* @param size Number of bytes to allocate
* @return On success, the buffer allocated. NULL on failure.
*/
-void *_mali_osk_valloc( u32 size );
+void *_mali_osk_valloc(u32 size);
/** @brief Free memory.
*
*
* @param ptr Pointer to buffer to free
*/
-void _mali_osk_vfree( void *ptr );
+void _mali_osk_vfree(void *ptr);
/** @brief Copies memory.
*
* @param len Number of bytes to copy.
* @return \a dst is always passed through unmodified.
*/
-void *_mali_osk_memcpy( void *dst, const void *src, u32 len );
+void *_mali_osk_memcpy(void *dst, const void *src, u32 len);
/** @brief Fills memory.
*
* @param n Number of bytes to be set to the value.
* @return \a s is always passed through unmodified
*/
-void *_mali_osk_memset( void *s, u32 c, u32 n );
+void *_mali_osk_memset(void *s, u32 c, u32 n);
/** @} */ /* end group _mali_osk_memory */
* @return MALI_TRUE when \a max_allocated bytes are not in use yet. MALI_FALSE
* when at least \a max_allocated bytes are in use.
*/
-mali_bool _mali_osk_mem_check_allocated( u32 max_allocated );
+mali_bool _mali_osk_mem_check_allocated(u32 max_allocated);
/** @addtogroup _mali_osk_low_level_memory
* This defines an arbitrary memory barrier operation, which forces an ordering constraint
* on memory read and write operations.
*/
-void _mali_osk_mem_barrier( void );
+void _mali_osk_mem_barrier(void);
/** @brief Issue a write memory barrier
*
* This defines an write memory barrier operation which forces an ordering constraint
* on memory write operations.
*/
-void _mali_osk_write_mem_barrier( void );
+void _mali_osk_write_mem_barrier(void);
/** @brief Map a physically contiguous region into kernel space
*
* @return On success, a Mali IO address through which the mapped-in
* memory/registers can be accessed. NULL on failure.
*/
-mali_io_address _mali_osk_mem_mapioregion( u32 phys, u32 size, const char *description );
+mali_io_address _mali_osk_mem_mapioregion(u32 phys, u32 size, const char *description);
/** @brief Unmap a physically contiguous address range from kernel space.
*
* @param mapping The Mali IO address through which the mapping is
* accessed.
*/
-void _mali_osk_mem_unmapioregion( u32 phys, u32 size, mali_io_address mapping );
+void _mali_osk_mem_unmapioregion(u32 phys, u32 size, mali_io_address mapping);
/** @brief Allocate and Map a physically contiguous region into kernel space
*
* @return On success, a Mali IO address through which the mapped-in
* memory/registers can be accessed. NULL on failure, and (*phys) is unmodified.
*/
-mali_io_address _mali_osk_mem_allocioregion( u32 *phys, u32 size );
+mali_io_address _mali_osk_mem_allocioregion(u32 *phys, u32 size);
/** @brief Free a physically contiguous address range from kernel space.
*
* @param mapping The Mali IO address through which the mapping is
* accessed.
*/
-void _mali_osk_mem_freeioregion( u32 phys, u32 size, mali_io_address mapping );
+void _mali_osk_mem_freeioregion(u32 phys, u32 size, mali_io_address mapping);
/** @brief Request a region of physically contiguous memory
*
* @return _MALI_OSK_ERR_OK on success. Otherwise, a suitable
* _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_osk_mem_reqregion( u32 phys, u32 size, const char *description );
+_mali_osk_errcode_t _mali_osk_mem_reqregion(u32 phys, u32 size, const char *description);
/** @brief Un-request a region of physically contiguous memory
*
* @param size the number of bytes of physically contiguous address space to
* un-request.
*/
-void _mali_osk_mem_unreqregion( u32 phys, u32 size );
+void _mali_osk_mem_unreqregion(u32 phys, u32 size);
/** @brief Read from a location currently mapped in through
* _mali_osk_mem_mapioregion
* @param offset Byte offset from the given IO address to operate on, must be a multiple of 4
* @return the 32-bit word from the specified location.
*/
-u32 _mali_osk_mem_ioread32( volatile mali_io_address mapping, u32 offset );
+u32 _mali_osk_mem_ioread32(volatile mali_io_address mapping, u32 offset);
/** @brief Write to a location currently mapped in through
* _mali_osk_mem_mapioregion without memory barriers
* @param offset Byte offset from the given IO address to operate on, must be a multiple of 4
* @param val the 32-bit word to write.
*/
-void _mali_osk_mem_iowrite32_relaxed( volatile mali_io_address addr, u32 offset, u32 val );
+void _mali_osk_mem_iowrite32_relaxed(volatile mali_io_address addr, u32 offset, u32 val);
/** @brief Write to a location currently mapped in through
* _mali_osk_mem_mapioregion with write memory barrier
* @param offset Byte offset from the given IO address to operate on, must be a multiple of 4
* @param val the 32-bit word to write.
*/
-void _mali_osk_mem_iowrite32( volatile mali_io_address mapping, u32 offset, u32 val );
+void _mali_osk_mem_iowrite32(volatile mali_io_address mapping, u32 offset, u32 val);
/** @brief Flush all CPU caches
*
* This should only be implemented if flushing of the cache is required for
* memory mapped in through _mali_osk_mem_mapregion.
*/
-void _mali_osk_cache_flushall( void );
+void _mali_osk_cache_flushall(void);
/** @brief Flush any caches necessary for the CPU and MALI to have the same view of a range of uncached mapped memory
*
* They zero the memory through a cached mapping, then flush the inner caches but not the outer caches.
* This is required for MALI to have the correct view of the memory.
*/
-void _mali_osk_cache_ensure_uncached_range_flushed( void *uncached_mapping, u32 offset, u32 size );
+void _mali_osk_cache_ensure_uncached_range_flushed(void *uncached_mapping, u32 offset, u32 size);
+
+/** @brief Safely copy as much data as possible from src to dest
+ *
+ * Do not crash if src or dest isn't available.
+ *
+ * @param dest Destination buffer (limited to user space mapped Mali memory)
+ * @param src Source buffer
+ * @param size Number of bytes to copy
+ * @return Number of bytes actually copied
+ */
+u32 _mali_osk_mem_write_safe(void *dest, const void *src, u32 size);
/** @} */ /* end group _mali_osk_low_level_memory */
* @param size The size of the type specific buffer to send
* @return Pointer to a notification object with a suitable buffer, or NULL on error.
*/
-_mali_osk_notification_t *_mali_osk_notification_create( u32 type, u32 size );
+_mali_osk_notification_t *_mali_osk_notification_create(u32 type, u32 size);
/** @brief Delete a notification object
*
*
* @param object the notification object to delete.
*/
-void _mali_osk_notification_delete( _mali_osk_notification_t *object );
+void _mali_osk_notification_delete(_mali_osk_notification_t *object);
/** @brief Create a notification queue
*
*
* @return Pointer to a new notification queue or NULL on error.
*/
-_mali_osk_notification_queue_t *_mali_osk_notification_queue_init( void );
+_mali_osk_notification_queue_t *_mali_osk_notification_queue_init(void);
/** @brief Destroy a notification queue
*
*
* @param queue The queue to destroy
*/
-void _mali_osk_notification_queue_term( _mali_osk_notification_queue_t *queue );
+void _mali_osk_notification_queue_term(_mali_osk_notification_queue_t *queue);
/** @brief Schedule notification for delivery
*
* @param queue The notification queue to add this notification to
* @param object The entry to add
*/
-void _mali_osk_notification_queue_send( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t *object );
+void _mali_osk_notification_queue_send(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t *object);
/** @brief Receive a notification from a queue
*
* \ref _mali_osk_notification_t object, or NULL if none were received.
* @return _MALI_OSK_ERR_OK on success. _MALI_OSK_ERR_RESTARTSYSCALL if the sleep was interrupted.
*/
-_mali_osk_errcode_t _mali_osk_notification_queue_receive( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result );
+_mali_osk_errcode_t _mali_osk_notification_queue_receive(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result);
/** @brief Dequeues a notification from a queue
*
* \ref _mali_osk_notification_t object, or NULL if none were received.
* @return _MALI_OSK_ERR_OK on success, _MALI_OSK_ERR_ITEM_NOT_FOUND if queue was empty.
*/
-_mali_osk_errcode_t _mali_osk_notification_queue_dequeue( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result );
+_mali_osk_errcode_t _mali_osk_notification_queue_dequeue(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result);
/** @} */ /* end group _mali_osk_notification */
* @param ticks_to_expire the amount of time in ticks for the timer to run
* before triggering.
*/
-void _mali_osk_timer_add( _mali_osk_timer_t *tim, u32 ticks_to_expire );
+void _mali_osk_timer_add(_mali_osk_timer_t *tim, u32 ticks_to_expire);
/** @brief Modify a timer
*
* should trigger.
*
*/
-void _mali_osk_timer_mod( _mali_osk_timer_t *tim, u32 ticks_to_expire);
+void _mali_osk_timer_mod(_mali_osk_timer_t *tim, u32 ticks_to_expire);
/** @brief Stop a timer, and block on its completion.
*
* @param tim the timer to stop.
*
*/
-void _mali_osk_timer_del( _mali_osk_timer_t *tim );
+void _mali_osk_timer_del(_mali_osk_timer_t *tim);
/** @brief Stop a timer.
*
*
* @param tim the timer to stop.
*/
-void _mali_osk_timer_del_async( _mali_osk_timer_t *tim );
+void _mali_osk_timer_del_async(_mali_osk_timer_t *tim);
/** @brief Check if timer is pending.
*
* @param tim the timer to check
* @return MALI_TRUE if time is active, MALI_FALSE if it is not active
*/
-mali_bool _mali_osk_timer_pending( _mali_osk_timer_t *tim);
+mali_bool _mali_osk_timer_pending(_mali_osk_timer_t *tim);
/** @brief Set a timer's callback parameters.
*
* @param callback Function to call when timer expires
* @param data Function-specific data to supply to the function on expiry.
*/
-void _mali_osk_timer_setcallback( _mali_osk_timer_t *tim, _mali_osk_timer_callback_t callback, void *data );
+void _mali_osk_timer_setcallback(_mali_osk_timer_t *tim, _mali_osk_timer_callback_t callback, void *data);
/** @brief Terminate a timer, and deallocate resources.
*
*
* @param tim the timer to deallocate.
*/
-void _mali_osk_timer_term( _mali_osk_timer_t *tim );
+void _mali_osk_timer_term(_mali_osk_timer_t *tim);
/** @} */ /* end group _mali_osk_timer */
* @return non-zero if ticka represents a time that occurs after tickb.
* Zero otherwise.
*/
-int _mali_osk_time_after( u32 ticka, u32 tickb );
+int _mali_osk_time_after(u32 ticka, u32 tickb);
/** @brief Convert milliseconds to OS 'ticks'
*
* @param ms time interval in milliseconds
* @return the corresponding time interval in OS ticks.
*/
-u32 _mali_osk_time_mstoticks( u32 ms );
+u32 _mali_osk_time_mstoticks(u32 ms);
/** @brief Convert OS 'ticks' to milliseconds
*
* @param ticks time interval in OS ticks.
* @return the corresponding time interval in milliseconds
*/
-u32 _mali_osk_time_tickstoms( u32 ticks );
+u32 _mali_osk_time_tickstoms(u32 ticks);
/** @brief Get the current time in OS 'ticks'.
* @return the current time in OS 'ticks'.
*/
-u32 _mali_osk_time_tickcount( void );
+u32 _mali_osk_time_tickcount(void);
/** @brief Cause a microsecond delay
*
*
* @param usecs the number of microseconds to wait for.
*/
-void _mali_osk_time_ubusydelay( u32 usecs );
+void _mali_osk_time_ubusydelay(u32 usecs);
/** @brief Return time in nano seconds, since any given reference.
*
* @return Time in nano seconds
*/
-u64 _mali_osk_time_get_ns( void );
+u64 _mali_osk_time_get_ns(void);
/** @} */ /* end group _mali_osk_time */
* @param val 32-bit words to count leading zeros on
* @return the number of leading zeros.
*/
-u32 _mali_osk_clz( u32 val );
+u32 _mali_osk_clz(u32 val);
/** @brief find last (most-significant) bit set
*
* @param val 32-bit words to count last bit set on
* @return last bit set.
*/
-u32 _mali_osk_fls( u32 val );
+u32 _mali_osk_fls(u32 val);
/** @} */ /* end group _mali_osk_math */
* @{ */
/** @brief Initialize an empty Wait Queue */
-_mali_osk_wait_queue_t* _mali_osk_wait_queue_init( void );
+_mali_osk_wait_queue_t *_mali_osk_wait_queue_init(void);
/** @brief Sleep if condition is false
*
* being asked to wake up again, the condition will be re-checked and the
* thread only woken up if the condition is now true.
*/
-void _mali_osk_wait_queue_wait_event( _mali_osk_wait_queue_t *queue, mali_bool (*condition)(void *), void *data );
+void _mali_osk_wait_queue_wait_event(_mali_osk_wait_queue_t *queue, mali_bool(*condition)(void *), void *data);
/** @brief Sleep if condition is false
*
* thread only woken up if the condition is now true. Will return if time
* exceeds timeout.
*/
-void _mali_osk_wait_queue_wait_event_timeout( _mali_osk_wait_queue_t *queue, mali_bool (*condition)(void *), void *data, u32 timeout );
+void _mali_osk_wait_queue_wait_event_timeout(_mali_osk_wait_queue_t *queue, mali_bool(*condition)(void *), void *data, u32 timeout);
/** @brief Wake up all threads in wait queue if their respective conditions are
* true
*
* Wake up all threads in wait queue \a queue whose condition is now true.
*/
-void _mali_osk_wait_queue_wake_up( _mali_osk_wait_queue_t *queue );
+void _mali_osk_wait_queue_wake_up(_mali_osk_wait_queue_t *queue);
/** @brief terminate a wait queue
*
* @param queue the queue to terminate.
*/
-void _mali_osk_wait_queue_term( _mali_osk_wait_queue_t *queue );
+void _mali_osk_wait_queue_term(_mali_osk_wait_queue_t *queue);
/** @} */ /* end group _mali_osk_wait_queue */
* @param fmt a _mali_osu_vsnprintf() style format string
* @param ... a variable-number of parameters suitable for \a fmt
*/
-void _mali_osk_dbgmsg( const char *fmt, ... );
+void _mali_osk_dbgmsg(const char *fmt, ...);
/** @brief Print fmt into buf.
*
* @param ... a variable-number of parameters suitable for \a fmt
* @return The number of bytes written to \a buf
*/
-u32 _mali_osk_snprintf( char *buf, u32 size, const char *fmt, ... );
+u32 _mali_osk_snprintf(char *buf, u32 size, const char *fmt, ...);
+
+/** @brief Print fmt into print_ctx.
+ *
+ * The interpretation of \a fmt is the same as the \c format parameter in
+ * _mali_osu_vsnprintf().
+ *
+ * @param print_ctx a pointer to the result file buffer
+ * @param fmt a _mali_osu_vsnprintf() style format string
+ * @param ... a variable-number of parameters suitable for \a fmt
+ */
+void _mali_osk_ctxprintf(_mali_osk_print_ctx *print_ctx, const char *fmt, ...);
/** @brief Abnormal process abort.
*
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
extern "C" {
#endif
-MALI_STATIC_INLINE void _mali_internal_clear_bit( u32 bit, u32 *addr )
+MALI_STATIC_INLINE void _mali_internal_clear_bit(u32 bit, u32 *addr)
{
- MALI_DEBUG_ASSERT( bit < 32 );
- MALI_DEBUG_ASSERT( NULL != addr );
+ MALI_DEBUG_ASSERT(bit < 32);
+ MALI_DEBUG_ASSERT(NULL != addr);
(*addr) &= ~(1 << bit);
}
-MALI_STATIC_INLINE void _mali_internal_set_bit( u32 bit, u32 *addr )
+MALI_STATIC_INLINE void _mali_internal_set_bit(u32 bit, u32 *addr)
{
- MALI_DEBUG_ASSERT( bit < 32 );
- MALI_DEBUG_ASSERT( NULL != addr );
+ MALI_DEBUG_ASSERT(bit < 32);
+ MALI_DEBUG_ASSERT(NULL != addr);
(*addr) |= (1 << bit);
}
-MALI_STATIC_INLINE u32 _mali_internal_test_bit( u32 bit, u32 value )
+MALI_STATIC_INLINE u32 _mali_internal_test_bit(u32 bit, u32 value)
{
- MALI_DEBUG_ASSERT( bit < 32 );
+ MALI_DEBUG_ASSERT(bit < 32);
return value & (1 << bit);
}
-MALI_STATIC_INLINE int _mali_internal_find_first_zero_bit( u32 value )
+MALI_STATIC_INLINE int _mali_internal_find_first_zero_bit(u32 value)
{
u32 inverted;
u32 negated;
* See ARM System Developers Guide for details of count_trailing_zeros */
/* Isolate the zero: it is preceeded by a run of 1s, so add 1 to it */
- negated = (u32)-inverted ; /* -a == ~a + 1 (mod 2^n) for n-bit numbers */
+ negated = (u32) - inverted ; /* -a == ~a + 1 (mod 2^n) for n-bit numbers */
/* negated = xxx...x1000...0 */
isolated = negated & inverted ; /* xxx...x1000...0 & zzz...z1000...0, zs are ~xs */
/* And so the first zero bit is in the same position as the 1 == number of 1s that preceeded it
* Note that the output is zero if value was all 1s */
- leading_zeros = _mali_osk_clz( isolated );
+ leading_zeros = _mali_osk_clz(isolated);
return 31 - leading_zeros;
}
* significant bit
* @param addr starting point for counting.
*/
-MALI_STATIC_INLINE void _mali_osk_clear_nonatomic_bit( u32 nr, u32 *addr )
+MALI_STATIC_INLINE void _mali_osk_clear_nonatomic_bit(u32 nr, u32 *addr)
{
addr += nr >> 5; /* find the correct word */
- nr = nr & ((1 << 5)-1); /* The bit number within the word */
+ nr = nr & ((1 << 5) - 1); /* The bit number within the word */
- _mali_internal_clear_bit( nr, addr );
+ _mali_internal_clear_bit(nr, addr);
}
/** @brief Set a bit in a sequence of 32-bit words
* significant bit
* @param addr starting point for counting.
*/
-MALI_STATIC_INLINE void _mali_osk_set_nonatomic_bit( u32 nr, u32 *addr )
+MALI_STATIC_INLINE void _mali_osk_set_nonatomic_bit(u32 nr, u32 *addr)
{
addr += nr >> 5; /* find the correct word */
- nr = nr & ((1 << 5)-1); /* The bit number within the word */
+ nr = nr & ((1 << 5) - 1); /* The bit number within the word */
- _mali_internal_set_bit( nr, addr );
+ _mali_internal_set_bit(nr, addr);
}
/** @brief Test a bit in a sequence of 32-bit words
* @return zero if bit was clear, non-zero if set. Do not rely on the return
* value being related to the actual word under test.
*/
-MALI_STATIC_INLINE u32 _mali_osk_test_bit( u32 nr, u32 *addr )
+MALI_STATIC_INLINE u32 _mali_osk_test_bit(u32 nr, u32 *addr)
{
addr += nr >> 5; /* find the correct word */
- nr = nr & ((1 << 5)-1); /* The bit number within the word */
+ nr = nr & ((1 << 5) - 1); /* The bit number within the word */
- return _mali_internal_test_bit( nr, *addr );
+ return _mali_internal_test_bit(nr, *addr);
}
/* Return maxbit if not found */
* @return the number of the first zero bit found, or maxbit if none were found
* in the specified range.
*/
-MALI_STATIC_INLINE u32 _mali_osk_find_first_zero_bit( const u32 *addr, u32 maxbit )
+MALI_STATIC_INLINE u32 _mali_osk_find_first_zero_bit(const u32 *addr, u32 maxbit)
{
u32 total;
- for ( total = 0; total < maxbit; total += 32, ++addr ) {
+ for (total = 0; total < maxbit; total += 32, ++addr) {
int result;
- result = _mali_internal_find_first_zero_bit( *addr );
+ result = _mali_internal_find_first_zero_bit(*addr);
/* non-negative signifies the bit was found */
- if ( result >= 0 ) {
+ if (result >= 0) {
total += (u32)result;
break;
}
}
/* Now check if we reached maxbit or above */
- if ( total >= maxbit ) {
+ if (total >= maxbit) {
total = maxbit;
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*
* @param list the list element to initialize
*/
-MALI_STATIC_INLINE void _mali_osk_list_init( _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_init(_mali_osk_list_t *list)
{
list->next = list;
list->prev = list;
* @param list the list in which to insert. The new element will be the next
* entry in this list
*/
-MALI_STATIC_INLINE void _mali_osk_list_add( _mali_osk_list_t *new_entry, _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_add(_mali_osk_list_t *new_entry, _mali_osk_list_t *list)
{
__mali_osk_list_add(new_entry, list, list->next);
}
* @param list the list in which to insert. The new element will be the previous
* entry in this list
*/
-MALI_STATIC_INLINE void _mali_osk_list_addtail( _mali_osk_list_t *new_entry, _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_addtail(_mali_osk_list_t *new_entry, _mali_osk_list_t *list)
{
__mali_osk_list_add(new_entry, list->prev, list);
}
*
* @param list the list element to remove.
*/
-MALI_STATIC_INLINE void _mali_osk_list_del( _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_del(_mali_osk_list_t *list)
{
__mali_osk_list_del(list->prev, list->next);
}
*
* @param list the list element to remove and initialize.
*/
-MALI_STATIC_INLINE void _mali_osk_list_delinit( _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_delinit(_mali_osk_list_t *list)
{
__mali_osk_list_del(list->prev, list->next);
_mali_osk_list_init(list);
* @param list the list to check.
* @return non-zero if the list is empty, and zero otherwise.
*/
-MALI_STATIC_INLINE mali_bool _mali_osk_list_empty( _mali_osk_list_t *list )
+MALI_STATIC_INLINE mali_bool _mali_osk_list_empty(_mali_osk_list_t *list)
{
return list->next == list;
}
* @param list the new list into which the element will be inserted, as the next
* element in the list.
*/
-MALI_STATIC_INLINE void _mali_osk_list_move( _mali_osk_list_t *move_entry, _mali_osk_list_t *list )
+MALI_STATIC_INLINE void _mali_osk_list_move(_mali_osk_list_t *move_entry, _mali_osk_list_t *list)
{
__mali_osk_list_del(move_entry->prev, move_entry->next);
_mali_osk_list_add(move_entry, list);
* @param old_list The existing list head
* @param new_list The new list head (must be an empty list)
*/
-MALI_STATIC_INLINE void _mali_osk_list_move_list( _mali_osk_list_t *old_list, _mali_osk_list_t *new_list )
+MALI_STATIC_INLINE void _mali_osk_list_move_list(_mali_osk_list_t *old_list, _mali_osk_list_t *new_list)
{
MALI_DEBUG_ASSERT(_mali_osk_list_empty(new_list));
if (!_mali_osk_list_empty(old_list)) {
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/** @brief Struct with device specific configuration data
*/
-struct _mali_osk_device_data {
- /* Dedicated GPU memory range (physical). */
- u32 dedicated_mem_start;
- u32 dedicated_mem_size;
-
- /* Shared GPU memory */
- u32 shared_mem_size;
-
- /* Frame buffer memory to be accessible by Mali GPU (physical) */
- u32 fb_start;
- u32 fb_size;
-
- /* Max runtime [ms] for jobs */
- int max_job_runtime;
-
- /* Report GPU utilization in this interval (specified in ms) */
- u32 utilization_interval;
-
- /* Function that will receive periodic GPU utilization numbers */
- void (*utilization_callback)(struct mali_gpu_utilization_data *data);
-
- /*
- * Mali PMU switch delay.
- * Only needed if the power gates are connected to the PMU in a high fanout
- * network. This value is the number of Mali clock cycles it takes to
- * enable the power gates and turn on the power mesh.
- * This value will have no effect if a daisy chain implementation is used.
- */
- u32 pmu_switch_delay;
-
- /* Mali Dynamic power domain configuration in sequence from 0-11
- * GP PP0 PP1 PP2 PP3 PP4 PP5 PP6 PP7, L2$0 L2$1 L2$2
- */
- u16 pmu_domain_config[12];
-
- /* Fuction that platform callback for freq tunning, needed when MALI400_POWER_PERFORMANCE_POLICY enabled */
- int (*set_freq_callback)(unsigned int mhz);
-};
+typedef struct mali_gpu_device_data _mali_osk_device_data;
/** @brief Find Mali GPU HW resource
*
*
* @return _MALI_OSK_ERR_OK on success, otherwise failure.
*/
-_mali_osk_errcode_t _mali_osk_device_data_get(struct _mali_osk_device_data *data);
+_mali_osk_errcode_t _mali_osk_device_data_get(_mali_osk_device_data *data);
/** @brief Determines if Mali GPU has been configured with shared interrupts.
*
/** @} */ /* end group _mali_osk_miscellaneous */
-/** @addtogroup _mali_osk_low_level_memory
- * @{ */
-
-/** @brief Copy as much data as possible from src to dest, do not crash if src or dest isn't available.
- *
- * @param dest Destination buffer (limited to user space mapped Mali memory)
- * @param src Source buffer
- * @param size Number of bytes to copy
- * @return Number of bytes actually copied
- */
-u32 _mali_osk_mem_write_safe(void *dest, const void *src, u32 size);
-
-/** @} */ /* end group _mali_osk_low_level_memory */
-
-
#ifdef __cplusplus
}
#endif
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @param limit The desired maximum number of events to record on input, the actual maximum on output.
* @return _MALI_OSK_ERR_OK on success, otherwise failure.
*/
-_mali_osk_errcode_t _mali_osk_profiling_start(u32 * limit);
+_mali_osk_errcode_t _mali_osk_profiling_start(u32 *limit);
/**
* Add an profiling event
* @param count Returns the number of recorded events.
* @return _MALI_OSK_ERR_OK on success, otherwise failure.
*/
-_mali_osk_errcode_t _mali_osk_profiling_stop(u32 * count);
+_mali_osk_errcode_t _mali_osk_profiling_stop(u32 *count);
/**
* Retrieves the number of events that can be retrieved
* @param data The 5 data values for the retrieved event will be stored here.
* @return _MALI_OSK_ERR_OK on success, otherwise failure.
*/
-_mali_osk_errcode_t _mali_osk_profiling_get_event(u32 index, u64* timestamp, u32* event_id, u32 data[5]);
+_mali_osk_errcode_t _mali_osk_profiling_get_event(u32 index, u64 *timestamp, u32 *event_id, u32 data[5]);
/**
* Clear the recorded buffer.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*
* @param arg resource-specific data
*/
-typedef void (*_mali_osk_wq_work_handler_t)( void * arg );
+typedef void (*_mali_osk_wq_work_handler_t)(void *arg);
/* @} */ /* end group _mali_osk_wq */
*
* This function is implemented by the common layer to allow probing of a resource's IRQ.
* @param arg resource-specific data */
-typedef void (*_mali_osk_irq_trigger_t)( void * arg );
+typedef void (*_mali_osk_irq_trigger_t)(void *arg);
/** @brief Optional function to acknowledge an irq from a resource
*
* This function is implemented by the common layer to allow probing of a resource's IRQ.
* @param arg resource-specific data
* @return _MALI_OSK_ERR_OK if the IRQ was successful, or a suitable _mali_osk_errcode_t on failure. */
-typedef _mali_osk_errcode_t (*_mali_osk_irq_ack_t)( void * arg );
+typedef _mali_osk_errcode_t (*_mali_osk_irq_ack_t)(void *arg);
/** @brief IRQ 'upper-half' handler callback.
*
* @return _MALI_OSK_ERR_OK if the IRQ was correctly handled, or a suitable
* _mali_osk_errcode_t otherwise.
*/
-typedef _mali_osk_errcode_t (*_mali_osk_irq_uhandler_t)( void * arg );
+typedef _mali_osk_errcode_t (*_mali_osk_irq_uhandler_t)(void *arg);
/** @} */ /* end group _mali_osk_irq */
* Access to this range must be made through the _mali_osk_mem_ioread32() and
* _mali_osk_mem_iowrite32() functions.
*/
-typedef struct _mali_io_address * mali_io_address;
+typedef struct _mali_io_address *mali_io_address;
/** @defgroup _MALI_OSK_CPU_PAGE CPU Physical page size macros.
*
typedef struct _mali_osk_notification_t_struct {
u32 notification_type; /**< The notification type */
u32 result_buffer_size; /**< Size of the result buffer to copy to user space */
- void * result_buffer; /**< Buffer containing any type specific data */
+ void *result_buffer; /**< Buffer containing any type specific data */
} _mali_osk_notification_t;
/** @} */ /* end group _mali_osk_notification */
* by any callers of _mali_osk_timer_del(). Otherwise, a deadlock may occur.
*
* @param arg Function-specific data */
-typedef void (*_mali_osk_timer_callback_t)(void * arg);
+typedef void (*_mali_osk_timer_callback_t)(void *arg);
/** @brief Private type for Timer Callback Objects */
typedef struct _mali_osk_timer_t_struct _mali_osk_timer_t;
* Platform independent representation of a Mali HW resource
*/
typedef struct _mali_osk_resource {
- const char * description; /**< short description of the resource */
+ const char *description; /**< short description of the resource */
u32 base; /**< Physical base address of the resource, as seen by Mali resources. */
u32 irq; /**< IRQ number delivered to the CPU, or -1 to tell the driver to probe for it (if possible) */
} _mali_osk_resource_t;
/** @} */ /* end group uddapi */
+/** @brief Mali print ctx type which uses seq_file
+ */
+typedef struct seq_file _mali_osk_print_ctx;
+
#ifdef __cplusplus
}
#endif
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct mali_pm_domain *mali_pm_domain_create(u32 pmu_mask)
{
- struct mali_pm_domain* domain = NULL;
+ struct mali_pm_domain *domain = NULL;
u32 domain_id = 0;
domain = mali_pm_domain_get_from_mask(pmu_mask);
if (0 == mask) return NULL;
- id = _mali_osk_fls(mask)-1;
+ id = _mali_osk_fls(mask) - 1;
MALI_DEBUG_ASSERT(MALI_MAX_NUMBER_OF_DOMAINS > id);
/* Verify that pmu_mask only one bit is set */
if (_MALI_OSK_ERR_OK != err && _MALI_OSK_ERR_BUSY != err) {
MALI_PRINT_ERROR(("PM Domain: Failed to power up PM domain 0x%08x\n",
- domain->pmu_mask));
+ domain->pmu_mask));
}
}
mali_pm_domain_state_set(domain, MALI_PM_DOMAIN_ON);
if (_MALI_OSK_ERR_OK != err && _MALI_OSK_ERR_BUSY != err) {
MALI_PRINT_ERROR(("PM Domain: Failed to power down PM domain 0x%08x\n",
- domain->pmu_mask));
+ domain->pmu_mask));
}
}
}
mali_pm_domain_unlock(domain);
}
- if(!_mali_osk_pm_dev_ref_add_no_power_on()) {
+ if (!_mali_osk_pm_dev_ref_add_no_power_on()) {
is_powered = MALI_FALSE;
}
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_pm.h"
#include "mali_osk_mali.h"
-u16 mali_pmu_global_domain_config[MALI_MAX_NUMBER_OF_DOMAINS]= {0};
+u16 mali_pmu_global_domain_config[MALI_MAX_NUMBER_OF_DOMAINS] = {0};
static u32 mali_pmu_detect_mask(void);
struct mali_pmu_core *mali_pmu_create(_mali_osk_resource_t *resource)
{
- struct mali_pmu_core* pmu;
+ struct mali_pmu_core *pmu;
MALI_DEBUG_ASSERT(NULL == mali_global_pmu_core);
MALI_DEBUG_PRINT(2, ("Mali PMU: Creating Mali PMU core\n"));
if (_MALI_OSK_ERR_OK == mali_hw_core_create(&pmu->hw_core, resource, PMU_REGISTER_ADDRESS_SPACE_SIZE)) {
_mali_osk_errcode_t err;
- struct _mali_osk_device_data data = { 0, };
+ _mali_osk_device_data data = { 0, };
err = _mali_osk_device_data_get(&data);
if (_MALI_OSK_ERR_OK == err) {
MALI_DEBUG_ASSERT_POINTER(pmu);
MALI_DEBUG_ASSERT(0 == (mali_hw_core_register_read(&pmu->hw_core, PMU_REG_ADDR_MGMT_INT_RAWSTAT)
- & PMU_REG_VAL_IRQ));
+ & PMU_REG_VAL_IRQ));
stat = mali_hw_core_register_read(&pmu->hw_core, PMU_REG_ADDR_MGMT_STATUS);
stat &= pmu->registered_cores_mask;
}
if (swt_dly != pmu->switch_delay)
mali_hw_core_register_write_relaxed(&pmu->hw_core, PMU_REG_ADDR_MGMT_SW_DELAY, pmu->switch_delay);
-
#endif
#if defined(DEBUG)
MALI_DEBUG_ASSERT_POINTER(pmu);
MALI_DEBUG_ASSERT(0 == (mali_hw_core_register_read(&pmu->hw_core, PMU_REG_ADDR_MGMT_INT_RAWSTAT)
- & PMU_REG_VAL_IRQ));
+ & PMU_REG_VAL_IRQ));
stat = mali_hw_core_register_read(&pmu->hw_core, PMU_REG_ADDR_MGMT_STATUS);
stat &= pmu->registered_cores_mask;
stat = mali_hw_core_register_read(&pmu->hw_core, PMU_REG_ADDR_MGMT_STATUS);
cores_off_mask = pmu->registered_cores_mask & ~(stat | pmu->active_cores_mask);
- cores_on_mask = pmu->registered_cores_mask & (stat & pmu->active_cores_mask);
+ cores_on_mask = pmu->registered_cores_mask & (stat & pmu->active_cores_mask);
if (0 != cores_off_mask) {
err = mali_pmu_power_down_internal(pmu, cores_off_mask);
_mali_osk_errcode_t err;
MALI_DEBUG_ASSERT_POINTER(pmu);
- MALI_DEBUG_ASSERT(pmu->registered_cores_mask != 0 );
+ MALI_DEBUG_ASSERT(pmu->registered_cores_mask != 0);
/* Make sure we have a valid power domain mask */
if (mask > pmu->registered_cores_mask) {
_mali_osk_errcode_t err;
MALI_DEBUG_ASSERT_POINTER(pmu);
- MALI_DEBUG_ASSERT(pmu->registered_cores_mask != 0 );
+ MALI_DEBUG_ASSERT(pmu->registered_cores_mask != 0);
/* Make sure we have a valid power domain mask */
if (mask & ~pmu->registered_cores_mask) {
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_osk.h"
-#define MALI_GP_DOMAIN_INDEX 0
-#define MALI_PP0_DOMAIN_INDEX 1
-#define MALI_PP1_DOMAIN_INDEX 2
-#define MALI_PP2_DOMAIN_INDEX 3
-#define MALI_PP3_DOMAIN_INDEX 4
-#define MALI_PP4_DOMAIN_INDEX 5
-#define MALI_PP5_DOMAIN_INDEX 6
-#define MALI_PP6_DOMAIN_INDEX 7
-#define MALI_PP7_DOMAIN_INDEX 8
-#define MALI_L20_DOMAIN_INDEX 9
-#define MALI_L21_DOMAIN_INDEX 10
-#define MALI_L22_DOMAIN_INDEX 11
-
-#define MALI_MAX_NUMBER_OF_DOMAINS 12
+#define MALI_GP_DOMAIN_INDEX 0
+#define MALI_PP0_DOMAIN_INDEX 1
+#define MALI_PP1_DOMAIN_INDEX 2
+#define MALI_PP2_DOMAIN_INDEX 3
+#define MALI_PP3_DOMAIN_INDEX 4
+#define MALI_PP4_DOMAIN_INDEX 5
+#define MALI_PP5_DOMAIN_INDEX 6
+#define MALI_PP6_DOMAIN_INDEX 7
+#define MALI_PP7_DOMAIN_INDEX 8
+#define MALI_L20_DOMAIN_INDEX 9
+#define MALI_L21_DOMAIN_INDEX 10
+#define MALI_L22_DOMAIN_INDEX 11
+
+#define MALI_MAX_NUMBER_OF_DOMAINS 12
/* Record the domain config from the customer or default config */
extern u16 mali_pmu_global_domain_config[];
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/* Number of frame registers on Mali-300 and later */
#define MALI_PP_MALI400_NUM_FRAME_REGISTERS ((0x058/4)+1)
-static struct mali_pp_core* mali_global_pp_cores[MALI_MAX_NUMBER_OF_PP_CORES] = { NULL };
+static struct mali_pp_core *mali_global_pp_cores[MALI_MAX_NUMBER_OF_PP_CORES] = { NULL };
static u32 mali_global_num_pp_cores = 0;
/* Interrupt handlers */
struct mali_pp_core *mali_pp_create(const _mali_osk_resource_t *resource, struct mali_group *group, mali_bool is_virtual, u32 bcast_id)
{
- struct mali_pp_core* core = NULL;
+ struct mali_pp_core *core = NULL;
MALI_DEBUG_PRINT(2, ("Mali PP: Creating Mali PP core: %s\n", resource->description));
MALI_DEBUG_PRINT(2, ("Mali PP: Base address of PP core: 0x%x\n", resource->base));
MALI_DEBUG_ASSERT(!is_virtual || -1 != resource->irq);
core->irq = _mali_osk_irq_init(resource->irq,
- mali_group_upper_half_pp,
- group,
- mali_pp_irq_probe_trigger,
- mali_pp_irq_probe_ack,
- core,
- resource->description);
+ mali_group_upper_half_pp,
+ group,
+ mali_pp_irq_probe_trigger,
+ mali_pp_irq_probe_ack,
+ core,
+ resource->description);
if (NULL != core->irq) {
mali_global_pp_cores[mali_global_num_pp_cores] = core;
mali_global_num_pp_cores++;
if (i == MALI_REG_POLL_COUNT_FAST) {
MALI_PRINT_ERROR(("Mali PP: Failed to reset core %s, rawstat: 0x%08x\n",
- core->hw_core.description, rawstat));
+ core->hw_core.description, rawstat));
return _MALI_OSK_ERR_FAULT;
}
}
void mali_pp_job_dma_cmd_prepare(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job,
- mali_bool restart_virtual, mali_dma_cmd_buf *buf)
+ mali_dma_cmd_buf *buf)
{
u32 relative_address;
u32 start_index;
MALI_DEBUG_ASSERT_POINTER(core);
- /* Write frame registers */
-
- /*
- * There are two frame registers which are different for each sub job:
- * 1. The Renderer List Address Register (MALI200_REG_ADDR_FRAME)
- * 2. The FS Stack Address Register (MALI200_REG_ADDR_STACK)
- */
- mali_dma_write_conditional(buf, &core->hw_core, MALI200_REG_ADDR_FRAME, mali_pp_job_get_addr_frame(job, sub_job), mali_frame_registers_reset_values[MALI200_REG_ADDR_FRAME / sizeof(u32)]);
-
- /* For virtual jobs, the stack address shouldn't be broadcast but written individually */
- if (!mali_pp_job_is_virtual(job) || restart_virtual) {
- mali_dma_write_conditional(buf, &core->hw_core, MALI200_REG_ADDR_STACK, mali_pp_job_get_addr_stack(job, sub_job), mali_frame_registers_reset_values[MALI200_REG_ADDR_STACK / sizeof(u32)]);
- }
-
/* Write registers between MALI200_REG_ADDR_FRAME and MALI200_REG_ADDR_STACK */
relative_address = MALI200_REG_ADDR_RSW;
start_index = MALI200_REG_ADDR_RSW / sizeof(u32);
nr_of_regs = (MALI200_REG_ADDR_STACK - MALI200_REG_ADDR_RSW) / sizeof(u32);
mali_dma_write_array_conditional(buf, &core->hw_core,
- relative_address, &frame_registers[start_index],
- nr_of_regs, &mali_frame_registers_reset_values[start_index]);
+ relative_address, &frame_registers[start_index],
+ nr_of_regs, &mali_frame_registers_reset_values[start_index]);
/* MALI200_REG_ADDR_STACK_SIZE */
relative_address = MALI200_REG_ADDR_STACK_SIZE;
start_index = MALI200_REG_ADDR_STACK_SIZE / sizeof(u32);
mali_dma_write_conditional(buf, &core->hw_core,
- relative_address, frame_registers[start_index],
- mali_frame_registers_reset_values[start_index]);
+ relative_address, frame_registers[start_index],
+ mali_frame_registers_reset_values[start_index]);
/* Skip 2 reserved registers */
nr_of_regs = MALI_PP_MALI400_NUM_FRAME_REGISTERS - MALI200_REG_ADDR_ORIGIN_OFFSET_X / sizeof(u32);
mali_dma_write_array_conditional(buf, &core->hw_core,
- relative_address, &frame_registers[start_index],
- nr_of_regs, &mali_frame_registers_reset_values[start_index]);
+ relative_address, &frame_registers[start_index],
+ nr_of_regs, &mali_frame_registers_reset_values[start_index]);
/* Write WBx registers */
if (wb0_registers[0]) { /* M200_WB0_REG_SOURCE_SELECT register */
mali_dma_write_conditional(buf, &core->hw_core, MALI200_REG_ADDR_MGMT_PERF_CNT_1_ENABLE, MALI200_REG_VAL_PERF_CNT_ENABLE, mali_perf_cnt_enable_reset_value);
}
- /* This is the command that starts the core. */
+ /* This is the command that starts the core.
+ *
+ * Don't actually run the job if PROFILING_SKIP_PP_JOBS are set, just
+ * force core to assert the completion interrupt.
+ */
+#if !defined(PROFILING_SKIP_PP_JOBS)
mali_dma_write(buf, &core->hw_core, MALI200_REG_ADDR_MGMT_CTRL_MGMT, MALI200_REG_VAL_CTRL_MGMT_START_RENDERING);
+#else
+ mali_dma_write(buf, &core->hw_core, MALI200_REG_ADDR_MGMT_INT_RAWSTAT, MALI200_REG_VAL_IRQ_END_OF_FRAME);
+#endif
}
-void mali_pp_job_start(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job, mali_bool restart_virtual)
+void mali_pp_job_start(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job)
{
u32 relative_address;
u32 start_index;
MALI_DEBUG_ASSERT_POINTER(core);
- /* Write frame registers */
-
- /*
- * There are two frame registers which are different for each sub job:
- * 1. The Renderer List Address Register (MALI200_REG_ADDR_FRAME)
- * 2. The FS Stack Address Register (MALI200_REG_ADDR_STACK)
- */
- mali_hw_core_register_write_relaxed_conditional(&core->hw_core, MALI200_REG_ADDR_FRAME, mali_pp_job_get_addr_frame(job, sub_job), mali_frame_registers_reset_values[MALI200_REG_ADDR_FRAME / sizeof(u32)]);
-
- /* For virtual jobs, the stack address shouldn't be broadcast but written individually */
- if (!mali_pp_job_is_virtual(job) || restart_virtual) {
- mali_hw_core_register_write_relaxed_conditional(&core->hw_core, MALI200_REG_ADDR_STACK, mali_pp_job_get_addr_stack(job, sub_job), mali_frame_registers_reset_values[MALI200_REG_ADDR_STACK / sizeof(u32)]);
- }
-
/* Write registers between MALI200_REG_ADDR_FRAME and MALI200_REG_ADDR_STACK */
relative_address = MALI200_REG_ADDR_RSW;
start_index = MALI200_REG_ADDR_RSW / sizeof(u32);
nr_of_regs = (MALI200_REG_ADDR_STACK - MALI200_REG_ADDR_RSW) / sizeof(u32);
mali_hw_core_register_write_array_relaxed_conditional(&core->hw_core,
- relative_address, &frame_registers[start_index],
- nr_of_regs, &mali_frame_registers_reset_values[start_index]);
+ relative_address, &frame_registers[start_index],
+ nr_of_regs, &mali_frame_registers_reset_values[start_index]);
/* MALI200_REG_ADDR_STACK_SIZE */
relative_address = MALI200_REG_ADDR_STACK_SIZE;
start_index = MALI200_REG_ADDR_STACK_SIZE / sizeof(u32);
mali_hw_core_register_write_relaxed_conditional(&core->hw_core,
- relative_address, frame_registers[start_index],
- mali_frame_registers_reset_values[start_index]);
+ relative_address, frame_registers[start_index],
+ mali_frame_registers_reset_values[start_index]);
/* Skip 2 reserved registers */
nr_of_regs = MALI_PP_MALI400_NUM_FRAME_REGISTERS - MALI200_REG_ADDR_ORIGIN_OFFSET_X / sizeof(u32);
mali_hw_core_register_write_array_relaxed_conditional(&core->hw_core,
- relative_address, &frame_registers[start_index],
- nr_of_regs, &mali_frame_registers_reset_values[start_index]);
+ relative_address, &frame_registers[start_index],
+ nr_of_regs, &mali_frame_registers_reset_values[start_index]);
/* Write WBx registers */
if (wb0_registers[0]) { /* M200_WB0_REG_SOURCE_SELECT register */
}
#ifdef CONFIG_MALI400_HEATMAPS_ENABLED
- if(job->uargs.perf_counter_flag & _MALI_PERFORMANCE_COUNTER_FLAG_HEATMAP_ENABLE) {
+ if (job->uargs.perf_counter_flag & _MALI_PERFORMANCE_COUNTER_FLAG_HEATMAP_ENABLE) {
mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_MGMT_PERFMON_CONTR, ((job->uargs.tilesx & 0x3FF) << 16) | 1);
mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_MGMT_PERFMON_BASE, job->uargs.heatmap_mem & 0xFFFFFFF8);
}
/* Adding barrier to make sure all rester writes are finished */
_mali_osk_write_mem_barrier();
- /* This is the command that starts the core. */
+ /* This is the command that starts the core.
+ *
+ * Don't actually run the job if PROFILING_SKIP_PP_JOBS are set, just
+ * force core to assert the completion interrupt.
+ */
+#if !defined(PROFILING_SKIP_PP_JOBS)
mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_MGMT_CTRL_MGMT, MALI200_REG_VAL_CTRL_MGMT_START_RENDERING);
+#else
+ mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_MGMT_INT_RAWSTAT, MALI200_REG_VAL_IRQ_END_OF_FRAME);
+#endif
/* Adding barrier to make sure previous rester writes is finished */
_mali_osk_write_mem_barrier();
return mali_hw_core_register_read(&core->hw_core, MALI200_REG_ADDR_MGMT_VERSION);
}
-struct mali_pp_core* mali_pp_get_global_pp_core(u32 index)
+struct mali_pp_core *mali_pp_get_global_pp_core(u32 index)
{
if (mali_global_num_pp_cores > index) {
return mali_global_pp_cores[index];
#if 0
void mali_pp_print_state(struct mali_pp_core *core)
{
- MALI_DEBUG_PRINT(2, ("Mali PP: State: 0x%08x\n", mali_hw_core_register_read(&core->hw_core, MALI200_REG_ADDR_MGMT_STATUS) ));
+ MALI_DEBUG_PRINT(2, ("Mali PP: State: 0x%08x\n", mali_hw_core_register_read(&core->hw_core, MALI200_REG_ADDR_MGMT_STATUS)));
}
#endif
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_errcode_t mali_pp_initialize(void);
void mali_pp_terminate(void);
-struct mali_pp_core *mali_pp_create(const _mali_osk_resource_t * resource, struct mali_group *group, mali_bool is_virtual, u32 bcast_id);
+struct mali_pp_core *mali_pp_create(const _mali_osk_resource_t *resource, struct mali_group *group, mali_bool is_virtual, u32 bcast_id);
void mali_pp_delete(struct mali_pp_core *core);
void mali_pp_stop_bus(struct mali_pp_core *core);
_mali_osk_errcode_t mali_pp_reset(struct mali_pp_core *core);
_mali_osk_errcode_t mali_pp_hard_reset(struct mali_pp_core *core);
-void mali_pp_job_start(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job, mali_bool restart_virtual);
+void mali_pp_job_start(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job);
/**
* @brief Add commands to DMA command buffer to start PP job on core.
*/
void mali_pp_job_dma_cmd_prepare(struct mali_pp_core *core, struct mali_pp_job *job, u32 sub_job,
- mali_bool restart_virtual, mali_dma_cmd_buf *buf);
+ mali_dma_cmd_buf *buf);
u32 mali_pp_core_get_version(struct mali_pp_core *core);
return core->bcast_id;
}
-struct mali_pp_core* mali_pp_get_global_pp_core(u32 index);
+struct mali_pp_core *mali_pp_get_global_pp_core(u32 index);
u32 mali_pp_get_glob_num_pp_cores(void);
/* Debug */
mali_hw_core_register_write(&core->hw_core, MALI200_REG_ADDR_MGMT_INT_MASK, MALI200_REG_VAL_IRQ_MASK_USED);
}
-MALI_STATIC_INLINE void mali_pp_write_addr_stack(struct mali_pp_core *core, struct mali_pp_job *job)
+MALI_STATIC_INLINE void mali_pp_write_addr_renderer_list(struct mali_pp_core *core,
+ struct mali_pp_job *job, u32 subjob)
{
- u32 addr = mali_pp_job_get_addr_stack(job, core->core_id);
+ u32 addr = mali_pp_job_get_addr_frame(job, subjob);
+ mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_FRAME, addr);
+}
+
+
+MALI_STATIC_INLINE void mali_pp_write_addr_stack(struct mali_pp_core *core, struct mali_pp_job *job, u32 subjob)
+{
+ u32 addr = mali_pp_job_get_addr_stack(job, subjob);
mali_hw_core_register_write_relaxed(&core->hw_core, MALI200_REG_ADDR_STACK, addr);
}
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_atomic_term(&pp_counter_per_sub_job_count);
}
-struct mali_pp_job *mali_pp_job_create(struct mali_session_data *session, _mali_uk_pp_start_job_s *uargs, u32 id)
+struct mali_pp_job *mali_pp_job_create(struct mali_session_data *session,
+ _mali_uk_pp_start_job_s __user *uargs, u32 id)
{
struct mali_pp_job *job;
u32 perf_counter_flag;
job->num_memory_cookies = job->uargs.num_memory_cookies;
if (job->num_memory_cookies > 0) {
u32 size;
+ u32 __user *memory_cookies = (u32 __user *)(uintptr_t)job->uargs.memory_cookies;
if (job->uargs.num_memory_cookies > session->descriptor_mapping->current_nr_mappings) {
MALI_PRINT_ERROR(("Mali PP job: Too many memory cookies specified in job object\n"));
goto fail;
}
- size = sizeof(*job->uargs.memory_cookies) * job->num_memory_cookies;
+ size = sizeof(*memory_cookies) * job->num_memory_cookies;
job->memory_cookies = _mali_osk_malloc(size);
if (NULL == job->memory_cookies) {
goto fail;
}
- if (0 != _mali_osk_copy_from_user(job->memory_cookies, job->uargs.memory_cookies, size)) {
+ if (0 != _mali_osk_copy_from_user(job->memory_cookies, memory_cookies, size)) {
MALI_PRINT_ERROR(("Mali PP job: Failed to copy %d bytes of memory cookies from user!\n", size));
goto fail;
}
}
/* Prepare DMA command buffer to start job, if it is virtual. */
- if (mali_pp_job_is_virtual(job)) {
+ if (mali_pp_job_is_virtual_group_job(job)) {
struct mali_pp_core *core;
_mali_osk_errcode_t err = mali_dma_get_cmd_buf(&job->dma_cmd_buf);
core = mali_pp_scheduler_get_virtual_pp();
MALI_DEBUG_ASSERT_POINTER(core);
- mali_pp_job_dma_cmd_prepare(core, job, 0, MALI_FALSE, &job->dma_cmd_buf);
+ mali_pp_job_dma_cmd_prepare(core, job, 0, &job->dma_cmd_buf);
}
if (_MALI_OSK_ERR_OK != mali_pp_job_check(job)) {
u32 mali_pp_job_get_perf_counter_src0(struct mali_pp_job *job, u32 sub_job)
{
/* Virtual jobs always use the global job counter (or if there are per sub job counters at all) */
- if (mali_pp_job_is_virtual(job) || 0 == job->perf_counter_per_sub_job_count) {
+ if (mali_pp_job_is_virtual_group_job(job) || 0 == job->perf_counter_per_sub_job_count) {
return job->uargs.perf_counter_src0;
}
u32 mali_pp_job_get_perf_counter_src1(struct mali_pp_job *job, u32 sub_job)
{
/* Virtual jobs always use the global job counter (or if there are per sub job counters at all) */
- if (mali_pp_job_is_virtual(job) || 0 == job->perf_counter_per_sub_job_count) {
+ if (mali_pp_job_is_virtual_group_job(job) || 0 == job->perf_counter_per_sub_job_count) {
/* Virtual jobs always use the global job counter */
return job->uargs.perf_counter_src1;
}
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_kernel_common.h"
#include "regs/mali_200_regs.h"
#include "mali_kernel_core.h"
-#include <linux/version.h>
-#ifdef CONFIG_SYNC
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,10)
-#include <sync.h>
-#else
-#include <linux/sync.h>
-#endif
-#endif
#include "mali_dma.h"
#include "mali_dlbu.h"
#include "mali_timeline.h"
return (NULL == job) ? 0 : job->cache_order;
}
-MALI_STATIC_INLINE u32 mali_pp_job_get_user_id(struct mali_pp_job *job)
+MALI_STATIC_INLINE u64 mali_pp_job_get_user_id(struct mali_pp_job *job)
{
return job->uargs.user_job_ptr;
}
return job->tid;
}
-MALI_STATIC_INLINE u32* mali_pp_job_get_frame_registers(struct mali_pp_job *job)
+MALI_STATIC_INLINE u32 *mali_pp_job_get_frame_registers(struct mali_pp_job *job)
{
return job->uargs.frame_registers;
}
-MALI_STATIC_INLINE u32* mali_pp_job_get_dlbu_registers(struct mali_pp_job *job)
+MALI_STATIC_INLINE u32 *mali_pp_job_get_dlbu_registers(struct mali_pp_job *job)
{
return job->uargs.dlbu_registers;
}
-MALI_STATIC_INLINE mali_bool mali_pp_job_is_virtual(struct mali_pp_job *job)
+MALI_STATIC_INLINE mali_bool mali_pp_job_is_virtual_group_job(struct mali_pp_job *job)
+{
+ if (mali_is_mali450()) {
+ return 1 != job->uargs.num_cores;
+ }
+
+ return MALI_FALSE;
+}
+
+MALI_STATIC_INLINE mali_bool mali_pp_job_is_with_dlbu(struct mali_pp_job *job)
{
#if defined(CONFIG_MALI450)
return 0 == job->uargs.num_cores;
MALI_STATIC_INLINE u32 mali_pp_job_get_addr_frame(struct mali_pp_job *job, u32 sub_job)
{
- if (mali_pp_job_is_virtual(job)) {
+ if (mali_pp_job_is_with_dlbu(job)) {
return MALI_DLBU_VIRT_ADDR;
} else if (0 == sub_job) {
return job->uargs.frame_registers[MALI200_REG_ADDR_FRAME / sizeof(u32)];
return 0;
}
-MALI_STATIC_INLINE u32* mali_pp_job_get_wb0_registers(struct mali_pp_job *job)
+MALI_STATIC_INLINE u32 *mali_pp_job_get_wb0_registers(struct mali_pp_job *job)
{
return job->uargs.wb0_registers;
}
-MALI_STATIC_INLINE u32* mali_pp_job_get_wb1_registers(struct mali_pp_job *job)
+MALI_STATIC_INLINE u32 *mali_pp_job_get_wb1_registers(struct mali_pp_job *job)
{
return job->uargs.wb1_registers;
}
-MALI_STATIC_INLINE u32* mali_pp_job_get_wb2_registers(struct mali_pp_job *job)
+MALI_STATIC_INLINE u32 *mali_pp_job_get_wb2_registers(struct mali_pp_job *job)
{
return job->uargs.wb2_registers;
}
{
MALI_DEBUG_ASSERT_POINTER(job);
- if ( job->uargs.wb0_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT] ||
- job->uargs.wb1_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT] ||
- job->uargs.wb2_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT]
+ if (job->uargs.wb0_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT] ||
+ job->uargs.wb1_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT] ||
+ job->uargs.wb2_registers[MALI200_REG_ADDR_WB_SOURCE_SELECT]
) {
/* At least one output unit active */
return MALI_FALSE;
MALI_STATIC_INLINE void mali_pp_job_mark_sub_job_completed(struct mali_pp_job *job, mali_bool success)
{
job->sub_jobs_completed++;
- if ( MALI_FALSE == success ) {
+ if (MALI_FALSE == success) {
job->sub_job_errors++;
}
}
MALI_STATIC_INLINE mali_bool mali_pp_job_was_success(struct mali_pp_job *job)
{
- if ( 0 == job->sub_job_errors ) {
+ if (0 == job->sub_job_errors) {
return MALI_TRUE;
}
return MALI_FALSE;
MALI_STATIC_INLINE _mali_osk_errcode_t mali_pp_job_check(struct mali_pp_job *job)
{
- if (mali_pp_job_is_virtual(job) && job->sub_jobs_num != 1) {
+ if (mali_pp_job_is_with_dlbu(job) && job->sub_jobs_num != 1) {
return _MALI_OSK_ERR_FAULT;
}
return _MALI_OSK_ERR_OK;
MALI_STATIC_INLINE mali_bool mali_pp_job_is_large_and_unstarted(struct mali_pp_job *job)
{
MALI_DEBUG_ASSERT_POINTER(job);
- MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual(job));
+ MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual_group_job(job));
return (0 == job->sub_jobs_started && 2 < job->sub_jobs_num);
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#endif /* !defined(CONFIG_DMA_SHARED_BUFFER) && !defined(CONFIG_MALI_DMA_BUF_MAP_ON_ATTACH) */
static void mali_pp_scheduler_job_queued(void);
-static void mali_pp_scheduler_job_completed(void);
+static void mali_pp_scheduler_job_completed(mali_bool job_started);
/* Maximum of 8 PP cores (a group can only have maximum of 1 PP core) */
#define MALI_MAX_NUMBER_OF_PP_GROUPS 9
static _MALI_OSK_LIST_HEAD_STATIC_INIT(group_list_disabled); /* List of disabled physical groups */
/* Virtual job queue (Mali-450 only) */
-static struct mali_pp_scheduler_job_queue virtual_job_queue;
+static struct mali_pp_scheduler_job_queue virtual_group_job_queue;
/**
* Add job to scheduler queue.
_MALI_OSK_INIT_LIST_HEAD(&job_queue.high_pri);
job_queue.depth = 0;
- _MALI_OSK_INIT_LIST_HEAD(&virtual_job_queue.normal_pri);
- _MALI_OSK_INIT_LIST_HEAD(&virtual_job_queue.high_pri);
- virtual_job_queue.depth = 0;
+ _MALI_OSK_INIT_LIST_HEAD(&virtual_group_job_queue.normal_pri);
+ _MALI_OSK_INIT_LIST_HEAD(&virtual_group_job_queue.high_pri);
+ virtual_group_job_queue.depth = 0;
#if defined(MALI_UPPER_HALF_SCHEDULING)
pp_scheduler_lock = _mali_osk_spinlock_irq_init(_MALI_OSK_LOCKFLAG_ORDERED, _MALI_OSK_LOCK_ORDER_SCHEDULER);
/**
* Returns a virtual job if a virtual job is ready to run
*/
-MALI_STATIC_INLINE struct mali_pp_job *mali_pp_scheduler_get_virtual_job(void)
+MALI_STATIC_INLINE struct mali_pp_job *mali_pp_scheduler_get_virtual_group_job(void)
{
MALI_ASSERT_PP_SCHEDULER_LOCKED();
MALI_DEBUG_ASSERT_POINTER(virtual_group);
- return mali_pp_scheduler_get_job(&virtual_job_queue);
+ return mali_pp_scheduler_get_job(&virtual_group_job_queue);
}
-MALI_STATIC_INLINE void mali_pp_scheduler_dequeue_virtual_job(struct mali_pp_job *job)
+static void mali_pp_scheduler_dequeue_virtual_group_job(struct mali_pp_job *job)
{
MALI_ASSERT_PP_SCHEDULER_LOCKED();
- MALI_DEBUG_ASSERT(virtual_job_queue.depth > 0);
+ MALI_DEBUG_ASSERT(virtual_group_job_queue.depth > 0);
/* Remove job from queue */
- _mali_osk_list_delinit(&job->list);
- _mali_osk_list_delinit(&job->session_fb_lookup_list);
- --virtual_job_queue.depth;
+ if (!mali_pp_job_has_unstarted_sub_jobs(job)) {
+ _mali_osk_list_delinit(&job->list);
+ _mali_osk_list_delinit(&job->session_fb_lookup_list);
+ --virtual_group_job_queue.depth;
+ }
+}
+
+MALI_STATIC_INLINE void mali_pp_scheduler_pick_virtual_group_job(struct mali_pp_job *job,
+ u32 *first_subjob, u32 *last_subjob)
+{
+ MALI_ASSERT_GROUP_LOCKED(virtual_group);
+ MALI_ASSERT_PP_SCHEDULER_LOCKED();
+
+ MALI_DEBUG_ASSERT(VIRTUAL_GROUP_IDLE == virtual_group_state);
+ MALI_DEBUG_ASSERT_POINTER(job);
+ MALI_DEBUG_ASSERT(mali_pp_job_is_virtual_group_job(job));
+
+ MALI_DEBUG_ASSERT_POINTER(first_subjob);
+ MALI_DEBUG_ASSERT_POINTER(last_subjob);
+
+ MALI_DEBUG_ASSERT(virtual_group_job_queue.depth > 0);
+
+ MALI_DEBUG_ASSERT(mali_pp_job_has_unstarted_sub_jobs(job));
+
+ *first_subjob = *last_subjob =
+ mali_pp_job_get_first_unstarted_sub_job(job);
+
+ if (mali_pp_job_is_with_dlbu(job)) {
+ MALI_DEBUG_ASSERT(1 == mali_pp_job_get_sub_job_count(job));
+ mali_pp_job_mark_sub_job_started(job, 0);
+ } else {
+ struct mali_group *child, *temp;
+ _MALI_OSK_LIST_FOREACHENTRY(child, temp,
+ &virtual_group->group_list, struct mali_group, group_list) {
+ if (mali_pp_job_has_unstarted_sub_jobs(job)) {
+ *last_subjob = mali_pp_job_get_first_unstarted_sub_job(job);
+ mali_pp_job_mark_sub_job_started(job, *last_subjob);
+ } else {
+ break;
+ }
+ }
+ }
+
+ /* Virtual group is now working. */
+ virtual_group_state = VIRTUAL_GROUP_WORKING;
+
+ mali_pp_scheduler_dequeue_virtual_group_job(job);
}
+
/**
* Checks if the criteria is met for removing a physical core from virtual group
*/
jobres->status = _MALI_UK_JOB_STATUS_END_UNKNOWN_ERR;
}
- if (mali_pp_job_is_virtual(job)) {
+ if (mali_pp_job_is_with_dlbu(job)) {
num_counters_to_copy = num_cores; /* Number of physical cores available */
} else {
num_counters_to_copy = mali_pp_job_get_sub_job_count(job);
#endif
}
-static void mali_pp_scheduler_finalize_job(struct mali_pp_job * job)
+static void mali_pp_scheduler_finalize_job(struct mali_pp_job *job, mali_bool job_started)
{
/* This job object should not be on any lists. */
MALI_DEBUG_ASSERT(_mali_osk_list_empty(&job->list));
}
#endif
- mali_pp_scheduler_job_completed();
+ mali_pp_scheduler_job_completed(job_started);
}
void mali_pp_scheduler_schedule(void)
{
- struct mali_group* physical_groups_to_start[MALI_MAX_NUMBER_OF_PP_GROUPS - 1];
- struct mali_pp_job* physical_jobs_to_start[MALI_MAX_NUMBER_OF_PP_GROUPS - 1];
+ struct mali_group *physical_groups_to_start[MALI_MAX_NUMBER_OF_PP_GROUPS - 1];
+ struct mali_pp_job *physical_jobs_to_start[MALI_MAX_NUMBER_OF_PP_GROUPS - 1];
u32 physical_sub_jobs_to_start[MALI_MAX_NUMBER_OF_PP_GROUPS - 1];
int num_physical_jobs_to_start = 0;
int i;
break;
}
- MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual(job));
+ MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual_group_job(job));
MALI_DEBUG_ASSERT(mali_pp_job_has_unstarted_sub_jobs(job));
MALI_DEBUG_ASSERT(1 <= mali_pp_job_get_sub_job_count(job));
struct mali_pp_job *job;
/* Find a virtual job we can start. */
- job = mali_pp_scheduler_get_virtual_job();
+ job = mali_pp_scheduler_get_virtual_group_job();
if (NULL != job) {
- MALI_DEBUG_ASSERT(mali_pp_job_is_virtual(job));
- MALI_DEBUG_ASSERT(mali_pp_job_has_unstarted_sub_jobs(job));
- MALI_DEBUG_ASSERT(1 == mali_pp_job_get_sub_job_count(job));
+ u32 first_subjob, last_subjob;
- /* Mark the one and only sub job as started. */
- mali_pp_job_mark_sub_job_started(job, 0);
-
- /* Remove job from queue. */
- mali_pp_scheduler_dequeue_virtual_job(job);
-
- /* Virtual group is now working. */
- virtual_group_state = VIRTUAL_GROUP_WORKING;
+ /* To mark necessary subjobs status of this job and remove the job from job queue
+ * when all the subjobs will be run by this virtual group in one go
+ */
+ mali_pp_scheduler_pick_virtual_group_job(job, &first_subjob, &last_subjob);
/* We no longer need the scheduler lock, but we still need the virtual lock
- * in order to start the virtual job. */
+ * in order to start the virtual job.
+ */
mali_pp_scheduler_unlock();
/* Start job. */
- mali_group_start_pp_job(virtual_group, job, 0);
-
- MALI_DEBUG_PRINT(4, ("Mali PP scheduler: Virtual job %u (0x%08X) part %u/%u started (from schedule).\n",
- mali_pp_job_get_id(job), job, 1,
- mali_pp_job_get_sub_job_count(job)));
-
- mali_group_unlock(virtual_group);
+ mali_group_start_job_on_virtual(virtual_group, job, first_subjob, last_subjob);
} else {
/* No virtual job to start. */
mali_pp_scheduler_unlock();
- mali_group_unlock(virtual_group);
}
} else {
/* We have a virtual group, but it is busy or disabled. */
MALI_DEBUG_ASSERT(VIRTUAL_GROUP_IDLE != virtual_group_state);
mali_pp_scheduler_unlock();
- mali_group_unlock(virtual_group);
}
+ mali_group_unlock(virtual_group);
} else {
/* There is no virtual group. */
mali_pp_scheduler_unlock();
MALI_DEBUG_ASSERT_POINTER(group);
MALI_DEBUG_ASSERT_POINTER(job);
MALI_DEBUG_ASSERT(!mali_group_is_virtual(group));
- MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual(job));
+ MALI_DEBUG_ASSERT(!mali_pp_job_is_virtual_group_job(job));
mali_group_lock(group);
/* Set state to IDLE if group was acquired from the virtual group. */
group->state = MALI_GROUP_STATE_IDLE;
- mali_group_start_pp_job(group, job, sub_job);
+ mali_group_start_job_on_group(group, job, sub_job);
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: Physical job %u (0x%08X) part %u/%u started (from schedule).\n",
- mali_pp_job_get_id(job), job, sub_job + 1,
- mali_pp_job_get_sub_job_count(job)));
+ mali_pp_job_get_id(job), job, sub_job + 1,
+ mali_pp_job_get_sub_job_count(job)));
mali_group_unlock(group);
}
}
/* Get next virtual job. */
- virtual_job = mali_pp_scheduler_get_virtual_job();
+ virtual_job = mali_pp_scheduler_get_virtual_group_job();
if (NULL != virtual_job && VIRTUAL_GROUP_IDLE == virtual_group_state) {
- /* There is a runnable virtual job. */
-
- MALI_DEBUG_ASSERT(mali_pp_job_is_virtual(virtual_job));
- MALI_DEBUG_ASSERT(mali_pp_job_has_unstarted_sub_jobs(virtual_job));
- MALI_DEBUG_ASSERT(1 == mali_pp_job_get_sub_job_count(virtual_job));
-
- mali_pp_job_mark_sub_job_started(virtual_job, 0);
-
- /* Remove job from queue. */
- mali_pp_scheduler_dequeue_virtual_job(virtual_job);
-
- /* Virtual group is now working. */
- virtual_group_state = VIRTUAL_GROUP_WORKING;
-
+ u32 first_subjob, last_subjob;
+ /* To mark necessary subjobs status of this job and remove the job from job queue
+ * when all the subjobs will be run by this virtual group in one go
+ */
+ mali_pp_scheduler_pick_virtual_group_job(virtual_job, &first_subjob, &last_subjob);
+
+ /* We no longer need the scheduler lock, but we still need the virtual lock
+ * in order to start the virtual job.
+ */
mali_pp_scheduler_unlock();
/* Start job. */
- mali_group_start_pp_job(group, virtual_job, 0);
+ mali_group_start_job_on_virtual(group, virtual_job, first_subjob, last_subjob);
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: Virtual job %u (0x%08X) part %u/%u started (from job_done).\n",
- mali_pp_job_get_id(virtual_job), virtual_job, 1,
- mali_pp_job_get_sub_job_count(virtual_job)));
+ mali_pp_job_get_id(virtual_job), virtual_job, 1,
+ mali_pp_job_get_sub_job_count(virtual_job)));
} else {
#if defined(CONFIG_GPU_TRACEPOINTS) && defined(CONFIG_TRACEPOINTS)
trace_gpu_sched_switch("Mali_Virtual_PP", sched_clock(), 0, 0, 0);
physical_group->state = MALI_GROUP_STATE_IDLE;
/* Start job. */
- mali_group_start_pp_job(physical_group, physical_job, physical_sub_job);
+ mali_group_start_job_on_group(physical_group, physical_job, physical_sub_job);
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: Physical job %u (0x%08X) part %u/%u started (from job_done).\n",
- mali_pp_job_get_id(physical_job), physical_job, physical_sub_job + 1,
- mali_pp_job_get_sub_job_count(physical_job)));
+ mali_pp_job_get_id(physical_job), physical_job, physical_sub_job + 1,
+ mali_pp_job_get_sub_job_count(physical_job)));
mali_group_unlock(physical_group);
}
mali_pp_scheduler_unlock();
/* Group is already on the working list, so start the new job. */
- mali_group_start_pp_job(group, job, sub_job);
+ mali_group_start_job_on_group(group, job, sub_job);
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: Physical job %u (0x%08X) part %u/%u started (from job_done).\n",
- mali_pp_job_get_id(job), job, sub_job + 1, mali_pp_job_get_sub_job_count(job)));
+ mali_pp_job_get_id(job), job, sub_job + 1, mali_pp_job_get_sub_job_count(job)));
mali_group_unlock(group);
} else {
mali_scheduler_mask schedule_mask = MALI_SCHEDULER_MASK_EMPTY;
MALI_DEBUG_PRINT(3, ("Mali PP scheduler: %s job %u (0x%08X) part %u/%u completed (%s).\n",
- mali_pp_job_is_virtual(job) ? "Virtual" : "Physical",
- mali_pp_job_get_id(job),
- job, sub_job + 1,
- mali_pp_job_get_sub_job_count(job),
- success ? "success" : "failure"));
+ mali_pp_job_is_virtual_group_job(job) ? "Virtual Group" : "Physical",
+ mali_pp_job_get_id(job),
+ job, sub_job + 1,
+ mali_pp_job_get_sub_job_count(job),
+ success ? "success" : "failure"));
MALI_ASSERT_GROUP_LOCKED(group);
mali_pp_scheduler_lock();
- mali_pp_job_mark_sub_job_completed(job, success);
+ if (mali_group_is_virtual(group) && !mali_pp_job_is_with_dlbu(job)) {
+ u32 subjobs;
- MALI_DEBUG_ASSERT(mali_pp_job_is_virtual(job) == mali_group_is_virtual(group));
+ /* Get how many subjobs are running parallel in this virtual group */
+ subjobs = mali_pp_job_get_first_unstarted_sub_job(job) - group->pp_running_sub_job;
+ MALI_DEBUG_ASSERT(subjobs > 0);
+
+ for (; 0 < subjobs; subjobs--) {
+ mali_pp_job_mark_sub_job_completed(job, success);
+ }
+
+ mali_group_non_dlbu_job_done_virtual(group);
+ } else {
+ mali_pp_job_mark_sub_job_completed(job, success);
+ }
+
+ MALI_DEBUG_ASSERT(mali_pp_job_is_virtual_group_job(job) == mali_group_is_virtual(group));
job_is_done = mali_pp_job_is_complete(job);
if (job_is_done) {
- /* Job is removed from these lists when the last sub job is scheduled. */
+ /* Some groups added into the virtual group may take some subjobs to run but
+ * without dequeuing the job, here do necessary dequeue under scheduler lock
+ */
+ if (mali_group_is_virtual(group) && !mali_pp_job_is_with_dlbu(job)) {
+ if (!_mali_osk_list_empty(&job->list)) {
+ mali_pp_scheduler_dequeue_virtual_group_job(job);
+ }
+ }
+
MALI_DEBUG_ASSERT(_mali_osk_list_empty(&job->list));
MALI_DEBUG_ASSERT(_mali_osk_list_empty(&job->session_fb_lookup_list));
_mali_osk_list_delinit(&job->session_list);
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: All parts completed for %s job %u (0x%08X).\n",
- mali_pp_job_is_virtual(job) ? "virtual" : "physical",
- mali_pp_job_get_id(job), job));
+ mali_pp_job_is_virtual_group_job(job) ? "virtual group" : "physical",
+ mali_pp_job_get_id(job), job));
mali_pp_scheduler_unlock();
if (job_is_done) {
/* Return job to user and delete it. */
- mali_pp_scheduler_finalize_job(job);
+ mali_pp_scheduler_finalize_job(job, MALI_TRUE);
}
/* A GP job might be queued by tracker release above,
- * make sure GP scheduler gets a chance to schedule this (if possible)
+ * make sure GP scheduler has a chance to schedule this (if possible)
*/
mali_scheduler_schedule_from_mask(schedule_mask & ~MALI_SCHEDULER_MASK_PP, in_upper_half);
schedule_mask &= ~MALI_SCHEDULER_MASK_PP;
schedule_on_group = MALI_TRUE;
}
+ } else if ((0 < virtual_group_job_queue.depth) && (!mali_scheduler_mask_is_set(schedule_mask, MALI_SCHEDULER_MASK_PP))) {
+ /* This case is rare, only in virtual job has sub jobs case,
+ * the last "pilot job" here might not be the real pilot job,
+ * it may be a real pp job with only 1 subjob i.e. only 1 region inform,
+ * so this job may not trigger any virtual job queued in virtual queue,
+ * so it may suspend the pp scheduler, even when there are already
+ * some jobs in the virtual queue, so in this case we need to explicit
+ * set the schedule_mask */
+ schedule_mask |= MALI_SCHEDULER_MASK_PP;
}
if (schedule_on_group) {
if (job_is_done) {
/* Return job to user and delete it. */
- mali_pp_scheduler_finalize_job(job);
+ mali_pp_scheduler_finalize_job(job, MALI_TRUE);
}
}
}
}
-mali_timeline_point mali_pp_scheduler_submit_job(struct mali_session_data *session, struct mali_pp_job *job)
+static mali_timeline_point mali_pp_scheduler_submit_job(struct mali_session_data *session, struct mali_pp_job *job)
{
mali_timeline_point point;
u32 fb_lookup_id = 0;
mali_pp_scheduler_unlock();
- mali_pp_scheduler_job_queued();
+ /* We hold a PM reference for every job we hold queued (and running) */
+ _mali_osk_pm_dev_ref_add();
/* Add job to Timeline system. */
point = mali_timeline_system_add_tracker(session->timeline_system, &job->tracker, MALI_TIMELINE_PP);
MALI_DEBUG_ASSERT_POINTER(uargs);
MALI_DEBUG_ASSERT_POINTER(ctx);
- session = (struct mali_session_data*)ctx;
+ session = (struct mali_session_data *)ctx;
job = mali_pp_job_create(session, uargs, mali_scheduler_get_new_id());
if (NULL == job) {
return _MALI_OSK_ERR_NOMEM;
}
- timeline_point_ptr = (u32 __user *) job->uargs.timeline_point_ptr;
+ timeline_point_ptr = (u32 __user *)(uintptr_t)job->uargs.timeline_point_ptr;
point = mali_pp_scheduler_submit_job(session, job);
job = NULL;
struct mali_gp_job *gp_job;
u32 __user *timeline_point_ptr = NULL;
mali_timeline_point point;
+ _mali_uk_pp_start_job_s __user *pp_args;
+ _mali_uk_gp_start_job_s __user *gp_args;
MALI_DEBUG_ASSERT_POINTER(ctx);
MALI_DEBUG_ASSERT_POINTER(uargs);
return _MALI_OSK_ERR_NOMEM;
}
- pp_job = mali_pp_job_create(session, kargs.pp_args, mali_scheduler_get_new_id());
+ pp_args = (_mali_uk_pp_start_job_s __user *)(uintptr_t)kargs.pp_args;
+ gp_args = (_mali_uk_gp_start_job_s __user *)(uintptr_t)kargs.gp_args;
+
+ pp_job = mali_pp_job_create(session, pp_args, mali_scheduler_get_new_id());
if (NULL == pp_job) {
MALI_PRINT_ERROR(("Failed to create PP job.\n"));
return _MALI_OSK_ERR_NOMEM;
}
- gp_job = mali_gp_job_create(session, kargs.gp_args, mali_scheduler_get_new_id(), mali_pp_job_get_tracker(pp_job));
+ gp_job = mali_gp_job_create(session, gp_args, mali_scheduler_get_new_id(), mali_pp_job_get_tracker(pp_job));
if (NULL == gp_job) {
MALI_PRINT_ERROR(("Failed to create GP job.\n"));
mali_pp_job_delete(pp_job);
return _MALI_OSK_ERR_NOMEM;
}
- timeline_point_ptr = (u32 __user *) pp_job->uargs.timeline_point_ptr;
+ timeline_point_ptr = (u32 __user *)(uintptr_t)pp_job->uargs.timeline_point_ptr;
/* Submit GP job. */
mali_gp_scheduler_submit_job(session, gp_job);
_mali_osk_errcode_t _mali_ukk_get_pp_number_of_cores(_mali_uk_get_pp_number_of_cores_s *args)
{
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_DEBUG_ASSERT_POINTER(args->ctx);
+
args->number_of_total_cores = num_cores;
args->number_of_enabled_cores = enabled_cores;
+
return _MALI_OSK_ERR_OK;
}
_mali_osk_errcode_t _mali_ukk_get_pp_core_version(_mali_uk_get_pp_core_version_s *args)
{
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_DEBUG_ASSERT_POINTER(args->ctx);
+
args->version = pp_version;
+
return _MALI_OSK_ERR_OK;
}
struct mali_pp_job *tmp;
u32 fb_lookup_id;
- MALI_DEBUG_ASSERT_POINTER(args);
- MALI_DEBUG_ASSERT_POINTER(args->ctx);
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
- session = (struct mali_session_data*)args->ctx;
+ MALI_DEBUG_ASSERT_POINTER(session);
+ MALI_DEBUG_ASSERT_POINTER(args);
fb_lookup_id = args->fb_id & MALI_PP_JOB_FB_LOOKUP_LIST_MASK;
MALI_DEBUG_CODE(u32 disable_mask = 0);
if (mali_pp_job_get_frame_builder_id(job) == (u32) args->fb_id) {
- MALI_DEBUG_CODE(disable_mask |= 0xD<<(4*3));
- if (args->wb0_memory == job->uargs.wb0_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR/sizeof(u32)]) {
- MALI_DEBUG_CODE(disable_mask |= 0x1<<(4*1));
+ MALI_DEBUG_CODE(disable_mask |= 0xD << (4 * 3));
+ if (args->wb0_memory == job->uargs.wb0_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR / sizeof(u32)]) {
+ MALI_DEBUG_CODE(disable_mask |= 0x1 << (4 * 1));
mali_pp_job_disable_wb0(job);
}
- if (args->wb1_memory == job->uargs.wb1_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR/sizeof(u32)]) {
- MALI_DEBUG_CODE(disable_mask |= 0x2<<(4*2));
+ if (args->wb1_memory == job->uargs.wb1_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR / sizeof(u32)]) {
+ MALI_DEBUG_CODE(disable_mask |= 0x2 << (4 * 2));
mali_pp_job_disable_wb1(job);
}
- if (args->wb2_memory == job->uargs.wb2_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR/sizeof(u32)]) {
- MALI_DEBUG_CODE(disable_mask |= 0x3<<(4*3));
+ if (args->wb2_memory == job->uargs.wb2_registers[MALI200_REG_ADDR_WB_SOURCE_ADDR / sizeof(u32)]) {
+ MALI_DEBUG_CODE(disable_mask |= 0x3 << (4 * 3));
mali_pp_job_disable_wb2(job);
}
MALI_DEBUG_PRINT(3, ("Mali PP scheduler: Disable WB: 0x%X.\n", disable_mask));
/* Find all jobs from the aborting session. */
_MALI_OSK_LIST_FOREACHENTRY(job, tmp_job, &session->pp_job_list, struct mali_pp_job, session_list) {
/* Remove job from queue. */
- if (mali_pp_job_is_virtual(job)) {
- MALI_DEBUG_ASSERT(1 == mali_pp_job_get_sub_job_count(job));
- if (0 == mali_pp_job_get_first_unstarted_sub_job(job)) {
- --virtual_job_queue.depth;
- }
+ if (mali_pp_job_is_virtual_group_job(job)) {
+ if (mali_pp_job_has_unstarted_sub_jobs(job))
+ --virtual_group_job_queue.depth;
} else {
job_queue.depth -= mali_pp_job_get_sub_job_count(job) - mali_pp_job_get_first_unstarted_sub_job(job);
}
_MALI_OSK_LIST_FOREACHENTRY(job, tmp_job, &removed_jobs, struct mali_pp_job, list) {
mali_timeline_tracker_release(&job->tracker);
mali_pp_job_delete(job);
- mali_pp_scheduler_job_completed();
+ mali_pp_scheduler_job_completed(MALI_TRUE);
}
/* Abort any running jobs from the session. */
}
if (mali_pp_scheduler_has_virtual_group()) {
- n += mali_group_dump_state(virtual_group, buf + n, size -n);
+ n += mali_group_dump_state(virtual_group, buf + n, size - n);
}
n += _mali_osk_snprintf(buf + n, size - n, "\n");
mali_group_get_pm_domain_ref(group);
MALI_DEBUG_ASSERT(NULL == group->pm_domain ||
- MALI_PM_DOMAIN_ON == mali_pm_domain_state_get(group->pm_domain));
+ MALI_PM_DOMAIN_ON == mali_pm_domain_state_get(group->pm_domain));
if (update_hw) {
mali_group_lock(group);
mali_group_get_pm_domain_ref(group);
MALI_DEBUG_ASSERT(NULL == group->pm_domain ||
- MALI_PM_DOMAIN_ON == mali_pm_domain_state_get(group->pm_domain));
+ MALI_PM_DOMAIN_ON == mali_pm_domain_state_get(group->pm_domain));
/* Put group on idle list. */
if (mali_pm_is_power_on()) {
mali_group_lock(group);
mali_pp_scheduler_lock();
- MALI_DEBUG_ASSERT( MALI_GROUP_STATE_IDLE == group->state
- || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
- || MALI_GROUP_STATE_DISABLED == group->state);
+ MALI_DEBUG_ASSERT(MALI_GROUP_STATE_IDLE == group->state
+ || MALI_GROUP_STATE_LEAVING_VIRTUAL == group->state
+ || MALI_GROUP_STATE_DISABLED == group->state);
if (MALI_GROUP_STATE_DISABLED == group->state) {
MALI_DEBUG_PRINT(4, ("Mali PP scheduler: PP group %p already disabled.\n", group));
static void mali_pp_scheduler_core_scale_up(unsigned int target_core_nr)
{
- MALI_DEBUG_PRINT(3, ("Requesting %d cores: enabling %d cores\n", target_core_nr, target_core_nr - enabled_cores));
+ MALI_DEBUG_PRINT(2, ("Requesting %d cores: enabling %d cores\n", target_core_nr, target_core_nr - enabled_cores));
_mali_osk_pm_dev_ref_add_no_power_on();
_mali_osk_pm_dev_barrier();
static void mali_pp_scheduler_core_scale_down(unsigned int target_core_nr)
{
- MALI_DEBUG_PRINT(3, ("Requesting %d cores: disabling %d cores\n", target_core_nr, enabled_cores - target_core_nr));
+ MALI_DEBUG_PRINT(2, ("Requesting %d cores: disabling %d cores\n", target_core_nr, enabled_cores - target_core_nr));
mali_pp_scheduler_suspend();
static void mali_pp_scheduler_job_queued(void)
{
- /* We hold a PM reference for every job we hold queued (and running) */
- _mali_osk_pm_dev_ref_add();
-
if (mali_utilization_enabled()) {
/*
* We cheat a little bit by counting the PP as busy from the time a PP job is queued.
}
}
-static void mali_pp_scheduler_job_completed(void)
+static void mali_pp_scheduler_job_completed(mali_bool job_started)
{
/* Release the PM reference we got in the mali_pp_scheduler_job_queued() function */
_mali_osk_pm_dev_ref_dec();
- if (mali_utilization_enabled()) {
+ if (mali_utilization_enabled() && job_started) {
mali_utilization_pp_end();
}
}
#else
mali_pp_job_delete(job);
#endif /* defined(MALI_PP_SCHEDULER_USE_DEFERRED_JOB_DELETE) */
- mali_pp_scheduler_job_completed();
+
+ /* Release the PM reference taken for the job in
+ * mali_pp_scheduler_submit_job(). */
+ _mali_osk_pm_dev_ref_dec();
/* Since we are aborting we ignore the scheduler mask. */
return MALI_SCHEDULER_MASK_EMPTY;
}
+ mali_pp_scheduler_job_queued();
+
#if defined(CONFIG_GPU_TRACEPOINTS) && defined(CONFIG_TRACEPOINTS)
trace_gpu_job_enqueue(mali_pp_job_get_tid(job), mali_pp_job_get_id(job), "PP");
#endif
job->cache_order = mali_scheduler_get_new_cache_order();
/* Determine which queue the job should be added to. */
- if (mali_pp_job_is_virtual(job)) {
+ if (mali_pp_job_is_virtual_group_job(job)) {
if (job->session->use_high_priority_job_queue) {
- queue = &virtual_job_queue.high_pri;
+ queue = &virtual_group_job_queue.high_pri;
} else {
- queue = &virtual_job_queue.normal_pri;
+ queue = &virtual_group_job_queue.normal_pri;
}
- virtual_job_queue.depth += 1;
+ virtual_group_job_queue.depth += 1;
/* Set schedule bitmask if the virtual group is idle. */
if (VIRTUAL_GROUP_IDLE == virtual_group_state) {
* idle virtual group. */
if (!_mali_osk_list_empty(&group_list_idle)
|| (mali_pp_scheduler_has_virtual_group()
- && (VIRTUAL_GROUP_IDLE == virtual_group_state))) {
+ && (VIRTUAL_GROUP_IDLE == virtual_group_state))) {
schedule_mask |= MALI_SCHEDULER_MASK_PP;
}
}
_mali_osk_list_addtail(&job->session_list, &(job->session->pp_job_list));
MALI_DEBUG_PRINT(3, ("Mali PP scheduler: %s job %u (0x%08X) with %u parts queued.\n",
- mali_pp_job_is_virtual(job) ? "Virtual" : "Physical",
- mali_pp_job_get_id(job), job, mali_pp_job_get_sub_job_count(job)));
+ mali_pp_job_is_virtual_group_job(job) ? "Virtual Group" : "Physical",
+ mali_pp_job_get_id(job), job, mali_pp_job_get_sub_job_count(job)));
mali_pp_scheduler_unlock();
mali_pp_scheduler_abort_job_and_unlock_scheduler(job);
mali_pp_job_mark_sub_job_completed(job, MALI_FALSE); /* Flagging the job as failed. */
- mali_pp_scheduler_finalize_job(job);
+ mali_pp_scheduler_finalize_job(job, MALI_FALSE);
return MALI_SCHEDULER_MASK_EMPTY;
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_errcode_t mali_scheduler_initialize(void)
{
- if ( _MALI_OSK_ERR_OK != _mali_osk_atomic_init(&mali_job_id_autonumber, 0)) {
- MALI_DEBUG_PRINT(1, ("Initialization of atomic job id counter failed.\n"));
+ if (_MALI_OSK_ERR_OK != _mali_osk_atomic_init(&mali_job_id_autonumber, 0)) {
+ MALI_DEBUG_PRINT(1, ("Initialization of atomic job id counter failed.\n"));
return _MALI_OSK_ERR_FAULT;
}
- if ( _MALI_OSK_ERR_OK != _mali_osk_atomic_init(&mali_job_cache_order_autonumber, 0)) {
- MALI_DEBUG_PRINT(1, ("Initialization of atomic job cache order counter failed.\n"));
+ if (_MALI_OSK_ERR_OK != _mali_osk_atomic_init(&mali_job_cache_order_autonumber, 0)) {
+ MALI_DEBUG_PRINT(1, ("Initialization of atomic job cache order counter failed.\n"));
_mali_osk_atomic_term(&mali_job_id_autonumber);
return _MALI_OSK_ERR_FAULT;
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_PP_JOB_FB_LOOKUP_LIST_MASK (MALI_PP_JOB_FB_LOOKUP_LIST_SIZE - 1)
struct mali_session_data {
- _mali_osk_notification_queue_t * ioctl_queue;
+ _mali_osk_notification_queue_t *ioctl_queue;
_mali_osk_mutex_t *memory_lock; /**< Lock protecting the vm manipulation */
- mali_descriptor_mapping * descriptor_mapping; /**< Mapping between userspace descriptors and our pointers */
+ mali_descriptor_mapping *descriptor_mapping; /**< Mapping between userspace descriptors and our pointers */
_mali_osk_list_t memory_head; /**< Track all the memory allocated in this session, for freeing on abnormal termination */
struct mali_page_directory *page_directory; /**< MMU page directory for this session */
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct mali_soft_job_system *mali_soft_job_system_create(struct mali_session_data *session)
{
- u32 i;
struct mali_soft_job_system *system;
- struct mali_soft_job *job;
MALI_DEBUG_ASSERT_POINTER(session);
return NULL;
}
system->lock_owner = 0;
+ system->last_job_id = 0;
- _MALI_OSK_INIT_LIST_HEAD(&(system->jobs_free));
_MALI_OSK_INIT_LIST_HEAD(&(system->jobs_used));
- for (i = 0; i < MALI_MAX_NUM_SOFT_JOBS; ++i) {
- job = &(system->jobs[i]);
- _mali_osk_list_add(&(job->system_list), &(system->jobs_free));
- job->system = system;
- job->state = MALI_SOFT_JOB_STATE_FREE;
- job->id = i;
- }
-
return system;
}
MALI_DEBUG_ASSERT_POINTER(system);
/* All jobs should be free at this point. */
- MALI_DEBUG_CODE( {
- u32 i;
- struct mali_soft_job *job;
-
- for (i = 0; i < MALI_MAX_NUM_SOFT_JOBS; ++i)
- {
- job = &(system->jobs[i]);
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_FREE == job->state);
- }
- });
+ MALI_DEBUG_ASSERT(_mali_osk_list_empty(&(system->jobs_used)));
if (NULL != system) {
if (NULL != system->lock) {
}
}
-static struct mali_soft_job *mali_soft_job_system_alloc_job(struct mali_soft_job_system *system)
-{
- struct mali_soft_job *job;
-
- MALI_DEBUG_ASSERT_POINTER(system);
- MALI_ASSERT_SOFT_JOB_SYSTEM_LOCKED(system);
-
- if (_mali_osk_list_empty(&(system->jobs_free))) {
- /* No jobs available. */
- return NULL;
- }
-
- /* Grab first job and move it to the used list. */
- job = _MALI_OSK_LIST_ENTRY(system->jobs_free.next, struct mali_soft_job, system_list);
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_FREE == job->state);
-
- _mali_osk_list_move(&(job->system_list), &(system->jobs_used));
- job->state = MALI_SOFT_JOB_STATE_ALLOCATED;
-
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_INVALID_ID != job->id);
- MALI_DEBUG_ASSERT(system == job->system);
-
- return job;
-}
-
static void mali_soft_job_system_free_job(struct mali_soft_job_system *system, struct mali_soft_job *job)
{
MALI_DEBUG_ASSERT_POINTER(job);
mali_soft_job_system_lock(job->system);
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_FREE != job->state);
MALI_DEBUG_ASSERT(MALI_SOFT_JOB_INVALID_ID != job->id);
MALI_DEBUG_ASSERT(system == job->system);
- job->state = MALI_SOFT_JOB_STATE_FREE;
- _mali_osk_list_move(&(job->system_list), &(system->jobs_free));
+ _mali_osk_list_del(&(job->system_list));
mali_soft_job_system_unlock(job->system);
+
+ _mali_osk_free(job);
}
MALI_STATIC_INLINE struct mali_soft_job *mali_soft_job_system_lookup_job(struct mali_soft_job_system *system, u32 job_id)
{
+ struct mali_soft_job *job, *tmp;
+
MALI_DEBUG_ASSERT_POINTER(system);
MALI_ASSERT_SOFT_JOB_SYSTEM_LOCKED(system);
- if (job_id < MALI_MAX_NUM_SOFT_JOBS) {
- return &system->jobs[job_id];
+ _MALI_OSK_LIST_FOREACHENTRY(job, tmp, &system->jobs_used, struct mali_soft_job, system_list) {
+ if (job->id == job_id)
+ return job;
}
return NULL;
}
}
-struct mali_soft_job *mali_soft_job_create(struct mali_soft_job_system *system, mali_soft_job_type type, u32 user_job)
+struct mali_soft_job *mali_soft_job_create(struct mali_soft_job_system *system, mali_soft_job_type type, u64 user_job)
{
struct mali_soft_job *job;
_mali_osk_notification_t *notification = NULL;
MALI_DEBUG_ASSERT_POINTER(system);
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_TYPE_USER_SIGNALED >= type);
+ MALI_DEBUG_ASSERT((MALI_SOFT_JOB_TYPE_USER_SIGNALED == type) ||
+ (MALI_SOFT_JOB_TYPE_SELF_SIGNALED == type));
- if (MALI_SOFT_JOB_TYPE_USER_SIGNALED == type) {
- notification = _mali_osk_notification_create(_MALI_NOTIFICATION_SOFT_ACTIVATED, sizeof(_mali_uk_soft_job_activated_s));
- if (unlikely(NULL == notification)) {
- MALI_PRINT_ERROR(("Mali Soft Job: failed to allocate notification"));
- return NULL;
- }
+ notification = _mali_osk_notification_create(_MALI_NOTIFICATION_SOFT_ACTIVATED, sizeof(_mali_uk_soft_job_activated_s));
+ if (unlikely(NULL == notification)) {
+ MALI_PRINT_ERROR(("Mali Soft Job: failed to allocate notification"));
+ return NULL;
}
- mali_soft_job_system_lock(system);
-
- job = mali_soft_job_system_alloc_job(system);
- if (NULL == job) {
- mali_soft_job_system_unlock(system);
- MALI_PRINT_ERROR(("Mali Soft Job: failed to allocate job"));
- _mali_osk_notification_delete(notification);
+ job = _mali_osk_malloc(sizeof(struct mali_soft_job));
+ if (unlikely(NULL == job)) {
+ MALI_DEBUG_PRINT(2, ("Mali Soft Job: system alloc job failed. \n"));
return NULL;
}
+ mali_soft_job_system_lock(system);
+
+ job->system = system;
+ job->id = system->last_job_id++;
+ job->state = MALI_SOFT_JOB_STATE_ALLOCATED;
+
+ _mali_osk_list_add(&(job->system_list), &(system->jobs_used));
+
job->type = type;
job->user_job = user_job;
job->activated = MALI_FALSE;
- if (MALI_SOFT_JOB_TYPE_USER_SIGNALED == type) {
- job->activated_notification = notification;
- }
+ job->activated_notification = notification;
_mali_osk_atomic_init(&job->refcount, 1);
job = mali_soft_job_system_lookup_job(system, job_id);
- if (NULL == job || !(MALI_SOFT_JOB_STATE_STARTED == job->state || MALI_SOFT_JOB_STATE_TIMED_OUT == job->state)) {
+ if ((NULL == job) || (MALI_SOFT_JOB_TYPE_USER_SIGNALED != job->type)
+ || !(MALI_SOFT_JOB_STATE_STARTED == job->state || MALI_SOFT_JOB_STATE_TIMED_OUT == job->state)) {
mali_soft_job_system_unlock(system);
MALI_PRINT_ERROR(("Mali Soft Job: invalid soft job id %u", job_id));
return _MALI_OSK_ERR_ITEM_NOT_FOUND;
/* Wake up sleeping signaler. */
job->activated = MALI_TRUE;
- _mali_osk_wait_queue_wake_up(job->tracker.system->wait_queue);
- mali_soft_job_system_unlock(job->system);
+ /* If job type is self signaled, release tracker, move soft job to free list, and scheduler at once */
+ if (MALI_SOFT_JOB_TYPE_SELF_SIGNALED == job->type) {
+ mali_scheduler_mask schedule_mask;
+
+ MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_STARTED == job->state);
+
+ job->state = MALI_SOFT_JOB_STATE_SIGNALED;
+ mali_soft_job_system_unlock(job->system);
+
+ schedule_mask = mali_timeline_tracker_release(&job->tracker);
+ mali_scheduler_schedule_from_mask(schedule_mask, MALI_FALSE);
+
+ mali_soft_job_destroy(job);
+ } else {
+ _mali_osk_wait_queue_wake_up(job->tracker.system->wait_queue);
+
+ mali_soft_job_system_unlock(job->system);
+ }
}
mali_scheduler_mask mali_soft_job_system_timeout_job(struct mali_soft_job *job)
mali_soft_job_system_lock(job->system);
MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_STARTED == job->state ||
- MALI_SOFT_JOB_STATE_SIGNALED == job->state);
+ MALI_SOFT_JOB_STATE_SIGNALED == job->state);
if (unlikely(job->system->session->is_aborting)) {
/* The session is aborting. This job will be released and destroyed by @ref
void mali_soft_job_system_abort(struct mali_soft_job_system *system)
{
- u32 i;
struct mali_soft_job *job, *tmp;
_MALI_OSK_LIST_HEAD_STATIC_INIT(jobs);
mali_soft_job_system_lock(system);
- for (i = 0; i < MALI_MAX_NUM_SOFT_JOBS; ++i) {
- job = &(system->jobs[i]);
-
- MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_FREE == job->state ||
- MALI_SOFT_JOB_STATE_STARTED == job->state ||
- MALI_SOFT_JOB_STATE_TIMED_OUT == job->state);
+ _MALI_OSK_LIST_FOREACHENTRY(job, tmp, &system->jobs_used, struct mali_soft_job, system_list) {
+ MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_STARTED == job->state ||
+ MALI_SOFT_JOB_STATE_TIMED_OUT == job->state);
if (MALI_SOFT_JOB_STATE_STARTED == job->state) {
/* If the job has been activated, we have to release the tracker and destroy
/* Release and destroy jobs. */
_MALI_OSK_LIST_FOREACHENTRY(job, tmp, &jobs, struct mali_soft_job, system_list) {
MALI_DEBUG_ASSERT(MALI_SOFT_JOB_STATE_SIGNALED == job->state ||
- MALI_SOFT_JOB_STATE_TIMED_OUT == job->state);
+ MALI_SOFT_JOB_STATE_TIMED_OUT == job->state);
if (MALI_SOFT_JOB_STATE_SIGNALED == job->state) {
mali_timeline_tracker_release(&job->tracker);
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* Soft jobs of type MALI_SOFT_JOB_TYPE_USER_SIGNALED will only complete after activation if either
* they are signaled by user-space (@ref mali_soft_job_system_signaled_job) or if they are timed out
* by the Timeline system.
+ * Soft jobs of type MALI_SOFT_JOB_TYPE_SELF_SIGNALED will release job resource automatically
+ * in kernel when the job is activated.
*/
typedef enum mali_soft_job_type {
+ MALI_SOFT_JOB_TYPE_SELF_SIGNALED,
MALI_SOFT_JOB_TYPE_USER_SIGNALED,
} mali_soft_job_type;
/**
* Soft job state.
*
- * All soft jobs in a soft job system will initially be in state MALI_SOFT_JOB_STATE_FREE. On @ref
- * mali_soft_job_system_start_job a job will first be allocated. A job in state
- * MALI_SOFT_JOB_STATE_FREE will be picked and the state changed to MALI_SOFT_JOB_STATE_ALLOCATED.
+ * mali_soft_job_system_start_job a job will first be allocated.The job's state set to MALI_SOFT_JOB_STATE_ALLOCATED.
* Once the job is added to the timeline system, the state changes to MALI_SOFT_JOB_STATE_STARTED.
*
* For soft jobs of type MALI_SOFT_JOB_TYPE_USER_SIGNALED the state is changed to
* state is changed to MALI_SOFT_JOB_STATE_TIMED_OUT. This can only happen to soft jobs in state
* MALI_SOFT_JOB_STATE_STARTED.
*
- * When a soft job's reference count reaches zero, it will be freed and the state returns to
- * MALI_SOFT_JOB_STATE_FREE.
*/
typedef enum mali_soft_job_state {
- MALI_SOFT_JOB_STATE_FREE,
MALI_SOFT_JOB_STATE_ALLOCATED,
MALI_SOFT_JOB_STATE_STARTED,
MALI_SOFT_JOB_STATE_SIGNALED,
#define MALI_SOFT_JOB_INVALID_ID ((u32) -1)
-/* Maximum number of soft jobs per soft system. */
-#define MALI_MAX_NUM_SOFT_JOBS 20
-
/**
* Soft job struct.
*
*/
typedef struct mali_soft_job {
mali_soft_job_type type; /**< Soft job type. Must be one of MALI_SOFT_JOB_TYPE_*. */
- u32 user_job; /**< Identifier for soft job in user space. */
+ u64 user_job; /**< Identifier for soft job in user space. */
_mali_osk_atomic_t refcount; /**< Soft jobs are reference counted to prevent premature deletion. */
struct mali_timeline_tracker tracker; /**< Timeline tracker for soft job. */
mali_bool activated; /**< MALI_TRUE if the job has been activated, MALI_FALSE if not. */
*/
typedef struct mali_soft_job_system {
struct mali_session_data *session; /**< The session this soft job system belongs to. */
-
- struct mali_soft_job jobs[MALI_MAX_NUM_SOFT_JOBS]; /**< Array of all soft jobs in this system. */
- _MALI_OSK_LIST_HEAD(jobs_free); /**< List of all free soft jobs. */
_MALI_OSK_LIST_HEAD(jobs_used); /**< List of all allocated soft jobs. */
_mali_osk_spinlock_irq_t *lock; /**< Lock used to protect soft job system and its soft jobs. */
u32 lock_owner; /**< Contains tid of thread that locked the system or 0, if not locked. */
+ u32 last_job_id; /**< Recored the last job id protected by lock. */
} mali_soft_job_system;
/**
* @param user_job Identifier for soft job in user space.
* @return New soft job if successful, NULL if not.
*/
-struct mali_soft_job *mali_soft_job_create(struct mali_soft_job_system *system, mali_soft_job_type type, u32 user_job);
+struct mali_soft_job *mali_soft_job_create(struct mali_soft_job_system *system, mali_soft_job_type type, u64 user_job);
/**
* Destroy soft job.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_TIMELINE_SYSTEM_LOCKED(system) (mali_spinlock_reentrant_is_held((system)->spinlock, _mali_osk_get_tid()))
static mali_scheduler_mask mali_timeline_system_release_waiter(struct mali_timeline_system *system,
- struct mali_timeline_waiter *waiter);
+ struct mali_timeline_waiter *waiter);
#if defined(CONFIG_SYNC)
+#include <linux/version.h>
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,5,0)
+#include <linux/list.h>
+#include <linux/workqueue.h>
+#include <linux/spinlock.h>
+
+struct mali_deferred_fence_put_entry {
+ struct hlist_node list;
+ struct sync_fence *fence;
+};
+
+static HLIST_HEAD(mali_timeline_sync_fence_to_free_list);
+static DEFINE_SPINLOCK(mali_timeline_sync_fence_to_free_lock);
+
+static void put_sync_fences(struct work_struct *ignore)
+{
+ struct hlist_head list;
+ struct hlist_node *tmp, *pos;
+ unsigned long flags;
+ struct mali_deferred_fence_put_entry *o;
+
+ spin_lock_irqsave(&mali_timeline_sync_fence_to_free_lock, flags);
+ hlist_move_list(&mali_timeline_sync_fence_to_free_list, &list);
+ spin_unlock_irqrestore(&mali_timeline_sync_fence_to_free_lock, flags);
+
+ hlist_for_each_entry_safe(o, pos, tmp, &list, list) {
+ sync_fence_put(o->fence);
+ kfree(o);
+ }
+}
+
+static DECLARE_DELAYED_WORK(delayed_sync_fence_put, put_sync_fences);
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3,5,0) */
+
/* Callback that is called when a sync fence a tracker is waiting on is signaled. */
static void mali_timeline_sync_fence_callback(struct sync_fence *sync_fence, struct sync_fence_waiter *sync_fence_waiter)
{
mali_spinlock_reentrant_signal(system->spinlock, tid);
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,5,0)
+ {
+ struct mali_deferred_fence_put_entry *obj;
+
+ obj = kzalloc(sizeof(struct mali_deferred_fence_put_entry), GFP_ATOMIC);
+ if (obj) {
+ unsigned long flags;
+ mali_bool schedule = MALI_FALSE;
+
+ obj->fence = sync_fence;
+
+ spin_lock_irqsave(&mali_timeline_sync_fence_to_free_lock, flags);
+ if (hlist_empty(&mali_timeline_sync_fence_to_free_list))
+ schedule = MALI_TRUE;
+ hlist_add_head(&obj->list, &mali_timeline_sync_fence_to_free_list);
+ spin_unlock_irqrestore(&mali_timeline_sync_fence_to_free_lock, flags);
+
+ if (schedule)
+ schedule_delayed_work(&delayed_sync_fence_put, 0);
+ }
+ }
+#else
sync_fence_put(sync_fence);
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3,5,0) */
if (!is_aborting) {
mali_scheduler_schedule_from_mask(schedule_mask, MALI_TRUE);
/* Waiter time must be between timeline head and tail, and there must
* be less than MALI_TIMELINE_MAX_POINT_SPAN elements between */
- MALI_DEBUG_ASSERT(( waiter_new->point - timeline->point_oldest) < MALI_TIMELINE_MAX_POINT_SPAN);
+ MALI_DEBUG_ASSERT((waiter_new->point - timeline->point_oldest) < MALI_TIMELINE_MAX_POINT_SPAN);
MALI_DEBUG_ASSERT((-waiter_new->point + timeline->point_next) < MALI_TIMELINE_MAX_POINT_SPAN);
/* Finding out where to put this waiter, in the linked waiter list of the given timeline **/
}
void mali_timeline_tracker_init(struct mali_timeline_tracker *tracker,
- mali_timeline_tracker_type type,
- struct mali_timeline_fence *fence,
- void *job)
+ mali_timeline_tracker_type type,
+ struct mali_timeline_fence *fence,
+ void *job)
{
MALI_DEBUG_ASSERT_POINTER(tracker);
MALI_DEBUG_ASSERT_POINTER(job);
/* Tracker should still be on timeline */
MALI_DEBUG_ASSERT(!mali_timeline_is_empty(timeline));
- MALI_DEBUG_ASSERT( mali_timeline_is_point_on(timeline, tracker->point));
+ MALI_DEBUG_ASSERT(mali_timeline_is_point_on(timeline, tracker->point));
/* Tracker is no longer valid. */
MALI_DEBUG_CODE(tracker->magic = 0);
}
void mali_timeline_system_release_waiter_list(struct mali_timeline_system *system,
- struct mali_timeline_waiter *tail,
- struct mali_timeline_waiter *head)
+ struct mali_timeline_waiter *tail,
+ struct mali_timeline_waiter *head)
{
MALI_DEBUG_ASSERT_POINTER(system);
MALI_DEBUG_ASSERT_POINTER(head);
#endif /* defined(CONFIG_SYNC) */
/* Should not be any waiters or trackers left at this point. */
- MALI_DEBUG_CODE( {
+ MALI_DEBUG_CODE({
u32 i;
mali_spinlock_reentrant_wait(system->spinlock, tid);
for (i = 0; i < MALI_TIMELINE_MAX; ++i)
}
static void mali_timeline_system_allocate_waiters(struct mali_timeline_system *system,
- struct mali_timeline_waiter **tail,
- struct mali_timeline_waiter **head,
- int max_num_waiters)
+ struct mali_timeline_waiter **tail,
+ struct mali_timeline_waiter **head,
+ int max_num_waiters)
{
u32 i, tid = _mali_osk_get_tid();
mali_bool do_alloc;
* @param waiter_head List of pre-allocated waiters.
*/
static void mali_timeline_system_create_waiters_and_unlock(struct mali_timeline_system *system,
- struct mali_timeline_tracker *tracker,
- struct mali_timeline_waiter *waiter_tail,
- struct mali_timeline_waiter *waiter_head)
+ struct mali_timeline_tracker *tracker,
+ struct mali_timeline_waiter *waiter_tail,
+ struct mali_timeline_waiter *waiter_head)
{
int i;
u32 tid = _mali_osk_get_tid();
if (unlikely(!mali_timeline_is_point_valid(timeline, point))) {
MALI_PRINT_ERROR(("Mali Timeline: point %d is not valid (oldest=%d, next=%d)\n",
- point, timeline->point_oldest, timeline->point_next));
+ point, timeline->point_oldest, timeline->point_next));
continue;
}
}
mali_timeline_point mali_timeline_system_add_tracker(struct mali_timeline_system *system,
- struct mali_timeline_tracker *tracker,
- enum mali_timeline_id timeline_id)
+ struct mali_timeline_tracker *tracker,
+ enum mali_timeline_id timeline_id)
{
int num_waiters = 0;
struct mali_timeline_waiter *waiter_tail, *waiter_head;
}
static mali_scheduler_mask mali_timeline_system_release_waiter(struct mali_timeline_system *system,
- struct mali_timeline_waiter *waiter)
+ struct mali_timeline_waiter *waiter)
{
struct mali_timeline_tracker *tracker;
mali_scheduler_mask schedule_mask = MALI_SCHEDULER_MASK_EMPTY;
}
mali_timeline_point mali_timeline_system_get_latest_point(struct mali_timeline_system *system,
- enum mali_timeline_id timeline_id)
+ enum mali_timeline_id timeline_id)
{
mali_timeline_point point;
struct mali_timeline *timeline;
MALI_DEBUG_ASSERT_POINTER(timeline->system);
system = timeline->system;
- if (MALI_TIMELINE_MAX > id) {
- return mali_timeline_is_point_on(system->timelines[id], tracker->fence.points[id]);
+ if (MALI_TIMELINE_MAX > id ) {
+ if(MALI_TIMELINE_NO_POINT != tracker->fence.points[id]) {
+ return mali_timeline_is_point_on(system->timelines[id], tracker->fence.points[id]);
+ } else {
+ return MALI_FALSE;
+ }
} else {
MALI_DEBUG_ASSERT(MALI_TIMELINE_NONE == id);
return MALI_FALSE;
{
switch (id) {
case MALI_TIMELINE_GP:
- return " GP";
+ return "GP";
case MALI_TIMELINE_PP:
- return " PP";
+ return "PP";
case MALI_TIMELINE_SOFT:
return "SOFT";
default:
{
switch (type) {
case MALI_TIMELINE_TRACKER_GP:
- return " GP";
+ return "GP";
case MALI_TIMELINE_TRACKER_PP:
- return " PP";
+ return "PP";
case MALI_TIMELINE_TRACKER_SOFT:
return "SOFT";
case MALI_TIMELINE_TRACKER_WAIT:
return MALI_TIMELINE_TS_FINISH;
}
-void mali_timeline_debug_print_tracker(struct mali_timeline_tracker *tracker)
+void mali_timeline_debug_print_tracker(struct mali_timeline_tracker *tracker, _mali_osk_print_ctx *print_ctx)
{
const char *tracker_state = "IWAF";
+ char state_char = 'I';
+ char tracker_type[32] = {0};
MALI_DEBUG_ASSERT_POINTER(tracker);
+ state_char = *(tracker_state + mali_timeline_debug_get_tracker_state(tracker));
+ _mali_osk_snprintf(tracker_type, sizeof(tracker_type), "%s", timeline_tracker_type_to_string(tracker->type));
+
if (0 != tracker->trigger_ref_count) {
- MALI_PRINTF(("TL: %s %u %c - ref_wait:%u [%s%u,%s%u,%s%u,%d] (0x%08X)\n",
- timeline_tracker_type_to_string(tracker->type), tracker->point,
- *(tracker_state + mali_timeline_debug_get_tracker_state(tracker)),
- tracker->trigger_ref_count,
- is_waiting_on_timeline(tracker, MALI_TIMELINE_GP) ? "W" : " ", tracker->fence.points[0],
- is_waiting_on_timeline(tracker, MALI_TIMELINE_PP) ? "W" : " ", tracker->fence.points[1],
- is_waiting_on_timeline(tracker, MALI_TIMELINE_SOFT) ? "W" : " ", tracker->fence.points[2],
- tracker->fence.sync_fd, tracker->job));
+#if defined(CONFIG_SYNC)
+ _mali_osk_ctxprintf(print_ctx, "TL: %s %u %c - ref_wait:%u [%s%u,%s%u,%s%u, fd:%d, fence:(0x%08X)] job:(0x%08X)\n",
+ tracker_type, tracker->point, state_char, tracker->trigger_ref_count,
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_GP) ? "W" : " ", tracker->fence.points[0],
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_PP) ? "W" : " ", tracker->fence.points[1],
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_SOFT) ? "W" : " ", tracker->fence.points[2],
+ tracker->fence.sync_fd, tracker->sync_fence, tracker->job);
} else {
- MALI_PRINTF(("TL: %s %u %c (0x%08X)\n",
- timeline_tracker_type_to_string(tracker->type), tracker->point,
- *(tracker_state + mali_timeline_debug_get_tracker_state(tracker)),
- tracker->job));
+ _mali_osk_ctxprintf(print_ctx, "TL: %s %u %c fd:%d fence:(0x%08X) job:(0x%08X)\n",
+ tracker_type, tracker->point, state_char,
+ tracker->fence.sync_fd, tracker->sync_fence, tracker->job);
}
+#else
+ _mali_osk_ctxprintf(print_ctx, "TL: %s %u %c - ref_wait:%u [%s%u,%s%u,%s%u] job:(0x%08X)\n",
+ tracker_type, tracker->point, state_char, tracker->trigger_ref_count,
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_GP) ? "W" : " ", tracker->fence.points[0],
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_PP) ? "W" : " ", tracker->fence.points[1],
+ is_waiting_on_timeline(tracker, MALI_TIMELINE_SOFT) ? "W" : " ", tracker->fence.points[2],
+ tracker->job);
+ } else {
+ _mali_osk_ctxprintf(print_ctx, "TL: %s %u %c job:(0x%08X)\n",
+ tracker_type, tracker->point, state_char,
+ tracker->job);
+ }
+#endif
}
-void mali_timeline_debug_print_timeline(struct mali_timeline *timeline)
+void mali_timeline_debug_print_timeline(struct mali_timeline *timeline, _mali_osk_print_ctx *print_ctx)
{
struct mali_timeline_tracker *tracker = NULL;
- int i_max = 30;
MALI_DEBUG_ASSERT_POINTER(timeline);
tracker = timeline->tracker_tail;
- while (NULL != tracker && 0 < --i_max) {
- mali_timeline_debug_print_tracker(tracker);
+ while (NULL != tracker) {
+ mali_timeline_debug_print_tracker(tracker, print_ctx);
tracker = tracker->timeline_next;
}
-
- if (0 == i_max) {
- MALI_PRINTF(("TL: Too many trackers in list to print\n"));
- }
}
-void mali_timeline_debug_print_system(struct mali_timeline_system *system)
+void mali_timeline_debug_print_system(struct mali_timeline_system *system, _mali_osk_print_ctx *print_ctx)
{
int i;
int num_printed = 0;
+ u32 tid = _mali_osk_get_tid();
MALI_DEBUG_ASSERT_POINTER(system);
+ mali_spinlock_reentrant_wait(system->spinlock, tid);
+
/* Print all timelines */
for (i = 0; i < MALI_TIMELINE_MAX; ++i) {
struct mali_timeline *timeline = system->timelines[i];
if (NULL == timeline->tracker_head) continue;
- MALI_PRINTF(("TL: Timeline %s:\n",
- timeline_id_to_string((enum mali_timeline_id)i)));
- mali_timeline_debug_print_timeline(timeline);
+ _mali_osk_ctxprintf(print_ctx, "TL: Timeline %s:\n",
+ timeline_id_to_string((enum mali_timeline_id)i));
+
+ mali_timeline_debug_print_timeline(timeline, print_ctx);
num_printed++;
}
if (0 == num_printed) {
- MALI_PRINTF(("TL: All timelines empty\n"));
+ _mali_osk_ctxprintf(print_ctx, "TL: All timelines empty\n");
}
+
+ mali_spinlock_reentrant_signal(system->spinlock, tid);
}
#endif /* defined(MALI_TIMELINE_DEBUG_FUNCTIONS) */
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @return Point on timeline identifying this tracker, or MALI_TIMELINE_NO_POINT if not on timeline.
*/
mali_timeline_point mali_timeline_system_add_tracker(struct mali_timeline_system *system,
- struct mali_timeline_tracker *tracker,
- enum mali_timeline_id timeline_id);
+ struct mali_timeline_tracker *tracker,
+ enum mali_timeline_id timeline_id);
/**
* Get latest point on timeline.
* @return Latest point on timeline, or MALI_TIMELINE_NO_POINT if the timeline is empty.
*/
mali_timeline_point mali_timeline_system_get_latest_point(struct mali_timeline_system *system,
- enum mali_timeline_id timeline_id);
+ enum mali_timeline_id timeline_id);
/**
* Initialize tracker.
* @param job Pointer to job struct this tracker is associated with.
*/
void mali_timeline_tracker_init(struct mali_timeline_tracker *tracker,
- mali_timeline_tracker_type type,
- struct mali_timeline_fence *fence,
- void *job);
+ mali_timeline_tracker_type type,
+ struct mali_timeline_fence *fence,
+ void *job);
/**
* Grab trigger ref count on tracker.
*/
void mali_timeline_fence_copy_uk_fence(struct mali_timeline_fence *fence, _mali_uk_fence_t *uk_fence);
+#if defined(DEBUG)
#define MALI_TIMELINE_DEBUG_FUNCTIONS
+#endif /* DEBUG */
#if defined(MALI_TIMELINE_DEBUG_FUNCTIONS)
/**
*
* @param tracker Tracker to print.
*/
-void mali_timeline_debug_print_tracker(struct mali_timeline_tracker *tracker);
+void mali_timeline_debug_print_tracker(struct mali_timeline_tracker *tracker, _mali_osk_print_ctx *print_ctx);
/**
* Print debug information about timeline.
*
* @param timeline Timeline to print.
*/
-void mali_timeline_debug_print_timeline(struct mali_timeline *timeline);
+void mali_timeline_debug_print_timeline(struct mali_timeline *timeline, _mali_osk_print_ctx *print_ctx);
/**
* Print debug information about timeline system.
*
* @param system Timeline system to print.
*/
-void mali_timeline_debug_print_system(struct mali_timeline_system *system);
+void mali_timeline_debug_print_system(struct mali_timeline_system *system, _mali_osk_print_ctx *print_ctx);
#endif /* defined(MALI_TIMELINE_DEBUG_FUNCTIONS) */
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @param context pointer to storage to return a (void*)context handle.
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_open( void **context );
+_mali_osk_errcode_t _mali_ukk_open(void **context);
/** @brief End a Mali Device Driver session
*
* @param context pointer to a stored (void*)context handle.
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_close( void **context );
+_mali_osk_errcode_t _mali_ukk_close(void **context);
/** @} */ /* end group _mali_uk_context */
* @param args see _mali_uk_wait_for_notification_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_wait_for_notification( _mali_uk_wait_for_notification_s *args );
+_mali_osk_errcode_t _mali_ukk_wait_for_notification(_mali_uk_wait_for_notification_s *args);
/** @brief Post a notification to the notification queue of this application.
*
* @param args see _mali_uk_post_notification_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_post_notification( _mali_uk_post_notification_s *args );
+_mali_osk_errcode_t _mali_ukk_post_notification(_mali_uk_post_notification_s *args);
/** @brief Verifies if the user and kernel side of this API are compatible.
+ *
+ * This function is obsolete, but kept to allow old, incompatible user space
+ * clients to robustly detect the incompatibility.
*
* @param args see _mali_uk_get_api_version_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_get_api_version( _mali_uk_get_api_version_s *args );
+_mali_osk_errcode_t _mali_ukk_get_api_version(_mali_uk_get_api_version_s *args);
+
+/** @brief Verifies if the user and kernel side of this API are compatible.
+ *
+ * @param args see _mali_uk_get_api_version_v2_s in "mali_utgard_uk_types.h"
+ * @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
+ */
+_mali_osk_errcode_t _mali_ukk_get_api_version_v2(_mali_uk_get_api_version_v2_s *args);
/** @brief Get the user space settings applicable for calling process.
*
* @param args see _mali_uk_mem_mmap_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_mem_mmap( _mali_uk_mem_mmap_s *args );
+_mali_osk_errcode_t _mali_ukk_mem_mmap(_mali_uk_mem_mmap_s *args);
/** @brief Unmap Mali Memory from the current user process
*
* @param args see _mali_uk_mem_munmap_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_mem_munmap( _mali_uk_mem_munmap_s *args );
+_mali_osk_errcode_t _mali_ukk_mem_munmap(_mali_uk_mem_munmap_s *args);
/** @brief Determine the buffer size necessary for an MMU page table dump.
* @param args see _mali_uk_query_mmu_page_table_dump_size_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_query_mmu_page_table_dump_size( _mali_uk_query_mmu_page_table_dump_size_s *args );
+_mali_osk_errcode_t _mali_ukk_query_mmu_page_table_dump_size(_mali_uk_query_mmu_page_table_dump_size_s *args);
/** @brief Dump MMU Page tables.
* @param args see _mali_uk_dump_mmu_page_table_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_dump_mmu_page_table( _mali_uk_dump_mmu_page_table_s * args );
+_mali_osk_errcode_t _mali_ukk_dump_mmu_page_table(_mali_uk_dump_mmu_page_table_s *args);
/** @brief Write user data to specified Mali memory without causing segfaults.
* @param args see _mali_uk_mem_write_safe_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_mem_write_safe( _mali_uk_mem_write_safe_s *args );
+_mali_osk_errcode_t _mali_ukk_mem_write_safe(_mali_uk_mem_write_safe_s *args);
/** @brief Map a physically contiguous range of memory into Mali
* @param args see _mali_uk_map_external_mem_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_map_external_mem( _mali_uk_map_external_mem_s *args );
+_mali_osk_errcode_t _mali_ukk_map_external_mem(_mali_uk_map_external_mem_s *args);
/** @brief Unmap a physically contiguous range of memory from Mali
* @param args see _mali_uk_unmap_external_mem_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_unmap_external_mem( _mali_uk_unmap_external_mem_s *args );
+_mali_osk_errcode_t _mali_ukk_unmap_external_mem(_mali_uk_unmap_external_mem_s *args);
#if defined(CONFIG_MALI400_UMP)
/** @brief Map UMP memory into Mali
* @param args see _mali_uk_attach_ump_mem_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_attach_ump_mem( _mali_uk_attach_ump_mem_s *args );
+_mali_osk_errcode_t _mali_ukk_attach_ump_mem(_mali_uk_attach_ump_mem_s *args);
/** @brief Unmap UMP memory from Mali
* @param args see _mali_uk_release_ump_mem_s in mali_utgard_uk_types.h
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_release_ump_mem( _mali_uk_release_ump_mem_s *args );
+_mali_osk_errcode_t _mali_ukk_release_ump_mem(_mali_uk_release_ump_mem_s *args);
#endif /* CONFIG_MALI400_UMP */
-/** @brief Determine virtual-to-physical mapping of a contiguous memory range
- * (optional)
- *
- * This allows the user-side to do a virtual-to-physical address translation.
- * In conjunction with _mali_uku_map_external_mem, this can be used to do
- * direct rendering.
- *
- * This function will only succeed on a virtual range that is mapped into the
- * current process, and that is contigious.
- *
- * If va is not page-aligned, then it is rounded down to the next page
- * boundary. The remainer is added to size, such that ((u32)va)+size before
- * rounding is equal to ((u32)va)+size after rounding. The rounded modified
- * va and size will be written out into args on success.
- *
- * If the supplied size is zero, or not a multiple of the system's PAGE_SIZE,
- * then size will be rounded up to the next multiple of PAGE_SIZE before
- * translation occurs. The rounded up size will be written out into args on
- * success.
- *
- * On most OSs, virtual-to-physical address translation is a priveledged
- * function. Therefore, the implementer must validate the range supplied, to
- * ensure they are not providing arbitrary virtual-to-physical address
- * translations. While it is unlikely such a mechanism could be used to
- * compromise the security of a system on its own, it is possible it could be
- * combined with another small security risk to cause a much larger security
- * risk.
- *
- * @note This is an optional part of the interface, and is only used by certain
- * implementations of libEGL. If the platform layer in your libEGL
- * implementation does not require Virtual-to-Physical address translation,
- * then this function need not be implemented. A stub implementation should not
- * be required either, as it would only be removed by the compiler's dead code
- * elimination.
- *
- * @note if implemented, this function is entirely platform-dependant, and does
- * not exist in common code.
- *
- * @param args see _mali_uk_va_to_mali_pa_s in "mali_utgard_uk_types.h"
- * @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
- */
-_mali_osk_errcode_t _mali_ukk_va_to_mali_pa( _mali_uk_va_to_mali_pa_s * args );
-
/** @} */ /* end group _mali_uk_memory */
* @param uargs see _mali_uk_pp_start_job_s in "mali_utgard_uk_types.h". Use _mali_osk_copy_from_user to retrieve data!
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_pp_start_job( void *ctx, _mali_uk_pp_start_job_s *uargs );
+_mali_osk_errcode_t _mali_ukk_pp_start_job(void *ctx, _mali_uk_pp_start_job_s *uargs);
/**
* @brief Issue a request to start new jobs on both Vertex Processor and Fragment Processor.
* @param uargs see _mali_uk_pp_and_gp_start_job_s in "mali_utgard_uk_types.h". Use _mali_osk_copy_from_user to retrieve data!
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_pp_and_gp_start_job( void *ctx, _mali_uk_pp_and_gp_start_job_s *uargs );
+_mali_osk_errcode_t _mali_ukk_pp_and_gp_start_job(void *ctx, _mali_uk_pp_and_gp_start_job_s *uargs);
/** @brief Returns the number of Fragment Processors in the system
*
* @param args see _mali_uk_get_pp_number_of_cores_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_get_pp_number_of_cores( _mali_uk_get_pp_number_of_cores_s *args );
+_mali_osk_errcode_t _mali_ukk_get_pp_number_of_cores(_mali_uk_get_pp_number_of_cores_s *args);
/** @brief Returns the version that all Fragment Processor cores are compatible with.
*
* @param args see _mali_uk_get_pp_core_version_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_get_pp_core_version( _mali_uk_get_pp_core_version_s *args );
+_mali_osk_errcode_t _mali_ukk_get_pp_core_version(_mali_uk_get_pp_core_version_s *args);
/** @brief Disable Write-back unit(s) on specified job
*
* @param uargs see _mali_uk_gp_start_job_s in "mali_utgard_uk_types.h". Use _mali_osk_copy_from_user to retrieve data!
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_gp_start_job( void *ctx, _mali_uk_gp_start_job_s *uargs );
+_mali_osk_errcode_t _mali_ukk_gp_start_job(void *ctx, _mali_uk_gp_start_job_s *uargs);
/** @brief Returns the number of Vertex Processors in the system.
*
* @param args see _mali_uk_get_gp_number_of_cores_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_get_gp_number_of_cores( _mali_uk_get_gp_number_of_cores_s *args );
+_mali_osk_errcode_t _mali_ukk_get_gp_number_of_cores(_mali_uk_get_gp_number_of_cores_s *args);
/** @brief Returns the version that all Vertex Processor cores are compatible with.
*
* @param args see _mali_uk_get_gp_core_version_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_get_gp_core_version( _mali_uk_get_gp_core_version_s *args );
+_mali_osk_errcode_t _mali_ukk_get_gp_core_version(_mali_uk_get_gp_core_version_s *args);
/** @brief Resume or abort suspended Vertex Processor jobs.
*
* @param args see _mali_uk_gp_suspend_response_s in "mali_utgard_uk_types.h"
* @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_gp_suspend_response( _mali_uk_gp_suspend_response_s *args );
+_mali_osk_errcode_t _mali_ukk_gp_suspend_response(_mali_uk_gp_suspend_response_s *args);
/** @} */ /* end group _mali_uk_gp */
/** @addtogroup _mali_uk_profiling U/K Timeline profiling module
* @{ */
-/** @brief Start recording profiling events.
- *
- * @param args see _mali_uk_profiling_start_s in "mali_utgard_uk_types.h"
- */
-_mali_osk_errcode_t _mali_ukk_profiling_start(_mali_uk_profiling_start_s *args);
-
/** @brief Add event to profiling buffer.
*
* @param args see _mali_uk_profiling_add_event_s in "mali_utgard_uk_types.h"
*/
_mali_osk_errcode_t _mali_ukk_profiling_add_event(_mali_uk_profiling_add_event_s *args);
-/** @brief Stop recording profiling events.
- *
- * @param args see _mali_uk_profiling_stop_s in "mali_utgard_uk_types.h"
- */
-_mali_osk_errcode_t _mali_ukk_profiling_stop(_mali_uk_profiling_stop_s *args);
-
-/** @brief Retrieve a recorded profiling event.
+/** @brief Return the total memory usage
*
- * @param args see _mali_uk_profiling_get_event_s in "mali_utgard_uk_types.h"
- */
-_mali_osk_errcode_t _mali_ukk_profiling_get_event(_mali_uk_profiling_get_event_s *args);
-
-/** @brief Clear recorded profiling events.
- *
- * @param args see _mali_uk_profiling_clear_s in "mali_utgard_uk_types.h"
+ * @param args see _mali_uk_profiling_memory_usage_get_s in "mali_utgard_uk_types.h"
+ * @return _MALI_OSK_ERR_OK on success, otherwise a suitable _mali_osk_errcode_t on failure.
*/
-_mali_osk_errcode_t _mali_ukk_profiling_clear(_mali_uk_profiling_clear_s *args);
+_mali_osk_errcode_t _mali_ukk_profiling_memory_usage_get(_mali_uk_profiling_memory_usage_get_s *args);
/** @} */ /* end group _mali_uk_profiling */
#endif
/**
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
-#include "mali_osk.h"
#include "mali_kernel_common.h"
+#include "mali_osk.h"
+#include "mali_ukk.h"
#include "mali_uk_types.h"
#include "mali_user_settings_db.h"
#include "mali_session.h"
for (i = 0; i < num_sessions_alloc; i++) {
notobjs[i] = _mali_osk_notification_create(_MALI_NOTIFICATION_SETTINGS_CHANGED,
- sizeof(_mali_uk_settings_changed_s));
+ sizeof(_mali_uk_settings_changed_s));
if (NULL != notobjs[i]) {
_mali_uk_settings_changed_s *data;
data = notobjs[i]->result_buffer;
/**
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_GPU_RESOURCES_MALI450_MP2_PMU(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCES_MALI450_MP2(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_PMU(base_addr + 0x2000) \
-
+
#define MALI_GPU_RESOURCES_MALI450_MP3(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_L2(base_addr + 0x10000) \
MALI_GPU_RESOURCE_GP_WITH_MMU(base_addr + 0x00000, gp_irq, base_addr + 0x03000, gp_mmu_irq) \
#define MALI_GPU_RESOURCES_MALI450_MP3_PMU(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCES_MALI450_MP3(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_PMU(base_addr + 0x2000) \
-
+
#define MALI_GPU_RESOURCES_MALI450_MP4(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_L2(base_addr + 0x10000) \
MALI_GPU_RESOURCE_GP_WITH_MMU(base_addr + 0x00000, gp_irq, base_addr + 0x03000, gp_mmu_irq) \
#define MALI_GPU_RESOURCES_MALI450_MP4_PMU(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCES_MALI450_MP4(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_PMU(base_addr + 0x2000) \
-
+
#define MALI_GPU_RESOURCES_MALI450_MP6(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_L2(base_addr + 0x10000) \
MALI_GPU_RESOURCE_GP_WITH_MMU(base_addr + 0x00000, gp_irq, base_addr + 0x03000, gp_mmu_irq) \
#define MALI_GPU_RESOURCES_MALI450_MP6_PMU(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCES_MALI450_MP6(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_PMU(base_addr + 0x2000) \
-
+
#define MALI_GPU_RESOURCES_MALI450_MP8(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp6_irq, pp6_mmu_irq, pp7_irq, pp7_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_L2(base_addr + 0x10000) \
MALI_GPU_RESOURCE_GP_WITH_MMU(base_addr + 0x00000, gp_irq, base_addr + 0x03000, gp_mmu_irq) \
#define MALI_GPU_RESOURCES_MALI450_MP8_PMU(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp6_irq, pp6_mmu_irq, pp7_irq, pp7_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCES_MALI450_MP8(base_addr, gp_irq, gp_mmu_irq, pp0_irq, pp0_mmu_irq, pp1_irq, pp1_mmu_irq, pp2_irq, pp2_mmu_irq, pp3_irq, pp3_mmu_irq, pp4_irq, pp4_mmu_irq, pp5_irq, pp5_mmu_irq, pp6_irq, pp6_mmu_irq, pp7_irq, pp7_mmu_irq, pp_bcast_irq) \
MALI_GPU_RESOURCE_PMU(base_addr + 0x2000) \
-
+
#define MALI_GPU_RESOURCE_L2(addr) \
{ \
.name = "Mali_L2", \
- .flags = IORESOURCE_MEM, \
- .start = addr, \
- .end = addr + 0x200, \
+ .flags = IORESOURCE_MEM, \
+ .start = addr, \
+ .end = addr + 0x200, \
},
#define MALI_GPU_RESOURCE_GP(gp_addr, gp_irq) \
{ \
.name = "Mali_GP", \
- .flags = IORESOURCE_MEM, \
- .start = gp_addr, \
- .end = gp_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = gp_addr, \
+ .end = gp_addr + 0x100, \
}, \
{ \
.name = "Mali_GP_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = gp_irq, \
- .end = gp_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = gp_irq, \
+ .end = gp_irq, \
}, \
-
+
#define MALI_GPU_RESOURCE_GP_WITH_MMU(gp_addr, gp_irq, gp_mmu_addr, gp_mmu_irq) \
{ \
.name = "Mali_GP", \
- .flags = IORESOURCE_MEM, \
- .start = gp_addr, \
- .end = gp_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = gp_addr, \
+ .end = gp_addr + 0x100, \
}, \
{ \
.name = "Mali_GP_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = gp_irq, \
- .end = gp_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = gp_irq, \
+ .end = gp_irq, \
}, \
{ \
.name = "Mali_GP_MMU", \
- .flags = IORESOURCE_MEM, \
- .start = gp_mmu_addr, \
- .end = gp_mmu_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = gp_mmu_addr, \
+ .end = gp_mmu_addr + 0x100, \
}, \
{ \
.name = "Mali_GP_MMU_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = gp_mmu_irq, \
- .end = gp_mmu_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = gp_mmu_irq, \
+ .end = gp_mmu_irq, \
},
#define MALI_GPU_RESOURCE_PP(pp_addr, pp_irq) \
{ \
.name = "Mali_PP", \
- .flags = IORESOURCE_MEM, \
- .start = pp_addr, \
- .end = pp_addr + 0x1100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pp_addr, \
+ .end = pp_addr + 0x1100, \
}, \
{ \
.name = "Mali_PP_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = pp_irq, \
- .end = pp_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = pp_irq, \
+ .end = pp_irq, \
}, \
-
+
#define MALI_GPU_RESOURCE_PP_WITH_MMU(id, pp_addr, pp_irq, pp_mmu_addr, pp_mmu_irq) \
{ \
.name = "Mali_PP" #id, \
- .flags = IORESOURCE_MEM, \
- .start = pp_addr, \
- .end = pp_addr + 0x1100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pp_addr, \
+ .end = pp_addr + 0x1100, \
}, \
{ \
.name = "Mali_PP" #id "_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = pp_irq, \
- .end = pp_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = pp_irq, \
+ .end = pp_irq, \
}, \
{ \
.name = "Mali_PP" #id "_MMU", \
- .flags = IORESOURCE_MEM, \
- .start = pp_mmu_addr, \
- .end = pp_mmu_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pp_mmu_addr, \
+ .end = pp_mmu_addr + 0x100, \
}, \
{ \
.name = "Mali_PP" #id "_MMU_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = pp_mmu_irq, \
- .end = pp_mmu_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = pp_mmu_irq, \
+ .end = pp_mmu_irq, \
},
#define MALI_GPU_RESOURCE_MMU(mmu_addr, mmu_irq) \
{ \
.name = "Mali_MMU", \
- .flags = IORESOURCE_MEM, \
- .start = mmu_addr, \
- .end = mmu_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = mmu_addr, \
+ .end = mmu_addr + 0x100, \
}, \
{ \
.name = "Mali_MMU_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = mmu_irq, \
- .end = mmu_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = mmu_irq, \
+ .end = mmu_irq, \
},
#define MALI_GPU_RESOURCE_PMU(pmu_addr) \
{ \
.name = "Mali_PMU", \
- .flags = IORESOURCE_MEM, \
- .start = pmu_addr, \
- .end = pmu_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pmu_addr, \
+ .end = pmu_addr + 0x100, \
},
#define MALI_GPU_RESOURCE_DMA(dma_addr) \
{ \
.name = "Mali_DMA", \
- .flags = IORESOURCE_MEM, \
- .start = dma_addr, \
- .end = dma_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = dma_addr, \
+ .end = dma_addr + 0x100, \
},
#define MALI_GPU_RESOURCE_DLBU(dlbu_addr) \
{ \
.name = "Mali_DLBU", \
- .flags = IORESOURCE_MEM, \
- .start = dlbu_addr, \
- .end = dlbu_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = dlbu_addr, \
+ .end = dlbu_addr + 0x100, \
},
#define MALI_GPU_RESOURCE_BCAST(bcast_addr) \
{ \
.name = "Mali_Broadcast", \
- .flags = IORESOURCE_MEM, \
- .start = bcast_addr, \
- .end = bcast_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = bcast_addr, \
+ .end = bcast_addr + 0x100, \
},
#define MALI_GPU_RESOURCE_PP_BCAST(pp_addr, pp_irq) \
{ \
.name = "Mali_PP_Broadcast", \
- .flags = IORESOURCE_MEM, \
- .start = pp_addr, \
- .end = pp_addr + 0x1100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pp_addr, \
+ .end = pp_addr + 0x1100, \
}, \
{ \
.name = "Mali_PP_Broadcast_IRQ", \
- .flags = IORESOURCE_IRQ, \
- .start = pp_irq, \
- .end = pp_irq, \
+ .flags = IORESOURCE_IRQ, \
+ .start = pp_irq, \
+ .end = pp_irq, \
}, \
-
+
#define MALI_GPU_RESOURCE_PP_MMU_BCAST(pp_mmu_bcast_addr) \
{ \
.name = "Mali_PP_MMU_Broadcast", \
- .flags = IORESOURCE_MEM, \
- .start = pp_mmu_bcast_addr, \
- .end = pp_mmu_bcast_addr + 0x100, \
+ .flags = IORESOURCE_MEM, \
+ .start = pp_mmu_bcast_addr, \
+ .end = pp_mmu_bcast_addr + 0x100, \
},
struct mali_gpu_utilization_data {
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_IOC_PROFILING_BASE (_MALI_UK_PROFILING_SUBSYSTEM + MALI_IOC_BASE)
#define MALI_IOC_VSYNC_BASE (_MALI_UK_VSYNC_SUBSYSTEM + MALI_IOC_BASE)
-#define MALI_IOC_WAIT_FOR_NOTIFICATION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_WAIT_FOR_NOTIFICATION, _mali_uk_wait_for_notification_s *)
-#define MALI_IOC_GET_API_VERSION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_API_VERSION, _mali_uk_get_api_version_s *)
-#define MALI_IOC_POST_NOTIFICATION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_POST_NOTIFICATION, _mali_uk_post_notification_s *)
-#define MALI_IOC_GET_USER_SETTING _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_USER_SETTING, _mali_uk_get_user_setting_s *)
-#define MALI_IOC_GET_USER_SETTINGS _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_USER_SETTINGS, _mali_uk_get_user_settings_s *)
-#define MALI_IOC_REQUEST_HIGH_PRIORITY _IOW (MALI_IOC_CORE_BASE, _MALI_UK_REQUEST_HIGH_PRIORITY, _mali_uk_request_high_priority_s *)
-#define MALI_IOC_TIMELINE_GET_LATEST_POINT _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_GET_LATEST_POINT, _mali_uk_timeline_get_latest_point_s *)
-#define MALI_IOC_TIMELINE_WAIT _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_WAIT, _mali_uk_timeline_wait_s *)
-#define MALI_IOC_TIMELINE_CREATE_SYNC_FENCE _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_CREATE_SYNC_FENCE, _mali_uk_timeline_create_sync_fence_s *)
-#define MALI_IOC_SOFT_JOB_START _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_SOFT_JOB_START, _mali_uk_soft_job_start_s *)
-#define MALI_IOC_SOFT_JOB_SIGNAL _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_SOFT_JOB_SIGNAL, _mali_uk_soft_job_signal_s *)
+#define MALI_IOC_WAIT_FOR_NOTIFICATION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_WAIT_FOR_NOTIFICATION, _mali_uk_wait_for_notification_s)
+#define MALI_IOC_GET_API_VERSION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_API_VERSION, u32)
+#define MALI_IOC_GET_API_VERSION_V2 _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_API_VERSION, _mali_uk_get_api_version_v2_s)
+#define MALI_IOC_POST_NOTIFICATION _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_POST_NOTIFICATION, _mali_uk_post_notification_s)
+#define MALI_IOC_GET_USER_SETTING _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_USER_SETTING, _mali_uk_get_user_setting_s)
+#define MALI_IOC_GET_USER_SETTINGS _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_GET_USER_SETTINGS, _mali_uk_get_user_settings_s)
+#define MALI_IOC_REQUEST_HIGH_PRIORITY _IOW (MALI_IOC_CORE_BASE, _MALI_UK_REQUEST_HIGH_PRIORITY, _mali_uk_request_high_priority_s)
+#define MALI_IOC_TIMELINE_GET_LATEST_POINT _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_GET_LATEST_POINT, _mali_uk_timeline_get_latest_point_s)
+#define MALI_IOC_TIMELINE_WAIT _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_WAIT, _mali_uk_timeline_wait_s)
+#define MALI_IOC_TIMELINE_CREATE_SYNC_FENCE _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_TIMELINE_CREATE_SYNC_FENCE, _mali_uk_timeline_create_sync_fence_s)
+#define MALI_IOC_SOFT_JOB_START _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_SOFT_JOB_START, _mali_uk_soft_job_start_s)
+#define MALI_IOC_SOFT_JOB_SIGNAL _IOWR(MALI_IOC_CORE_BASE, _MALI_UK_SOFT_JOB_SIGNAL, _mali_uk_soft_job_signal_s)
-#define MALI_IOC_MEM_MAP_EXT _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_MAP_EXT_MEM, _mali_uk_map_external_mem_s *)
-#define MALI_IOC_MEM_UNMAP_EXT _IOW (MALI_IOC_MEMORY_BASE, _MALI_UK_UNMAP_EXT_MEM, _mali_uk_unmap_external_mem_s *)
-#define MALI_IOC_MEM_ATTACH_DMA_BUF _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_ATTACH_DMA_BUF, _mali_uk_attach_dma_buf_s *)
-#define MALI_IOC_MEM_RELEASE_DMA_BUF _IOW(MALI_IOC_MEMORY_BASE, _MALI_UK_RELEASE_DMA_BUF, _mali_uk_release_dma_buf_s *)
-#define MALI_IOC_MEM_DMA_BUF_GET_SIZE _IOR(MALI_IOC_MEMORY_BASE, _MALI_UK_DMA_BUF_GET_SIZE, _mali_uk_dma_buf_get_size_s *)
-#define MALI_IOC_MEM_ATTACH_UMP _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_ATTACH_UMP_MEM, _mali_uk_attach_ump_mem_s *)
-#define MALI_IOC_MEM_RELEASE_UMP _IOW(MALI_IOC_MEMORY_BASE, _MALI_UK_RELEASE_UMP_MEM, _mali_uk_release_ump_mem_s *)
-#define MALI_IOC_MEM_QUERY_MMU_PAGE_TABLE_DUMP_SIZE _IOR (MALI_IOC_MEMORY_BASE, _MALI_UK_QUERY_MMU_PAGE_TABLE_DUMP_SIZE, _mali_uk_query_mmu_page_table_dump_size_s *)
-#define MALI_IOC_MEM_DUMP_MMU_PAGE_TABLE _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_DUMP_MMU_PAGE_TABLE, _mali_uk_dump_mmu_page_table_s *)
-#define MALI_IOC_MEM_WRITE_SAFE _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_MEM_WRITE_SAFE, _mali_uk_mem_write_safe_s *)
+#define MALI_IOC_MEM_MAP_EXT _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_MAP_EXT_MEM, _mali_uk_map_external_mem_s)
+#define MALI_IOC_MEM_UNMAP_EXT _IOW (MALI_IOC_MEMORY_BASE, _MALI_UK_UNMAP_EXT_MEM, _mali_uk_unmap_external_mem_s)
+#define MALI_IOC_MEM_ATTACH_DMA_BUF _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_ATTACH_DMA_BUF, _mali_uk_attach_dma_buf_s)
+#define MALI_IOC_MEM_RELEASE_DMA_BUF _IOW(MALI_IOC_MEMORY_BASE, _MALI_UK_RELEASE_DMA_BUF, _mali_uk_release_dma_buf_s)
+#define MALI_IOC_MEM_DMA_BUF_GET_SIZE _IOR(MALI_IOC_MEMORY_BASE, _MALI_UK_DMA_BUF_GET_SIZE, _mali_uk_dma_buf_get_size_s)
+#define MALI_IOC_MEM_ATTACH_UMP _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_ATTACH_UMP_MEM, _mali_uk_attach_ump_mem_s)
+#define MALI_IOC_MEM_RELEASE_UMP _IOW(MALI_IOC_MEMORY_BASE, _MALI_UK_RELEASE_UMP_MEM, _mali_uk_release_ump_mem_s)
+#define MALI_IOC_MEM_QUERY_MMU_PAGE_TABLE_DUMP_SIZE _IOR (MALI_IOC_MEMORY_BASE, _MALI_UK_QUERY_MMU_PAGE_TABLE_DUMP_SIZE, _mali_uk_query_mmu_page_table_dump_size_s)
+#define MALI_IOC_MEM_DUMP_MMU_PAGE_TABLE _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_DUMP_MMU_PAGE_TABLE, _mali_uk_dump_mmu_page_table_s)
+#define MALI_IOC_MEM_WRITE_SAFE _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_MEM_WRITE_SAFE, _mali_uk_mem_write_safe_s)
-#define MALI_IOC_PP_START_JOB _IOWR(MALI_IOC_PP_BASE, _MALI_UK_PP_START_JOB, _mali_uk_pp_start_job_s *)
-#define MALI_IOC_PP_AND_GP_START_JOB _IOWR(MALI_IOC_PP_BASE, _MALI_UK_PP_AND_GP_START_JOB, _mali_uk_pp_and_gp_start_job_s *)
-#define MALI_IOC_PP_NUMBER_OF_CORES_GET _IOR (MALI_IOC_PP_BASE, _MALI_UK_GET_PP_NUMBER_OF_CORES, _mali_uk_get_pp_number_of_cores_s *)
-#define MALI_IOC_PP_CORE_VERSION_GET _IOR (MALI_IOC_PP_BASE, _MALI_UK_GET_PP_CORE_VERSION, _mali_uk_get_pp_core_version_s * )
-#define MALI_IOC_PP_DISABLE_WB _IOW (MALI_IOC_PP_BASE, _MALI_UK_PP_DISABLE_WB, _mali_uk_pp_disable_wb_s * )
+#define MALI_IOC_PP_START_JOB _IOWR(MALI_IOC_PP_BASE, _MALI_UK_PP_START_JOB, _mali_uk_pp_start_job_s)
+#define MALI_IOC_PP_AND_GP_START_JOB _IOWR(MALI_IOC_PP_BASE, _MALI_UK_PP_AND_GP_START_JOB, _mali_uk_pp_and_gp_start_job_s)
+#define MALI_IOC_PP_NUMBER_OF_CORES_GET _IOR (MALI_IOC_PP_BASE, _MALI_UK_GET_PP_NUMBER_OF_CORES, _mali_uk_get_pp_number_of_cores_s)
+#define MALI_IOC_PP_CORE_VERSION_GET _IOR (MALI_IOC_PP_BASE, _MALI_UK_GET_PP_CORE_VERSION, _mali_uk_get_pp_core_version_s)
+#define MALI_IOC_PP_DISABLE_WB _IOW (MALI_IOC_PP_BASE, _MALI_UK_PP_DISABLE_WB, _mali_uk_pp_disable_wb_s)
-#define MALI_IOC_GP2_START_JOB _IOWR(MALI_IOC_GP_BASE, _MALI_UK_GP_START_JOB, _mali_uk_gp_start_job_s *)
-#define MALI_IOC_GP2_NUMBER_OF_CORES_GET _IOR (MALI_IOC_GP_BASE, _MALI_UK_GET_GP_NUMBER_OF_CORES, _mali_uk_get_gp_number_of_cores_s *)
-#define MALI_IOC_GP2_CORE_VERSION_GET _IOR (MALI_IOC_GP_BASE, _MALI_UK_GET_GP_CORE_VERSION, _mali_uk_get_gp_core_version_s *)
-#define MALI_IOC_GP2_SUSPEND_RESPONSE _IOW (MALI_IOC_GP_BASE, _MALI_UK_GP_SUSPEND_RESPONSE,_mali_uk_gp_suspend_response_s *)
+#define MALI_IOC_GP2_START_JOB _IOWR(MALI_IOC_GP_BASE, _MALI_UK_GP_START_JOB, _mali_uk_gp_start_job_s)
+#define MALI_IOC_GP2_NUMBER_OF_CORES_GET _IOR (MALI_IOC_GP_BASE, _MALI_UK_GET_GP_NUMBER_OF_CORES, _mali_uk_get_gp_number_of_cores_s)
+#define MALI_IOC_GP2_CORE_VERSION_GET _IOR (MALI_IOC_GP_BASE, _MALI_UK_GET_GP_CORE_VERSION, _mali_uk_get_gp_core_version_s)
+#define MALI_IOC_GP2_SUSPEND_RESPONSE _IOW (MALI_IOC_GP_BASE, _MALI_UK_GP_SUSPEND_RESPONSE,_mali_uk_gp_suspend_response_s)
-#define MALI_IOC_PROFILING_START _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_START, _mali_uk_profiling_start_s *)
-#define MALI_IOC_PROFILING_ADD_EVENT _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_ADD_EVENT, _mali_uk_profiling_add_event_s*)
-#define MALI_IOC_PROFILING_STOP _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_STOP, _mali_uk_profiling_stop_s *)
-#define MALI_IOC_PROFILING_GET_EVENT _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_GET_EVENT, _mali_uk_profiling_get_event_s *)
-#define MALI_IOC_PROFILING_CLEAR _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_CLEAR, _mali_uk_profiling_clear_s *)
-#define MALI_IOC_PROFILING_GET_CONFIG _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_GET_CONFIG, _mali_uk_get_user_settings_s *)
-#define MALI_IOC_PROFILING_REPORT_SW_COUNTERS _IOW (MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_REPORT_SW_COUNTERS, _mali_uk_sw_counters_report_s *)
+#define MALI_IOC_PROFILING_ADD_EVENT _IOWR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_ADD_EVENT, _mali_uk_profiling_add_event_s)
+#define MALI_IOC_PROFILING_REPORT_SW_COUNTERS _IOW (MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_REPORT_SW_COUNTERS, _mali_uk_sw_counters_report_s)
+#define MALI_IOC_PROFILING_MEMORY_USAGE_GET _IOR(MALI_IOC_PROFILING_BASE, _MALI_UK_PROFILING_MEMORY_USAGE_GET, _mali_uk_profiling_memory_usage_get_s)
-#define MALI_IOC_VSYNC_EVENT_REPORT _IOW (MALI_IOC_VSYNC_BASE, _MALI_UK_VSYNC_EVENT_REPORT, _mali_uk_vsync_event_report_s *)
-
-/* Deprecated ioctls */
-#define MALI_IOC_MEM_GET_BIG_BLOCK _IOWR(MALI_IOC_MEMORY_BASE, _MALI_UK_GET_BIG_BLOCK, void *)
-#define MALI_IOC_MEM_FREE_BIG_BLOCK _IOW (MALI_IOC_MEMORY_BASE, _MALI_UK_FREE_BIG_BLOCK, void *)
-#define MALI_IOC_MEM_INIT _IOR (MALI_IOC_MEMORY_BASE, _MALI_UK_INIT_MEM, void *)
-#define MALI_IOC_MEM_TERM _IOW (MALI_IOC_MEMORY_BASE, _MALI_UK_TERM_MEM, void *)
+#define MALI_IOC_VSYNC_EVENT_REPORT _IOW (MALI_IOC_VSYNC_BASE, _MALI_UK_VSYNC_EVENT_REPORT, _mali_uk_vsync_event_report_s)
#ifdef __cplusplus
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
MALI_PROFILING_EVENT_REASON_SINGLE_SW_EGL_CREATE_FENCE_SYNC = 60,
MALI_PROFILING_EVENT_REASON_SINGLE_SW_EGL_CREATE_NATIVE_FENCE_SYNC = 61,
MALI_PROFILING_EVENT_REASON_SINGLE_SW_EGL_FENCE_FLUSH = 62,
- MALI_PROFILING_EVENT_REASON_SINGLE_SW_EGL_FLUSH_SERVER_WAITS= 63,
+ MALI_PROFILING_EVENT_REASON_SINGLE_SW_EGL_FLUSH_SERVER_WAITS = 63,
} cinstr_profiling_event_reason_single_sw_t;
/**
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_MALI_UK_PP_SUBSYSTEM, /**< Fragment Processor Group of U/K calls */
_MALI_UK_GP_SUBSYSTEM, /**< Vertex Processor Group of U/K calls */
_MALI_UK_PROFILING_SUBSYSTEM, /**< Profiling Group of U/K calls */
- _MALI_UK_PMM_SUBSYSTEM, /**< Power Management Module Group of U/K calls */
_MALI_UK_VSYNC_SUBSYSTEM, /**< VSYNC Group of U/K calls */
} _mali_uk_subsystem_t;
_MALI_UK_INIT_MEM = 0, /**< _mali_ukk_init_mem() */
_MALI_UK_TERM_MEM, /**< _mali_ukk_term_mem() */
- _MALI_UK_GET_BIG_BLOCK, /**< _mali_ukk_get_big_block() */
- _MALI_UK_FREE_BIG_BLOCK, /**< _mali_ukk_free_big_block() */
_MALI_UK_MAP_MEM, /**< _mali_ukk_mem_mmap() */
_MALI_UK_UNMAP_MEM, /**< _mali_ukk_mem_munmap() */
_MALI_UK_QUERY_MMU_PAGE_TABLE_DUMP_SIZE, /**< _mali_ukk_mem_get_mmu_page_table_dump_size() */
_MALI_UK_RELEASE_UMP_MEM, /**< _mali_ukk_release_ump_mem() */
_MALI_UK_MAP_EXT_MEM, /**< _mali_uku_map_external_mem() */
_MALI_UK_UNMAP_EXT_MEM, /**< _mali_uku_unmap_external_mem() */
- _MALI_UK_VA_TO_MALI_PA, /**< _mali_uku_va_to_mali_pa() */
_MALI_UK_MEM_WRITE_SAFE, /**< _mali_uku_mem_write_safe() */
/** Common functions for each core */
/** Profiling functions */
- _MALI_UK_PROFILING_START = 0, /**< __mali_uku_profiling_start() */
- _MALI_UK_PROFILING_ADD_EVENT, /**< __mali_uku_profiling_add_event() */
- _MALI_UK_PROFILING_STOP, /**< __mali_uku_profiling_stop() */
- _MALI_UK_PROFILING_GET_EVENT, /**< __mali_uku_profiling_get_event() */
- _MALI_UK_PROFILING_CLEAR, /**< __mali_uku_profiling_clear() */
- _MALI_UK_PROFILING_GET_CONFIG, /**< __mali_uku_profiling_get_config() */
+ _MALI_UK_PROFILING_ADD_EVENT = 0, /**< __mali_uku_profiling_add_event() */
_MALI_UK_PROFILING_REPORT_SW_COUNTERS,/**< __mali_uku_profiling_report_sw_counters() */
+ _MALI_UK_PROFILING_MEMORY_USAGE_GET, /**< __mali_uku_profiling_memory_usage_get() */
/** VSYNC reporting fuctions */
_MALI_UK_VSYNC_EVENT_REPORT = 0, /**< _mali_ukk_vsync_event_report() */
-
} _mali_uk_functions;
-/** @brief Get the size necessary for system info
- *
- * @see _mali_ukk_get_system_info_size()
- */
-typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 size; /**< [out] size of buffer necessary to hold system information data, in bytes */
-} _mali_uk_get_system_info_size_s;
-
-
/** @defgroup _mali_uk_getsysteminfo U/K Get System Info
* @{ */
*/
typedef u32 _mali_core_version;
-/**
- * Enum values for the different modes the driver can be put in.
- * Normal is the default mode. The driver then uses a job queue and takes job objects from the clients.
- * Job completion is reported using the _mali_ukk_wait_for_notification call.
- * The driver blocks this io command until a job has completed or failed or a timeout occurs.
- *
- * The 'raw' mode is reserved for future expansion.
- */
-typedef enum _mali_driver_mode {
- _MALI_DRIVER_MODE_RAW = 1, /**< Reserved for future expansion */
- _MALI_DRIVER_MODE_NORMAL = 2 /**< Normal mode of operation */
-} _mali_driver_mode;
-
-/** @brief List of possible cores
- *
- * add new entries to the end of this enum */
-typedef enum _mali_core_type {
- _MALI_GP2 = 2, /**< MaliGP2 Programmable Vertex Processor */
- _MALI_200 = 5, /**< Mali200 Programmable Fragment Processor */
- _MALI_400_GP = 6, /**< Mali400 Programmable Vertex Processor */
- _MALI_400_PP = 7, /**< Mali400 Programmable Fragment Processor */
- /* insert new core here, do NOT alter the existing values */
-} _mali_core_type;
-
-
-/** @brief Capabilities of Memory Banks
- *
- * These may be used to restrict memory banks for certain uses. They may be
- * used when access is not possible (e.g. Bus does not support access to it)
- * or when access is possible but not desired (e.g. Access is slow).
- *
- * In the case of 'possible but not desired', there is no way of specifying
- * the flags as an optimization hint, so that the memory could be used as a
- * last resort.
- *
- * @see _mali_mem_info
- */
-typedef enum _mali_bus_usage {
-
- _MALI_PP_READABLE = (1<<0), /** Readable by the Fragment Processor */
- _MALI_PP_WRITEABLE = (1<<1), /** Writeable by the Fragment Processor */
- _MALI_GP_READABLE = (1<<2), /** Readable by the Vertex Processor */
- _MALI_GP_WRITEABLE = (1<<3), /** Writeable by the Vertex Processor */
- _MALI_CPU_READABLE = (1<<4), /** Readable by the CPU */
- _MALI_CPU_WRITEABLE = (1<<5), /** Writeable by the CPU */
- _MALI_GP_L2_ALLOC = (1<<6), /** GP allocate mali L2 cache lines*/
- _MALI_MMU_READABLE = _MALI_PP_READABLE | _MALI_GP_READABLE, /** Readable by the MMU (including all cores behind it) */
- _MALI_MMU_WRITEABLE = _MALI_PP_WRITEABLE | _MALI_GP_WRITEABLE, /** Writeable by the MMU (including all cores behind it) */
-} _mali_bus_usage;
-
-typedef enum mali_memory_cache_settings {
- MALI_CACHE_STANDARD = 0,
- MALI_CACHE_GP_READ_ALLOCATE = 1,
-} mali_memory_cache_settings ;
-
-
-/** @brief Information about the Mali Memory system
- *
- * Information is stored in a linked list, which is stored entirely in the
- * buffer pointed to by the system_info member of the
- * _mali_uk_get_system_info_s arguments provided to _mali_ukk_get_system_info()
- *
- * Each element of the linked list describes a single Mali Memory bank.
- * Each allocation can only come from one bank, and will not cross multiple
- * banks.
- *
- * On Mali-MMU systems, there is only one bank, which describes the maximum
- * possible address range that could be allocated (which may be much less than
- * the available physical memory)
- *
- * The flags member describes the capabilities of the memory. It is an error
- * to attempt to build a job for a particular core (PP or GP) when the memory
- * regions used do not have the capabilities for supporting that core. This
- * would result in a job abort from the Device Driver.
- *
- * For example, it is correct to build a PP job where read-only data structures
- * are taken from a memory with _MALI_PP_READABLE set and
- * _MALI_PP_WRITEABLE clear, and a framebuffer with _MALI_PP_WRITEABLE set and
- * _MALI_PP_READABLE clear. However, it would be incorrect to use a framebuffer
- * where _MALI_PP_WRITEABLE is clear.
- */
-typedef struct _mali_mem_info {
- u32 size; /**< Size of the memory bank in bytes */
- _mali_bus_usage flags; /**< Capabilitiy flags of the memory */
- u32 maximum_order_supported; /**< log2 supported size */
- u32 identifier; /* mali_memory_cache_settings cache_settings; */
- struct _mali_mem_info * next; /**< Next List Link */
-} _mali_mem_info;
-
/** @} */ /* end group _mali_uk_core */
} _maligp_job_suspended_response_code;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 cookie; /**< [in] cookie from the _mali_uk_gp_job_suspended_s notification */
_maligp_job_suspended_response_code code; /**< [in] abort or resume response code, see \ref _maligp_job_suspended_response_code */
u32 arguments[2]; /**< [in] 0 when aborting a job. When resuming a job, the Mali start and end address for a new heap to resume the job with */
/** @defgroup _mali_uk_gpstartjob_s Vertex Processor Start Job
* @{ */
-/** @brief Status indicating the result of starting a Vertex or Fragment processor job */
-typedef enum {
- _MALI_UK_START_JOB_STARTED, /**< Job started */
- _MALI_UK_START_JOB_NOT_STARTED_DO_REQUEUE /**< Job could not be started at this time. Try starting the job again */
-} _mali_uk_start_job_status;
-
/** @brief Status indicating the result of the execution of a Vertex or Fragment processor job */
-
typedef enum {
- _MALI_UK_JOB_STATUS_END_SUCCESS = 1<<(16+0),
- _MALI_UK_JOB_STATUS_END_OOM = 1<<(16+1),
- _MALI_UK_JOB_STATUS_END_ABORT = 1<<(16+2),
- _MALI_UK_JOB_STATUS_END_TIMEOUT_SW = 1<<(16+3),
- _MALI_UK_JOB_STATUS_END_HANG = 1<<(16+4),
- _MALI_UK_JOB_STATUS_END_SEG_FAULT = 1<<(16+5),
- _MALI_UK_JOB_STATUS_END_ILLEGAL_JOB = 1<<(16+6),
- _MALI_UK_JOB_STATUS_END_UNKNOWN_ERR = 1<<(16+7),
- _MALI_UK_JOB_STATUS_END_SHUTDOWN = 1<<(16+8),
- _MALI_UK_JOB_STATUS_END_SYSTEM_UNUSABLE = 1<<(16+9)
+ _MALI_UK_JOB_STATUS_END_SUCCESS = 1 << (16 + 0),
+ _MALI_UK_JOB_STATUS_END_OOM = 1 << (16 + 1),
+ _MALI_UK_JOB_STATUS_END_ABORT = 1 << (16 + 2),
+ _MALI_UK_JOB_STATUS_END_TIMEOUT_SW = 1 << (16 + 3),
+ _MALI_UK_JOB_STATUS_END_HANG = 1 << (16 + 4),
+ _MALI_UK_JOB_STATUS_END_SEG_FAULT = 1 << (16 + 5),
+ _MALI_UK_JOB_STATUS_END_ILLEGAL_JOB = 1 << (16 + 6),
+ _MALI_UK_JOB_STATUS_END_UNKNOWN_ERR = 1 << (16 + 7),
+ _MALI_UK_JOB_STATUS_END_SHUTDOWN = 1 << (16 + 8),
+ _MALI_UK_JOB_STATUS_END_SYSTEM_UNUSABLE = 1 << (16 + 9)
} _mali_uk_job_status;
#define MALIGP2_NUM_REGS_FRAME (6)
*
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 user_job_ptr; /**< [in] identifier for the job in user space, a @c mali_gp_job_info* */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 user_job_ptr; /**< [in] identifier for the job in user space, a @c mali_gp_job_info* */
u32 priority; /**< [in] job priority. A lower number means higher priority */
u32 frame_registers[MALIGP2_NUM_REGS_FRAME]; /**< [in] core specific registers associated with this job */
u32 perf_counter_flag; /**< [in] bitmask indicating which performance counters to enable, see \ref _MALI_PERFORMANCE_COUNTER_FLAG_SRC0_ENABLE and related macro definitions */
u32 frame_builder_id; /**< [in] id of the originating frame builder */
u32 flush_id; /**< [in] flush id within the originating frame builder */
_mali_uk_fence_t fence; /**< [in] fence this job must wait on */
- u32 *timeline_point_ptr; /**< [in,out] pointer to location where point on gp timeline for this job will be written */
+ u64 timeline_point_ptr; /**< [in,out] pointer to u32: location where point on gp timeline for this job will be written */
} _mali_uk_gp_start_job_s;
#define _MALI_PERFORMANCE_COUNTER_FLAG_SRC0_ENABLE (1<<0) /**< Enable performance counter SRC0 for a job */
/** @} */ /* end group _mali_uk_gpstartjob_s */
typedef struct {
- u32 user_job_ptr; /**< [out] identifier for the job in user space */
+ u64 user_job_ptr; /**< [out] identifier for the job in user space */
_mali_uk_job_status status; /**< [out] status of finished job */
u32 heap_current_addr; /**< [out] value of the GP PLB PL heap start address register */
u32 perf_counter0; /**< [out] value of performance counter 0 (see ARM DDI0415A) */
} _mali_uk_gp_job_finished_s;
typedef struct {
- u32 user_job_ptr; /**< [out] identifier for the job in user space */
+ u64 user_job_ptr; /**< [out] identifier for the job in user space */
u32 cookie; /**< [out] identifier for the core in kernel space on which the job stalled */
} _mali_uk_gp_job_suspended_s;
*
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 user_job_ptr; /**< [in] identifier for the job in user space */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 user_job_ptr; /**< [in] identifier for the job in user space */
u32 priority; /**< [in] job priority. A lower number means higher priority */
u32 frame_registers[_MALI_PP_MAX_FRAME_REGISTERS]; /**< [in] core specific registers associated with first sub job, see ARM DDI0415A */
u32 frame_registers_addr_frame[_MALI_PP_MAX_SUB_JOBS - 1]; /**< [in] ADDR_FRAME registers for sub job 1-7 */
u32 wb1_registers[_MALI_PP_MAX_WB_REGISTERS];
u32 wb2_registers[_MALI_PP_MAX_WB_REGISTERS];
u32 dlbu_registers[_MALI_DLBU_MAX_REGISTERS]; /**< [in] Dynamic load balancing unit registers */
- u32 num_cores; /**< [in] Number of cores to set up (valid range: 1-4) */
+ u32 num_cores; /**< [in] Number of cores to set up (valid range: 1-8(M450) or 4(M400)) */
u32 perf_counter_flag; /**< [in] bitmask indicating which performance counters to enable, see \ref _MALI_PERFORMANCE_COUNTER_FLAG_SRC0_ENABLE and related macro definitions */
u32 perf_counter_src0; /**< [in] source id for performance counter 0 (see ARM DDI0415A, Table 3-60) */
u32 perf_counter_src1; /**< [in] source id for performance counter 1 (see ARM DDI0415A, Table 3-60) */
u32 tilesy; /**< [in] number of tiles in y direction (needed for reading the heatmap memory) */
u32 heatmap_mem; /**< [in] memory address to store counter values per tile (aka heatmap) */
u32 num_memory_cookies; /**< [in] number of memory cookies attached to job */
- u32 *memory_cookies; /**< [in] memory cookies attached to job */
+ u64 memory_cookies; /**< [in] pointer to array of u32 memory cookies attached to job */
_mali_uk_fence_t fence; /**< [in] fence this job must wait on */
- u32 *timeline_point_ptr; /**< [in,out] pointer to location where point on pp timeline for this job will be written */
+ u64 timeline_point_ptr; /**< [in,out] pointer to location of u32 where point on pp timeline for this job will be written */
} _mali_uk_pp_start_job_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- _mali_uk_gp_start_job_s *gp_args; /**< [in,out] GP uk arguments (see _mali_uk_gp_start_job_s) */
- _mali_uk_pp_start_job_s *pp_args; /**< [in,out] PP uk arguments (see _mali_uk_pp_start_job_s) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 gp_args; /**< [in,out] GP uk arguments (see _mali_uk_gp_start_job_s) */
+ u64 pp_args; /**< [in,out] PP uk arguments (see _mali_uk_pp_start_job_s) */
} _mali_uk_pp_and_gp_start_job_s;
/** @} */ /* end group _mali_uk_ppstartjob_s */
typedef struct {
- u32 user_job_ptr; /**< [out] identifier for the job in user space */
+ u64 user_job_ptr; /**< [out] identifier for the job in user space */
_mali_uk_job_status status; /**< [out] status of finished job */
u32 perf_counter0[_MALI_PP_MAX_SUB_JOBS]; /**< [out] value of perfomance counter 0 (see ARM DDI0415A), one for each sub job */
u32 perf_counter1[_MALI_PP_MAX_SUB_JOBS]; /**< [out] value of perfomance counter 1 (see ARM DDI0415A), one for each sub job */
} _mali_uk_pp_job_wbx_flag;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 fb_id; /**< [in] Frame builder ID of job to disable WB units for */
u32 wb0_memory;
u32 wb1_memory;
* @{ */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 type; /**< [in] type of soft job */
- u32 user_job; /**< [in] identifier for the job in user space */
- u32 *job_id_ptr; /**< [in,out] pointer to location where job id will be written */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 user_job; /**< [in] identifier for the job in user space */
+ u64 job_id_ptr; /**< [in,out] pointer to location of u32 where job id will be written */
_mali_uk_fence_t fence; /**< [in] fence this job must wait on */
u32 point; /**< [out] point on soft timeline for this job */
+ u32 type; /**< [in] type of soft job */
} _mali_uk_soft_job_start_s;
typedef struct {
- u32 user_job; /**< [out] identifier for the job in user space */
+ u64 user_job; /**< [out] identifier for the job in user space */
} _mali_uk_soft_job_activated_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 job_id; /**< [in] id for soft job */
} _mali_uk_soft_job_signal_s;
typedef enum {
/** core notifications */
- _MALI_NOTIFICATION_CORE_SHUTDOWN_IN_PROGRESS = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x20,
- _MALI_NOTIFICATION_APPLICATION_QUIT = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x40,
- _MALI_NOTIFICATION_SETTINGS_CHANGED = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x80,
- _MALI_NOTIFICATION_SOFT_ACTIVATED = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x100,
+ _MALI_NOTIFICATION_CORE_SHUTDOWN_IN_PROGRESS = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x20,
+ _MALI_NOTIFICATION_APPLICATION_QUIT = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x40,
+ _MALI_NOTIFICATION_SETTINGS_CHANGED = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x80,
+ _MALI_NOTIFICATION_SOFT_ACTIVATED = (_MALI_UK_CORE_SUBSYSTEM << 16) | 0x100,
/** Fragment Processor notifications */
- _MALI_NOTIFICATION_PP_FINISHED = (_MALI_UK_PP_SUBSYSTEM << 16) | 0x10,
- _MALI_NOTIFICATION_PP_NUM_CORE_CHANGE = (_MALI_UK_PP_SUBSYSTEM << 16) | 0x20,
+ _MALI_NOTIFICATION_PP_FINISHED = (_MALI_UK_PP_SUBSYSTEM << 16) | 0x10,
+ _MALI_NOTIFICATION_PP_NUM_CORE_CHANGE = (_MALI_UK_PP_SUBSYSTEM << 16) | 0x20,
/** Vertex Processor notifications */
- _MALI_NOTIFICATION_GP_FINISHED = (_MALI_UK_GP_SUBSYSTEM << 16) | 0x10,
- _MALI_NOTIFICATION_GP_STALLED = (_MALI_UK_GP_SUBSYSTEM << 16) | 0x20,
+ _MALI_NOTIFICATION_GP_FINISHED = (_MALI_UK_GP_SUBSYSTEM << 16) | 0x10,
+ _MALI_NOTIFICATION_GP_STALLED = (_MALI_UK_GP_SUBSYSTEM << 16) | 0x20,
} _mali_uk_notification_type;
/* See mali_user_settings_db.c */
extern const char *_mali_uk_user_setting_descriptions[];
#define _MALI_UK_USER_SETTING_DESCRIPTIONS \
-{ \
- "sw_events_enable", \
- "colorbuffer_capture_enable", \
- "depthbuffer_capture_enable", \
- "stencilbuffer_capture_enable", \
- "per_tile_counters_enable", \
- "buffer_capture_compositor", \
- "buffer_capture_window", \
- "buffer_capture_other", \
- "buffer_capture_n_frames", \
- "buffer_capture_resize_factor", \
- "sw_counters_enable", \
-};
+ { \
+ "sw_events_enable", \
+ "colorbuffer_capture_enable", \
+ "depthbuffer_capture_enable", \
+ "stencilbuffer_capture_enable", \
+ "per_tile_counters_enable", \
+ "buffer_capture_compositor", \
+ "buffer_capture_window", \
+ "buffer_capture_other", \
+ "buffer_capture_n_frames", \
+ "buffer_capture_resize_factor", \
+ "sw_counters_enable", \
+ };
/** @brief struct to hold the value to a particular setting as seen in the kernel space
*/
* when the polygon list builder unit has run out of memory.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_notification_type type; /**< [out] Type of notification available */
union {
_mali_uk_gp_job_suspended_s gp_job_suspended;/**< [out] Notification data for _MALI_NOTIFICATION_GP_STALLED notification type */
* This is used to send a quit message to the callback thread.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_notification_type type; /**< [in] Type of notification to post */
} _mali_uk_post_notification_s;
* The 16bit integer is stored twice in a 32bit integer
* For example, for version 1 the value would be 0x00010001
*/
-#define _MALI_API_VERSION 401
+#define _MALI_API_VERSION 600
#define _MALI_UK_API_VERSION _MAKE_VERSION_ID(_MALI_API_VERSION)
/**
* of the interface may be backwards compatible.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u32 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_api_version version; /**< [in,out] API version of user-side interface. */
int compatible; /**< [out] @c 1 when @version is compatible, @c 0 otherwise */
} _mali_uk_get_api_version_s;
+
+/** @brief Arguments for _mali_uk_get_api_version_v2()
+ *
+ * The user-side interface version must be written into the version member,
+ * encoded using _MAKE_VERSION_ID(). It will be compared to the API version of
+ * the kernel-side interface.
+ *
+ * On successful return, the version member will be the API version of the
+ * kernel-side interface. _MALI_UK_API_VERSION macro defines the current version
+ * of the API.
+ *
+ * The compatible member must be checked to see if the version of the user-side
+ * interface is compatible with the kernel-side interface, since future versions
+ * of the interface may be backwards compatible.
+ */
+typedef struct {
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ _mali_uk_api_version version; /**< [in,out] API version of user-side interface. */
+ int compatible; /**< [out] @c 1 when @version is compatible, @c 0 otherwise */
+} _mali_uk_get_api_version_v2_s;
+
/** @} */ /* end group _mali_uk_getapiversion_s */
/** @defgroup _mali_uk_get_user_settings_s Get user space settings */
*
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 settings[_MALI_UK_USER_SETTING_MAX]; /**< [out] The values for all settings */
} _mali_uk_get_user_settings_s;
/** @brief struct to hold the value of a particular setting from the user space within a given context
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_user_setting_t setting; /**< [in] setting to get */
u32 value; /**< [out] value of setting */
} _mali_uk_get_user_setting_s;
/** @brief Arguments for _mali_ukk_request_high_priority() */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
} _mali_uk_request_high_priority_s;
/** @} */ /* end group _mali_uk_core */
#define _MALI_MAP_EXTERNAL_MAP_GUARD_PAGE (1<<0)
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 phys_addr; /**< [in] physical address */
u32 size; /**< [in] size */
u32 mali_address; /**< [in] mali address to map the physical memory to */
} _mali_uk_map_external_mem_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 cookie; /**< [out] identifier for mapped memory object in kernel space */
} _mali_uk_unmap_external_mem_s;
/** @note This is identical to _mali_uk_map_external_mem_s above, however phys_addr is replaced by memory descriptor */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 mem_fd; /**< [in] Memory descriptor */
u32 size; /**< [in] size */
u32 mali_address; /**< [in] mali address to map the physical memory to */
} _mali_uk_attach_dma_buf_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 mem_fd; /**< [in] Memory descriptor */
u32 size; /**< [out] size */
} _mali_uk_dma_buf_get_size_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 cookie; /**< [in] identifier for mapped memory object in kernel space */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 cookie; /**< [in] identifier for mapped memory object in kernel space */
} _mali_uk_release_dma_buf_s;
/** @note This is identical to _mali_uk_map_external_mem_s above, however phys_addr is replaced by secure_id */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 secure_id; /**< [in] secure id */
u32 size; /**< [in] size */
u32 mali_address; /**< [in] mali address to map the physical memory to */
} _mali_uk_attach_ump_mem_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 cookie; /**< [in] identifier for mapped memory object in kernel space */
} _mali_uk_release_ump_mem_s;
-/** @brief Arguments for _mali_ukk_va_to_mali_pa()
- *
- * if size is zero or not a multiple of the system's page size, it will be
- * rounded up to the next multiple of the page size. This will occur before
- * any other use of the size parameter.
- *
- * if va is not PAGE_SIZE aligned, it will be rounded down to the next page
- * boundary.
- *
- * The range (va) to ((u32)va)+(size-1) inclusive will be checked for physical
- * contiguity.
- *
- * The implementor will check that the entire physical range is allowed to be mapped
- * into user-space.
- *
- * Failure will occur if either of the above are not satisfied.
- *
- * Otherwise, the physical base address of the range is returned through pa,
- * va is updated to be page aligned, and size is updated to be a non-zero
- * multiple of the system's pagesize.
- */
-typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- void *va; /**< [in,out] Virtual address of the start of the range */
- u32 pa; /**< [out] Physical base address of the range */
- u32 size; /**< [in,out] Size of the range, in bytes. */
-} _mali_uk_va_to_mali_pa_s;
-
/**
* @brief Arguments for _mali_uk[uk]_mem_write_safe()
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- const void *src; /**< [in] Pointer to source data */
- void *dest; /**< [in] Destination Mali buffer */
- u32 size; /**< [in,out] Number of bytes to write/copy on input, number of bytes actually written/copied on output */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 src; /**< [in] Pointer to source data */
+ u64 dest; /**< [in] Destination Mali buffer */
+ u32 size; /**< [in,out] Number of bytes to write/copy on input, number of bytes actually written/copied on output */
} _mali_uk_mem_write_safe_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 size; /**< [out] size of MMU page table information (registers + page tables) */
} _mali_uk_query_mmu_page_table_dump_size_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 size; /**< [in] size of buffer to receive mmu page table information */
- void *buffer; /**< [in,out] buffer to receive mmu page table information */
+ u64 buffer; /**< [in,out] buffer to receive mmu page table information */
u32 register_writes_size; /**< [out] size of MMU register dump */
- u32 *register_writes; /**< [out] pointer within buffer where MMU register dump is stored */
+ u64 register_writes; /**< [out] pointer within buffer where MMU register dump is stored */
u32 page_table_dump_size; /**< [out] size of MMU page table dump */
- u32 *page_table_dump; /**< [out] pointer within buffer where MMU page table dump is stored */
+ u64 page_table_dump; /**< [out] pointer within buffer where MMU page table dump is stored */
} _mali_uk_dump_mmu_page_table_s;
/** @} */ /* end group _mali_uk_memory */
* will contain the number of Fragment Processor cores in the system.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 number_of_total_cores; /**< [out] Total number of Fragment Processor cores in the system */
u32 number_of_enabled_cores; /**< [out] Number of enabled Fragment Processor cores */
} _mali_uk_get_pp_number_of_cores_s;
* the version that all Fragment Processor cores are compatible with.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_core_version version; /**< [out] version returned from core, see \ref _mali_core_version */
+ u32 padding;
} _mali_uk_get_pp_core_version_s;
/** @} */ /* end group _mali_uk_pp */
* will contain the number of Vertex Processor cores in the system.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 number_of_cores; /**< [out] number of Vertex Processor cores in the system */
} _mali_uk_get_gp_number_of_cores_s;
* the version that all Vertex Processor cores are compatible with.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_core_version version; /**< [out] version returned from core, see \ref _mali_core_version */
} _mali_uk_get_gp_core_version_s;
-typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 limit; /**< [in,out] The desired limit for number of events to record on input, actual limit on output */
-} _mali_uk_profiling_start_s;
+/** @} */ /* end group _mali_uk_gp */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 event_id; /**< [in] event id to register (see enum mali_profiling_events for values) */
u32 data[5]; /**< [in] event specific data */
} _mali_uk_profiling_add_event_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 count; /**< [out] The number of events sampled */
-} _mali_uk_profiling_stop_s;
-
-typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32 index; /**< [in] which index to get (starting at zero) */
- u64 timestamp; /**< [out] timestamp of event */
- u32 event_id; /**< [out] event id of event (see enum mali_profiling_events for values) */
- u32 data[5]; /**< [out] event specific data */
-} _mali_uk_profiling_get_event_s;
-
-typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
-} _mali_uk_profiling_clear_s;
-
-/** @} */ /* end group _mali_uk_gp */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u32 memory_usage; /**< [out] total memory usage */
+} _mali_uk_profiling_memory_usage_get_s;
/** @addtogroup _mali_uk_memory U/K Memory
* implementation of the U/K interface. Its value must be zero.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
void *mapping; /**< [out] Returns user-space virtual address for the mapping */
u32 size; /**< [in] Size of the requested mapping */
u32 phys_addr; /**< [in] Physical address - could be offset, depending on caller+callee convention */
u32 cookie; /**< [out] Returns a cookie for use in munmap calls */
- void *uku_private; /**< [in] User-side Private word used by U/K interface */
- void *ukk_private; /**< [in] Kernel-side Private word used by U/K interface */
- mali_memory_cache_settings cache_settings; /**< [in] Option to set special cache flags, tuning L2 efficency */
} _mali_uk_mem_mmap_s;
/** @brief Arguments to _mali_ukk_mem_munmap()
* originally obtained range, or to unmap more than was originally obtained.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
void *mapping; /**< [in] The mapping returned from mmap call */
u32 size; /**< [in] The size passed to mmap call */
u32 cookie; /**< [in] Cookie from mmap call */
*
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_vsync_event event; /**< [in] VSYNCH event type */
} _mali_uk_vsync_event_report_s;
* Values recorded for each of the software counters during a single renderpass.
*/
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
- u32* counters; /**< [in] The array of counter values */
- u32 num_counters; /**< [in] The number of elements in counters array */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 counters; /**< [in] The array of u32 counter values */
+ u32 num_counters; /**< [in] The number of elements in counters array */
} _mali_uk_sw_counters_report_s;
/** @} */ /* end group _mali_uk_sw_counters_report */
* @{ */
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
u32 timeline; /**< [in] timeline id */
u32 point; /**< [out] latest point on timeline */
} _mali_uk_timeline_get_latest_point_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_fence_t fence; /**< [in] fence */
u32 timeout; /**< [in] timeout (0 for no wait, -1 for blocking) */
u32 status; /**< [out] status of fence (1 if signaled, 0 if timeout) */
} _mali_uk_timeline_wait_s;
typedef struct {
- void *ctx; /**< [in,out] user-kernel context (trashed on output) */
+ u64 ctx; /**< [in,out] user-kernel context (trashed on output) */
_mali_uk_fence_t fence; /**< [in] mali fence to create linux sync fence from */
s32 sync_fd; /**< [out] file descriptor for new linux sync fence */
} _mali_uk_timeline_create_sync_fence_s;
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/**
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/**
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_kernel_license.h"
#include <linux/platform_device.h>
#include <linux/miscdevice.h>
+#include <linux/bug.h>
#include <linux/mali/mali_utgard.h>
#include "mali_kernel_common.h"
#include "mali_session.h"
/* Ask Linux to create the tracepoints */
#define CREATE_TRACE_POINTS
#include "mali_linux_trace.h"
+
+EXPORT_TRACEPOINT_SYMBOL_GPL(mali_timeline_event);
+EXPORT_TRACEPOINT_SYMBOL_GPL(mali_hw_counter);
+EXPORT_TRACEPOINT_SYMBOL_GPL(mali_sw_counters);
#endif /* CONFIG_TRACEPOINTS */
/* from the __malidrv_build_info.c file that is generated during build */
#endif
/* Linux power management operations provided by the Mali device driver */
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29))
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 29))
struct pm_ext_ops mali_dev_ext_pm_ops = {
.base =
{
static struct platform_driver mali_platform_driver = {
.probe = mali_probe,
.remove = mali_remove,
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29))
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 29))
.pm = &mali_dev_ext_pm_ops,
#endif
.driver =
.name = MALI_GPU_NAME_UTGARD,
.owner = THIS_MODULE,
.bus = &platform_bus_type,
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,29))
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 29))
.pm = &mali_dev_pm_ops,
#endif
#else
.ioctl = mali_ioctl,
#endif
+ .compat_ioctl = mali_ioctl,
.mmap = mali_mmap
};
/* See B4.1.117 PMCR, Performance Monitors Control Register. Writing to p15, c9, c12, 0 */
- write_value = 1<<0; /* Bit 0 set. Enable counters */
+ write_value = 1 << 0; /* Bit 0 set. Enable counters */
if (reset) {
- write_value |= 1<<1; /* Reset event counters */
- write_value |= 1<<2; /* Reset cycle counter */
+ write_value |= 1 << 1; /* Reset event counters */
+ write_value |= 1 << 2; /* Reset cycle counter */
}
if (enable_divide_by_64) {
- write_value |= 1<<3; /* Enable the Clock divider by 64 */
+ write_value |= 1 << 3; /* Enable the Clock divider by 64 */
}
- write_value |= 1<<4; /* Export enable. Not needed */
- asm volatile ("MCR p15, 0, %0, c9, c12, 0\t\n" :: "r"(write_value ));
+ write_value |= 1 << 4; /* Export enable. Not needed */
+ asm volatile("MCR p15, 0, %0, c9, c12, 0\t\n" :: "r"(write_value));
/* PMOVSR Overflow Flag Status Register - Clear Clock and Event overflows */
- asm volatile ("MCR p15, 0, %0, c9, c12, 3\t\n" :: "r"(0x8000000f));
+ asm volatile("MCR p15, 0, %0, c9, c12, 3\t\n" :: "r"(0x8000000f));
/* See B4.1.124 PMUSERENR - setting p15 c9 c14 to 1" */
/* User mode access to the Performance Monitors enabled. */
/* Lets User space read cpu clock cycles */
- asm volatile( "mcr p15, 0, %0, c9, c14, 0" :: "r"(1) );
+ asm volatile("mcr p15, 0, %0, c9, c14, 0" :: "r"(1));
}
/** A timer function that configures the cycle clock counter on current CPU.
- The function \a mali_init_cpu_time_counters_on_all_cpus sets up this function
- to trigger on all Cpus during module load. */
+ * The function \a mali_init_cpu_time_counters_on_all_cpus sets up this
+ * function to trigger on all Cpus during module load.
+ */
static void mali_init_cpu_clock_timer_func(unsigned long data)
{
int reset_counters, enable_divide_clock_counter_by_64;
MALI_IGNORE(data);
- reset_counters= 1;
+ reset_counters = 1;
enable_divide_clock_counter_by_64 = 0;
mali_init_cpu_time_counters(reset_counters, enable_divide_clock_counter_by_64);
}
/** A timer functions for storing current time on all cpus.
- Used for checking if the clocks have similar values or if they are drifting. */
+ * Used for checking if the clocks have similar values or if they are drifting.
+ */
static void mali_print_cpu_clock_timer_func(unsigned long data)
{
int current_cpu = raw_smp_processor_id();
MALI_IGNORE(data);
sample0 = mali_get_cpu_cyclecount();
- if ( current_cpu<8 ) {
+ if (current_cpu < 8) {
mali_cpu_clock_last_value[current_cpu] = sample0;
}
}
/** Init the performance registers on all CPUs to count clock cycles.
- For init \a print_only should be 0.
- If \a print_only is 1, it will intead print the current clock value of all CPUs.*/
+ * For init \a print_only should be 0.
+ * If \a print_only is 1, it will intead print the current clock value of all CPUs.
+ */
void mali_init_cpu_time_counters_on_all_cpus(int print_only)
{
int i = 0;
jiffies_wait = 2;
jiffies_trigger = jiffies + jiffies_wait;
- for ( i=0 ; i < 8 ; i++ ) {
+ for (i = 0 ; i < 8 ; i++) {
init_timer(&mali_init_cpu_clock_timers[i]);
if (print_only) mali_init_cpu_clock_timers[i].function = mali_print_cpu_clock_timer_func;
else mali_init_cpu_clock_timers[i].function = mali_init_cpu_clock_timer_func;
mali_init_cpu_clock_timers[i].expires = jiffies_trigger ;
}
cpu_number = cpumask_first(cpu_online_mask);
- for ( i=0 ; i < 8 ; i++ ) {
+ for (i = 0 ; i < 8 ; i++) {
int next_cpu;
add_timer_on(&mali_init_cpu_clock_timers[i], cpu_number);
next_cpu = cpumask_next(cpu_number, cpu_online_mask);
cpu_number = next_cpu;
}
- while (jiffies_wait) jiffies_wait= schedule_timeout_uninterruptible(jiffies_wait);
+ while (jiffies_wait) jiffies_wait = schedule_timeout_uninterruptible(jiffies_wait);
- for ( i=0 ; i < 8 ; i++ ) {
+ for (i = 0 ; i < 8 ; i++) {
del_timer_sync(&mali_init_cpu_clock_timers[i]);
}
if (print_only) {
- if ( (0==mali_cpu_clock_last_value[2]) && (0==mali_cpu_clock_last_value[3]) ) {
+ if ((0 == mali_cpu_clock_last_value[2]) && (0 == mali_cpu_clock_last_value[3])) {
/* Diff can be printed if we want to check if the clocks are in sync
int diff = mali_cpu_clock_last_value[0] - mali_cpu_clock_last_value[1];*/
MALI_DEBUG_PRINT(2, ("CPU cycle counters readout all: %08x %08x\n", mali_cpu_clock_last_value[0], mali_cpu_clock_last_value[1]));
} else {
- MALI_DEBUG_PRINT(2, ("CPU cycle counters readout all: %08x %08x %08x %08x\n", mali_cpu_clock_last_value[0], mali_cpu_clock_last_value[1], mali_cpu_clock_last_value[2], mali_cpu_clock_last_value[3] ));
+ MALI_DEBUG_PRINT(2, ("CPU cycle counters readout all: %08x %08x %08x %08x\n", mali_cpu_clock_last_value[0], mali_cpu_clock_last_value[1], mali_cpu_clock_last_value[2], mali_cpu_clock_last_value[3]));
}
}
}
{
int err = 0;
- MALI_DEBUG_PRINT(2, ("Inserting Mali v%d device driver. \n",_MALI_API_VERSION));
+ MALI_DEBUG_PRINT(2, ("Inserting Mali v%d device driver. \n", _MALI_API_VERSION));
MALI_DEBUG_PRINT(2, ("Compiled: %s, time: %s.\n", __DATE__, __TIME__));
MALI_DEBUG_PRINT(2, ("Driver revision: %s\n", SVN_REV_STRING));
void mali_module_exit(void)
{
- MALI_DEBUG_PRINT(2, ("Unloading Mali v%d device driver.\n",_MALI_API_VERSION));
+ MALI_DEBUG_PRINT(2, ("Unloading Mali v%d device driver.\n", _MALI_API_VERSION));
MALI_DEBUG_PRINT(2, ("mali_module_exit() unregistering driver\n"));
static int mali_open(struct inode *inode, struct file *filp)
{
- struct mali_session_data * session_data;
+ struct mali_session_data *session_data;
_mali_osk_errcode_t err;
/* input validation */
filp->f_pos = 0;
/* link in our session data */
- filp->private_data = (void*)session_data;
+ filp->private_data = (void *)session_data;
return 0;
}
return 0;
}
-int map_errcode( _mali_osk_errcode_t err )
+int map_errcode(_mali_osk_errcode_t err)
{
- switch(err) {
+ switch (err) {
case _MALI_OSK_ERR_OK :
return 0;
case _MALI_OSK_ERR_FAULT:
return -ENOTTY;
}
- switch(cmd) {
+ switch (cmd) {
case MALI_IOC_WAIT_FOR_NOTIFICATION:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_wait_for_notification_s), sizeof(u64)));
err = wait_for_notification_wrapper(session_data, (_mali_uk_wait_for_notification_s __user *)arg);
break;
+ case MALI_IOC_GET_API_VERSION_V2:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_api_version_v2_s), sizeof(u64)));
+ err = get_api_version_v2_wrapper(session_data, (_mali_uk_get_api_version_v2_s __user *)arg);
+ break;
+
case MALI_IOC_GET_API_VERSION:
err = get_api_version_wrapper(session_data, (_mali_uk_get_api_version_s __user *)arg);
break;
case MALI_IOC_POST_NOTIFICATION:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_post_notification_s), sizeof(u64)));
err = post_notification_wrapper(session_data, (_mali_uk_post_notification_s __user *)arg);
break;
case MALI_IOC_GET_USER_SETTINGS:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_user_settings_s), sizeof(u64)));
err = get_user_settings_wrapper(session_data, (_mali_uk_get_user_settings_s __user *)arg);
break;
case MALI_IOC_REQUEST_HIGH_PRIORITY:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_request_high_priority_s), sizeof(u64)));
err = request_high_priority_wrapper(session_data, (_mali_uk_request_high_priority_s __user *)arg);
break;
#if defined(CONFIG_MALI400_PROFILING)
- case MALI_IOC_PROFILING_START:
- err = profiling_start_wrapper(session_data, (_mali_uk_profiling_start_s __user *)arg);
- break;
-
case MALI_IOC_PROFILING_ADD_EVENT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_profiling_add_event_s), sizeof(u64)));
err = profiling_add_event_wrapper(session_data, (_mali_uk_profiling_add_event_s __user *)arg);
break;
- case MALI_IOC_PROFILING_STOP:
- err = profiling_stop_wrapper(session_data, (_mali_uk_profiling_stop_s __user *)arg);
- break;
-
- case MALI_IOC_PROFILING_GET_EVENT:
- err = profiling_get_event_wrapper(session_data, (_mali_uk_profiling_get_event_s __user *)arg);
- break;
-
- case MALI_IOC_PROFILING_CLEAR:
- err = profiling_clear_wrapper(session_data, (_mali_uk_profiling_clear_s __user *)arg);
+ case MALI_IOC_PROFILING_REPORT_SW_COUNTERS:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_sw_counters_report_s), sizeof(u64)));
+ err = profiling_report_sw_counters_wrapper(session_data, (_mali_uk_sw_counters_report_s __user *)arg);
break;
- case MALI_IOC_PROFILING_GET_CONFIG:
- /* Deprecated: still compatible with get_user_settings */
- err = get_user_settings_wrapper(session_data, (_mali_uk_get_user_settings_s __user *)arg);
- break;
- case MALI_IOC_PROFILING_REPORT_SW_COUNTERS:
- err = profiling_report_sw_counters_wrapper(session_data, (_mali_uk_sw_counters_report_s __user *)arg);
+ case MALI_IOC_PROFILING_MEMORY_USAGE_GET:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_profiling_memory_usage_get_s), sizeof(u64)));
+ err = profiling_memory_usage_get_wrapper(session_data, (_mali_uk_profiling_memory_usage_get_s __user *)arg);
break;
#else
- case MALI_IOC_PROFILING_START: /* FALL-THROUGH */
case MALI_IOC_PROFILING_ADD_EVENT: /* FALL-THROUGH */
- case MALI_IOC_PROFILING_STOP: /* FALL-THROUGH */
- case MALI_IOC_PROFILING_GET_EVENT: /* FALL-THROUGH */
- case MALI_IOC_PROFILING_CLEAR: /* FALL-THROUGH */
- case MALI_IOC_PROFILING_GET_CONFIG: /* FALL-THROUGH */
case MALI_IOC_PROFILING_REPORT_SW_COUNTERS: /* FALL-THROUGH */
+ case MALI_IOC_PROFILING_MEMORY_USAGE_GET: /* FALL-THROUGH */
MALI_DEBUG_PRINT(2, ("Profiling not supported\n"));
err = -ENOTTY;
break;
#endif
case MALI_IOC_MEM_WRITE_SAFE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_mem_write_safe_s), sizeof(u64)));
err = mem_write_safe_wrapper(session_data, (_mali_uk_mem_write_safe_s __user *)arg);
break;
case MALI_IOC_MEM_MAP_EXT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_map_external_mem_s), sizeof(u64)));
err = mem_map_ext_wrapper(session_data, (_mali_uk_map_external_mem_s __user *)arg);
break;
case MALI_IOC_MEM_UNMAP_EXT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_unmap_external_mem_s), sizeof(u64)));
err = mem_unmap_ext_wrapper(session_data, (_mali_uk_unmap_external_mem_s __user *)arg);
break;
case MALI_IOC_MEM_QUERY_MMU_PAGE_TABLE_DUMP_SIZE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_query_mmu_page_table_dump_size_s), sizeof(u64)));
err = mem_query_mmu_page_table_dump_size_wrapper(session_data, (_mali_uk_query_mmu_page_table_dump_size_s __user *)arg);
break;
case MALI_IOC_MEM_DUMP_MMU_PAGE_TABLE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_dump_mmu_page_table_s), sizeof(u64)));
err = mem_dump_mmu_page_table_wrapper(session_data, (_mali_uk_dump_mmu_page_table_s __user *)arg);
break;
#if defined(CONFIG_MALI400_UMP)
case MALI_IOC_MEM_ATTACH_UMP:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_attach_ump_mem_s), sizeof(u64)));
err = mem_attach_ump_wrapper(session_data, (_mali_uk_attach_ump_mem_s __user *)arg);
break;
case MALI_IOC_MEM_RELEASE_UMP:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_release_ump_mem_s), sizeof(u64)));
err = mem_release_ump_wrapper(session_data, (_mali_uk_release_ump_mem_s __user *)arg);
break;
#ifdef CONFIG_DMA_SHARED_BUFFER
case MALI_IOC_MEM_ATTACH_DMA_BUF:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_attach_dma_buf_s), sizeof(u64)));
err = mali_attach_dma_buf(session_data, (_mali_uk_attach_dma_buf_s __user *)arg);
break;
case MALI_IOC_MEM_RELEASE_DMA_BUF:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_release_dma_buf_s), sizeof(u64)));
err = mali_release_dma_buf(session_data, (_mali_uk_release_dma_buf_s __user *)arg);
break;
case MALI_IOC_MEM_DMA_BUF_GET_SIZE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_dma_buf_get_size_s), sizeof(u64)));
err = mali_dma_buf_get_size(session_data, (_mali_uk_dma_buf_get_size_s __user *)arg);
break;
#else
#endif
case MALI_IOC_PP_START_JOB:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_pp_start_job_s), sizeof(u64)));
err = pp_start_job_wrapper(session_data, (_mali_uk_pp_start_job_s __user *)arg);
break;
case MALI_IOC_PP_AND_GP_START_JOB:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_pp_and_gp_start_job_s), sizeof(u64)));
err = pp_and_gp_start_job_wrapper(session_data, (_mali_uk_pp_and_gp_start_job_s __user *)arg);
break;
case MALI_IOC_PP_NUMBER_OF_CORES_GET:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_pp_number_of_cores_s), sizeof(u64)));
err = pp_get_number_of_cores_wrapper(session_data, (_mali_uk_get_pp_number_of_cores_s __user *)arg);
break;
case MALI_IOC_PP_CORE_VERSION_GET:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_pp_core_version_s), sizeof(u64)));
err = pp_get_core_version_wrapper(session_data, (_mali_uk_get_pp_core_version_s __user *)arg);
break;
case MALI_IOC_PP_DISABLE_WB:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_pp_disable_wb_s), sizeof(u64)));
err = pp_disable_wb_wrapper(session_data, (_mali_uk_pp_disable_wb_s __user *)arg);
break;
case MALI_IOC_GP2_START_JOB:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_gp_start_job_s), sizeof(u64)));
err = gp_start_job_wrapper(session_data, (_mali_uk_gp_start_job_s __user *)arg);
break;
case MALI_IOC_GP2_NUMBER_OF_CORES_GET:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_gp_number_of_cores_s), sizeof(u64)));
err = gp_get_number_of_cores_wrapper(session_data, (_mali_uk_get_gp_number_of_cores_s __user *)arg);
break;
case MALI_IOC_GP2_CORE_VERSION_GET:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_get_gp_core_version_s), sizeof(u64)));
err = gp_get_core_version_wrapper(session_data, (_mali_uk_get_gp_core_version_s __user *)arg);
break;
case MALI_IOC_GP2_SUSPEND_RESPONSE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_gp_suspend_response_s), sizeof(u64)));
err = gp_suspend_response_wrapper(session_data, (_mali_uk_gp_suspend_response_s __user *)arg);
break;
case MALI_IOC_VSYNC_EVENT_REPORT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_vsync_event_report_s), sizeof(u64)));
err = vsync_event_report_wrapper(session_data, (_mali_uk_vsync_event_report_s __user *)arg);
break;
case MALI_IOC_TIMELINE_GET_LATEST_POINT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_timeline_get_latest_point_s), sizeof(u64)));
err = timeline_get_latest_point_wrapper(session_data, (_mali_uk_timeline_get_latest_point_s __user *)arg);
break;
case MALI_IOC_TIMELINE_WAIT:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_timeline_wait_s), sizeof(u64)));
err = timeline_wait_wrapper(session_data, (_mali_uk_timeline_wait_s __user *)arg);
break;
case MALI_IOC_TIMELINE_CREATE_SYNC_FENCE:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_timeline_create_sync_fence_s), sizeof(u64)));
err = timeline_create_sync_fence_wrapper(session_data, (_mali_uk_timeline_create_sync_fence_s __user *)arg);
break;
case MALI_IOC_SOFT_JOB_START:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_soft_job_start_s), sizeof(u64)));
err = soft_job_start_wrapper(session_data, (_mali_uk_soft_job_start_s __user *)arg);
break;
case MALI_IOC_SOFT_JOB_SIGNAL:
+ BUILD_BUG_ON(!IS_ALIGNED(sizeof(_mali_uk_soft_job_signal_s), sizeof(u64)));
err = soft_job_signal_wrapper(session_data, (_mali_uk_soft_job_signal_s __user *)arg);
break;
- case MALI_IOC_MEM_INIT: /* Fallthrough */
- case MALI_IOC_MEM_TERM: /* Fallthrough */
- MALI_DEBUG_PRINT(2, ("Deprecated ioctls called\n"));
- err = -ENOTTY;
- break;
-
- case MALI_IOC_MEM_GET_BIG_BLOCK: /* Fallthrough */
- case MALI_IOC_MEM_FREE_BIG_BLOCK:
- MALI_PRINT_ERROR(("Non-MMU mode is no longer supported.\n"));
- err = -ENOTTY;
- break;
-
default:
MALI_DEBUG_PRINT(2, ("No handler for ioctl 0x%08X 0x%08lX\n", cmd, arg));
err = -ENOTTY;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
extern struct platform_device *mali_platform_device;
-#if MALI_LICENSE_IS_GPL
-/* Defined in mali_osk_irq.h */
-extern struct workqueue_struct * mali_wq_normal;
-#endif
-
#ifdef __cplusplus
}
#endif
/**
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_gp_job.h"
#include "mali_pp_job.h"
#include "mali_pp_scheduler.h"
+#include "mali_session.h"
#define PRIVATE_DATA_COUNTER_MAKE_GP(src) (src)
#define PRIVATE_DATA_COUNTER_MAKE_PP(src) ((1 << 24) | src)
#define PRIVATE_DATA_COUNTER_IS_SUB_JOB(a) ((((a) >> 16) & 0xFF) ? MALI_TRUE : MALI_FALSE)
#define PRIVATE_DATA_COUNTER_GET_SUB_JOB(a) (((a) >> 8) & 0xFF)
-/* kasin Lee added. */
-#include "mali_kernel_utilization.h"
-/* End of Kasin Lee added. */
-
#define POWER_BUFFER_SIZE 3
static struct dentry *mali_debugfs_dir = NULL;
_MALI_MAX_EVENTS
} _mali_device_debug_power_events;
-static const char* const mali_power_events[_MALI_MAX_EVENTS] = {
+static const char *const mali_power_events[_MALI_MAX_EVENTS] = {
[_MALI_DEVICE_SUSPEND] = "suspend",
[_MALI_DEVICE_RESUME] = "resume",
[_MALI_DEVICE_DVFS_PAUSE] = "dvfs_pause",
group = (struct mali_group *)filp->private_data;
MALI_DEBUG_ASSERT_POINTER(group);
- r = sprintf(buffer, "%u\n", mali_group_is_enabled(group) ? 1 : 0);
+ r = snprintf(buffer, 64, "%u\n", mali_group_is_enabled(group) ? 1 : 0);
return simple_read_from_buffer(buf, count, offp, buffer, r);
}
hw_core = (struct mali_hw_core *)filp->private_data;
MALI_DEBUG_ASSERT_POINTER(hw_core);
- r = sprintf(buffer, "0x%08X\n", hw_core->phys_addr);
+ r = snprintf(buffer, 64, "0x%08X\n", hw_core->phys_addr);
return simple_read_from_buffer(buf, count, offp, buffer, r);
}
static ssize_t profiling_counter_src_read(struct file *filp, char __user *ubuf, size_t cnt, loff_t *ppos)
{
- u32 is_pp = PRIVATE_DATA_COUNTER_IS_PP((u32)filp->private_data);
- u32 src_id = PRIVATE_DATA_COUNTER_GET_SRC((u32)filp->private_data);
- mali_bool is_sub_job = PRIVATE_DATA_COUNTER_IS_SUB_JOB((u32)filp->private_data);
- u32 sub_job = PRIVATE_DATA_COUNTER_GET_SUB_JOB((u32)filp->private_data);
+ u32 is_pp = PRIVATE_DATA_COUNTER_IS_PP((uintptr_t)filp->private_data);
+ u32 src_id = PRIVATE_DATA_COUNTER_GET_SRC((uintptr_t)filp->private_data);
+ mali_bool is_sub_job = PRIVATE_DATA_COUNTER_IS_SUB_JOB((uintptr_t)filp->private_data);
+ u32 sub_job = PRIVATE_DATA_COUNTER_GET_SUB_JOB((uintptr_t)filp->private_data);
char buf[64];
int r;
u32 val;
}
if (MALI_HW_CORE_NO_COUNTER == val) {
- r = sprintf(buf, "-1\n");
+ r = snprintf(buf, 64, "-1\n");
} else {
- r = sprintf(buf, "%u\n", val);
+ r = snprintf(buf, 64, "%u\n", val);
}
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
static ssize_t profiling_counter_src_write(struct file *filp, const char __user *ubuf, size_t cnt, loff_t *ppos)
{
- u32 is_pp = PRIVATE_DATA_COUNTER_IS_PP((u32)filp->private_data);
- u32 src_id = PRIVATE_DATA_COUNTER_GET_SRC((u32)filp->private_data);
- mali_bool is_sub_job = PRIVATE_DATA_COUNTER_IS_SUB_JOB((u32)filp->private_data);
- u32 sub_job = PRIVATE_DATA_COUNTER_GET_SUB_JOB((u32)filp->private_data);
+ u32 is_pp = PRIVATE_DATA_COUNTER_IS_PP((uintptr_t)filp->private_data);
+ u32 src_id = PRIVATE_DATA_COUNTER_GET_SRC((uintptr_t)filp->private_data);
+ mali_bool is_sub_job = PRIVATE_DATA_COUNTER_IS_SUB_JOB((uintptr_t)filp->private_data);
+ u32 sub_job = PRIVATE_DATA_COUNTER_GET_SUB_JOB((uintptr_t)filp->private_data);
char buf[64];
long val;
int ret;
}
if (MALI_HW_CORE_NO_COUNTER == val) {
- r = sprintf(buf, "-1\n");
+ r = snprintf(buf, 64, "-1\n");
} else {
- r = sprintf(buf, "%u\n", val);
+ r = snprintf(buf, 64, "%u\n", val);
}
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
}
static ssize_t power_power_events_write(struct file *filp, const char __user *ubuf, size_t cnt, loff_t *ppos)
{
- if (!strncmp(ubuf,mali_power_events[_MALI_DEVICE_SUSPEND],strlen(mali_power_events[_MALI_DEVICE_SUSPEND]))) {
+ if (!strncmp(ubuf, mali_power_events[_MALI_DEVICE_SUSPEND], strlen(mali_power_events[_MALI_DEVICE_SUSPEND]))) {
mali_pm_os_suspend();
- } else if (!strncmp(ubuf,mali_power_events[_MALI_DEVICE_RESUME],strlen(mali_power_events[_MALI_DEVICE_RESUME]))) {
+ } else if (!strncmp(ubuf, mali_power_events[_MALI_DEVICE_RESUME], strlen(mali_power_events[_MALI_DEVICE_RESUME]))) {
mali_pm_os_resume();
- } else if (!strncmp(ubuf,mali_power_events[_MALI_DEVICE_DVFS_PAUSE],strlen(mali_power_events[_MALI_DEVICE_DVFS_PAUSE]))) {
+ } else if (!strncmp(ubuf, mali_power_events[_MALI_DEVICE_DVFS_PAUSE], strlen(mali_power_events[_MALI_DEVICE_DVFS_PAUSE]))) {
mali_dev_pause();
- } else if (!strncmp(ubuf,mali_power_events[_MALI_DEVICE_DVFS_RESUME],strlen(mali_power_events[_MALI_DEVICE_DVFS_RESUME]))) {
+ } else if (!strncmp(ubuf, mali_power_events[_MALI_DEVICE_DVFS_RESUME], strlen(mali_power_events[_MALI_DEVICE_DVFS_RESUME]))) {
mali_dev_resume();
}
*ppos += cnt;
size = seq_get_buf(seq_file, &buf);
- if(!size) {
+ if (!size) {
return -ENOMEM;
}
/* Create the internal state dump. */
- len = snprintf(buf+len, size-len, "Mali device driver %s\n", SVN_REV_STRING);
- len += snprintf(buf+len, size-len, "License: %s\n\n", MALI_KERNEL_LINUX_LICENSE);
+ len = snprintf(buf + len, size - len, "Mali device driver %s\n", SVN_REV_STRING);
+ len += snprintf(buf + len, size - len, "License: %s\n\n", MALI_KERNEL_LINUX_LICENSE);
len += _mali_kernel_core_dump_state(buf + len, size - len);
char buf[64];
int r;
- r = sprintf(buf, "%u\n", _mali_internal_profiling_is_recording() ? 1 : 0);
+ r = snprintf(buf, 64, "%u\n", _mali_internal_profiling_is_recording() ? 1 : 0);
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
}
u32 event_id;
u32 data[5];
- index = (u32)*spos;
+ index = (u32) * spos;
/* Retrieve all events */
if (_MALI_OSK_ERR_OK == _mali_internal_profiling_get_event(index, ×tamp, &event_id, data)) {
u32 event_id;
u32 data[5];
- index = (u32)*spos;
+ index = (u32) * spos;
/* Retrieve all events */
if (_MALI_OSK_ERR_OK == _mali_internal_profiling_get_event(index, ×tamp, &event_id, data)) {
seq_printf(seq_file, "[%06u] ", index);
- switch(event_id & 0x0F000000) {
+ switch (event_id & 0x0F000000) {
case MALI_PROFILING_EVENT_TYPE_SINGLE:
seq_printf(seq_file, "SINGLE | ");
break;
break;
}
- switch(event_id & 0x00FF0000) {
+ switch (event_id & 0x00FF0000) {
case MALI_PROFILING_EVENT_CHANNEL_SOFTWARE:
seq_printf(seq_file, "SW | ");
break;
if (MALI_EVENT_ID_IS_HW(event_id)) {
if (((event_id & 0x0F000000) == MALI_PROFILING_EVENT_TYPE_START) || ((event_id & 0x0F000000) == MALI_PROFILING_EVENT_TYPE_STOP)) {
- switch(event_id & 0x0000FFFF) {
+ switch (event_id & 0x0000FFFF) {
case MALI_PROFILING_EVENT_REASON_START_STOP_HW_PHYSICAL:
seq_printf(seq_file, "PHYSICAL | ");
break;
{
char buf[64];
size_t r;
- u32 mem = _mali_ukk_report_memory_usage()/1024;
+ u32 mem = _mali_ukk_report_memory_usage();
- r = snprintf(buf, 64, "%u kB\n", mem);
+ r = snprintf(buf, 64, "%u\n", mem);
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
}
{
char buf[64];
size_t r;
- u32 uval= _mali_ukk_utilization_gp_pp();
+ u32 uval = _mali_ukk_utilization_gp_pp();
r = snprintf(buf, 64, "%u\n", uval);
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
{
char buf[64];
size_t r;
- u32 uval= _mali_ukk_utilization_gp();
+ u32 uval = _mali_ukk_utilization_gp();
r = snprintf(buf, 64, "%u\n", uval);
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
{
char buf[64];
size_t r;
- u32 uval= _mali_ukk_utilization_pp();
+ u32 uval = _mali_ukk_utilization_pp();
r = snprintf(buf, 64, "%u\n", uval);
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
struct dentry *mali_user_settings_dir = debugfs_create_dir("userspace_settings", mali_debugfs_dir);
if (mali_user_settings_dir != NULL) {
- int i;
+ long i;
for (i = 0; i < _MALI_UK_USER_SETTING_MAX; i++) {
- debugfs_create_file(_mali_uk_user_setting_descriptions[i], 0600, mali_user_settings_dir, (void*)i, &user_settings_fops);
+ debugfs_create_file(_mali_uk_user_setting_descriptions[i],
+ 0600, mali_user_settings_dir, (void *)i,
+ &user_settings_fops);
}
}
int r;
char buffer[64];
- r = sprintf(buffer, "%u\n", mali_pp_scheduler_get_num_cores_enabled());
+ r = snprintf(buffer, 64, "%u\n", mali_pp_scheduler_get_num_cores_enabled());
return simple_read_from_buffer(buf, count, offp, buffer, r);
}
int r;
char buffer[64];
- r = sprintf(buffer, "%u\n", mali_pp_scheduler_get_num_cores_total());
+ r = snprintf(buffer, 64, "%u\n", mali_pp_scheduler_get_num_cores_total());
return simple_read_from_buffer(buf, count, offp, buffer, r);
}
switch (mali_kernel_core_get_product_id()) {
case _MALI_PRODUCT_ID_MALI200:
- r = sprintf(buffer, "Mali-200\n");
+ r = snprintf(buffer, 64, "Mali-200\n");
break;
case _MALI_PRODUCT_ID_MALI300:
- r = sprintf(buffer, "Mali-300\n");
+ r = snprintf(buffer, 64, "Mali-300\n");
break;
case _MALI_PRODUCT_ID_MALI400:
- r = sprintf(buffer, "Mali-400 MP\n");
+ r = snprintf(buffer, 64, "Mali-400 MP\n");
break;
case _MALI_PRODUCT_ID_MALI450:
- r = sprintf(buffer, "Mali-450 MP\n");
+ r = snprintf(buffer, 64, "Mali-450 MP\n");
break;
case _MALI_PRODUCT_ID_UNKNOWN:
return -EINVAL;
.read = version_read,
};
+#if defined(DEBUG)
+static int timeline_debugfs_show(struct seq_file *s, void *private_data)
+{
+ struct mali_session_data *session, *tmp;
+ u32 session_seq = 1;
+
+ seq_printf(s, "timeline system info: \n=================\n\n");
+
+ mali_session_lock();
+ MALI_SESSION_FOREACH(session, tmp, link){
+ seq_printf(s, "session %d <%p> start:\n", session_seq,session);
+ mali_timeline_debug_print_system(session->timeline_system,s);
+ seq_printf(s, "session %d end\n\n\n", session_seq++);
+ }
+ mali_session_unlock();
+
+ return 0;
+}
+
+static int timeline_debugfs_open( struct inode *inode, struct file *file)
+{
+ return single_open(file, timeline_debugfs_show, inode->i_private);
+}
+
+static const struct file_operations timeline_dump_fops = {
+ .owner = THIS_MODULE,
+ .open = timeline_debugfs_open,
+ .read = seq_read,
+ .llseek = seq_lseek,
+ .release = single_release
+};
+#endif
+
int mali_sysfs_register(const char *mali_dev_name)
{
mali_debugfs_dir = debugfs_create_dir(mali_dev_name, NULL);
- if(ERR_PTR(-ENODEV) == mali_debugfs_dir) {
+ if (ERR_PTR(-ENODEV) == mali_debugfs_dir) {
/* Debugfs not supported. */
mali_debugfs_dir = NULL;
} else {
- if(NULL != mali_debugfs_dir) {
+ if (NULL != mali_debugfs_dir) {
/* Debugfs directory created successfully; create files now */
struct dentry *mali_pmu_dir;
struct dentry *mali_power_dir;
mali_gp_dir = debugfs_create_dir("gp", mali_debugfs_dir);
if (mali_gp_dir != NULL) {
u32 num_groups;
- int i;
+ long i;
num_groups = mali_group_get_glob_num_groups();
for (i = 0; i < num_groups; i++) {
mali_pp_dir = debugfs_create_dir("pp", mali_debugfs_dir);
if (mali_pp_dir != NULL) {
u32 num_groups;
- int i;
+ long i;
debugfs_create_file("num_cores_total", 0400, mali_pp_dir, NULL, &pp_num_cores_total_fops);
debugfs_create_file("num_cores_enabled", 0600, mali_pp_dir, NULL, &pp_num_cores_enabled_fops);
mali_profiling_dir = debugfs_create_dir("profiling", mali_debugfs_dir);
if (mali_profiling_dir != NULL) {
u32 max_sub_jobs;
- int i;
+ long i;
struct dentry *mali_profiling_gp_dir;
struct dentry *mali_profiling_pp_dir;
#if defined(CONFIG_MALI400_INTERNAL_PROFILING)
*/
mali_profiling_gp_dir = debugfs_create_dir("gp", mali_profiling_dir);
if (mali_profiling_gp_dir != NULL) {
- debugfs_create_file("counter_src0", 0600, mali_profiling_gp_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_GP(0), &profiling_counter_src_fops);
- debugfs_create_file("counter_src1", 0600, mali_profiling_gp_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_GP(1), &profiling_counter_src_fops);
+ debugfs_create_file("counter_src0", 0600, mali_profiling_gp_dir, (void *)PRIVATE_DATA_COUNTER_MAKE_GP(0), &profiling_counter_src_fops);
+ debugfs_create_file("counter_src1", 0600, mali_profiling_gp_dir, (void *)PRIVATE_DATA_COUNTER_MAKE_GP(1), &profiling_counter_src_fops);
}
/*
*/
mali_profiling_pp_dir = debugfs_create_dir("pp", mali_profiling_dir);
if (mali_profiling_pp_dir != NULL) {
- debugfs_create_file("counter_src0", 0600, mali_profiling_pp_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_PP(0), &profiling_counter_src_fops);
- debugfs_create_file("counter_src1", 0600, mali_profiling_pp_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_PP(1), &profiling_counter_src_fops);
+ debugfs_create_file("counter_src0", 0600, mali_profiling_pp_dir, (void *)PRIVATE_DATA_COUNTER_MAKE_PP(0), &profiling_counter_src_fops);
+ debugfs_create_file("counter_src1", 0600, mali_profiling_pp_dir, (void *)PRIVATE_DATA_COUNTER_MAKE_PP(1), &profiling_counter_src_fops);
}
max_sub_jobs = mali_pp_scheduler_get_num_cores_total();
_mali_osk_snprintf(buf, sizeof(buf), "%u", i);
mali_profiling_pp_x_dir = debugfs_create_dir(buf, mali_profiling_pp_dir);
if (NULL != mali_profiling_pp_x_dir) {
- debugfs_create_file("counter_src0", 0600, mali_profiling_pp_x_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_PP_SUB_JOB(0, i), &profiling_counter_src_fops);
- debugfs_create_file("counter_src1", 0600, mali_profiling_pp_x_dir, (void*)PRIVATE_DATA_COUNTER_MAKE_PP_SUB_JOB(1, i), &profiling_counter_src_fops);
+ debugfs_create_file("counter_src0",
+ 0600, mali_profiling_pp_x_dir,
+ (void *)PRIVATE_DATA_COUNTER_MAKE_PP_SUB_JOB(0, i),
+ &profiling_counter_src_fops);
+ debugfs_create_file("counter_src1",
+ 0600, mali_profiling_pp_x_dir,
+ (void *)PRIVATE_DATA_COUNTER_MAKE_PP_SUB_JOB(1, i),
+ &profiling_counter_src_fops);
}
}
if (mali_profiling_proc_dir != NULL) {
struct dentry *mali_profiling_proc_default_dir = debugfs_create_dir("default", mali_profiling_proc_dir);
if (mali_profiling_proc_default_dir != NULL) {
- debugfs_create_file("enable", 0600, mali_profiling_proc_default_dir, (void*)_MALI_UK_USER_SETTING_SW_EVENTS_ENABLE, &user_settings_fops);
+ debugfs_create_file("enable", 0600, mali_profiling_proc_default_dir, (void *)_MALI_UK_USER_SETTING_SW_EVENTS_ENABLE, &user_settings_fops);
}
}
debugfs_create_file("record", 0600, mali_profiling_dir, NULL, &profiling_record_fops);
#if MALI_STATE_TRACKING
debugfs_create_file("state_dump", 0400, mali_debugfs_dir, NULL, &mali_seq_internal_state_fops);
#endif
+
+#if defined(DEBUG)
+ debugfs_create_file("timeline_dump", 0400, mali_debugfs_dir, NULL, &timeline_dump_fops);
+#endif
if (mali_sysfs_user_settings_register()) {
/* Failed to create the debugfs entries for the user settings DB. */
MALI_DEBUG_PRINT(2, ("Failed to create user setting debugfs files. Ignoring...\n"));
int mali_sysfs_unregister(void)
{
- if(NULL != mali_debugfs_dir) {
+ if (NULL != mali_debugfs_dir) {
debugfs_remove_recursive(mali_debugfs_dir);
}
return 0;
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*/
TRACE_EVENT(mali_timeline_event,
- TP_PROTO(unsigned int event_id, unsigned int d0, unsigned int d1,
- unsigned int d2, unsigned int d3, unsigned int d4),
+ TP_PROTO(unsigned int event_id, unsigned int d0, unsigned int d1,
+ unsigned int d2, unsigned int d3, unsigned int d4),
- TP_ARGS(event_id, d0, d1, d2, d3, d4),
+ TP_ARGS(event_id, d0, d1, d2, d3, d4),
- TP_STRUCT__entry(
- __field(unsigned int, event_id)
- __field(unsigned int, d0)
- __field(unsigned int, d1)
- __field(unsigned int, d2)
- __field(unsigned int, d3)
- __field(unsigned int, d4)
- ),
+ TP_STRUCT__entry(
+ __field(unsigned int, event_id)
+ __field(unsigned int, d0)
+ __field(unsigned int, d1)
+ __field(unsigned int, d2)
+ __field(unsigned int, d3)
+ __field(unsigned int, d4)
+ ),
- TP_fast_assign(
- __entry->event_id = event_id;
- __entry->d0 = d0;
- __entry->d1 = d1;
- __entry->d2 = d2;
- __entry->d3 = d3;
- __entry->d4 = d4;
- ),
+ TP_fast_assign(
+ __entry->event_id = event_id;
+ __entry->d0 = d0;
+ __entry->d1 = d1;
+ __entry->d2 = d2;
+ __entry->d3 = d3;
+ __entry->d4 = d4;
+ ),
- TP_printk("event=%d", __entry->event_id)
- );
+ TP_printk("event=%d", __entry->event_id)
+ );
/**
* Define a tracepoint used to regsiter the value of a hardware counter.
*/
TRACE_EVENT(mali_hw_counter,
- TP_PROTO(unsigned int counter_id, unsigned int value),
+ TP_PROTO(unsigned int counter_id, unsigned int value),
- TP_ARGS(counter_id, value),
+ TP_ARGS(counter_id, value),
- TP_STRUCT__entry(
- __field(unsigned int, counter_id)
- __field(unsigned int, value)
- ),
+ TP_STRUCT__entry(
+ __field(unsigned int, counter_id)
+ __field(unsigned int, value)
+ ),
- TP_fast_assign(
- __entry->counter_id = counter_id;
- ),
+ TP_fast_assign(
+ __entry->counter_id = counter_id;
+ ),
- TP_printk("event %d = %d", __entry->counter_id, __entry->value)
- );
+ TP_printk("event %d = %d", __entry->counter_id, __entry->value)
+ );
/**
* Define a tracepoint used to send a bundle of software counters.
*/
TRACE_EVENT(mali_sw_counters,
- TP_PROTO(pid_t pid, pid_t tid, void * surface_id, unsigned int * counters),
+ TP_PROTO(pid_t pid, pid_t tid, void *surface_id, unsigned int *counters),
- TP_ARGS(pid, tid, surface_id, counters),
+ TP_ARGS(pid, tid, surface_id, counters),
- TP_STRUCT__entry(
- __field(pid_t, pid)
- __field(pid_t, tid)
- __field(void *, surface_id)
- __field(unsigned int *, counters)
- ),
+ TP_STRUCT__entry(
+ __field(pid_t, pid)
+ __field(pid_t, tid)
+ __field(void *, surface_id)
+ __field(unsigned int *, counters)
+ ),
- TP_fast_assign(
- __entry->pid = pid;
- __entry->tid = tid;
- __entry->surface_id = surface_id;
- __entry->counters = counters;
- ),
+ TP_fast_assign(
+ __entry->pid = pid;
+ __entry->tid = tid;
+ __entry->surface_id = surface_id;
+ __entry->counters = counters;
+ ),
- TP_printk("counters were %s", __entry->counters == NULL? "NULL" : "not NULL")
- );
+ TP_printk("counters were %s", __entry->counters == NULL ? "NULL" : "not NULL")
+ );
+
+/**
+ * Define a tracepoint used to gather core activity for systrace
+ * @param pid The process id for which the core activity originates from
+ * @param active If the core is active (1) or not (0)
+ * @param core_type The type of core active, either GP (1) or PP (0)
+ * @param core_id The core id that is active for the core_type
+ * @param frame_builder_id The frame builder id associated with this core activity
+ * @param flush_id The flush id associated with this core activity
+ */
+TRACE_EVENT(mali_core_active,
+
+ TP_PROTO(pid_t pid, unsigned int active, unsigned int core_type, unsigned int core_id, unsigned int frame_builder_id, unsigned int flush_id),
+
+ TP_ARGS(pid, active, core_type, core_id, frame_builder_id, flush_id),
+
+ TP_STRUCT__entry(
+ __field(pid_t, pid)
+ __field(unsigned int, active)
+ __field(unsigned int, core_type)
+ __field(unsigned int, core_id)
+ __field(unsigned int, frame_builder_id)
+ __field(unsigned int, flush_id)
+ ),
+
+ TP_fast_assign(
+ __entry->pid = pid;
+ __entry->active = active;
+ __entry->core_type = core_type;
+ __entry->core_id = core_id;
+ __entry->frame_builder_id = frame_builder_id;
+ __entry->flush_id = flush_id;
+ ),
+
+ TP_printk("%s|%d|%s%i:%x|%d", __entry->active ? "S" : "F", __entry->pid, __entry->core_type ? "GP" : "PP", __entry->core_id, __entry->flush_id, __entry->frame_builder_id)
+ );
#endif /* MALI_LINUX_TRACE_H */
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
}
}
-static void mali_mem_vma_open(struct vm_area_struct * vma)
+static void mali_mem_vma_open(struct vm_area_struct *vma)
{
- mali_mem_allocation *descriptor = (mali_mem_allocation*)vma->vm_private_data;
+ mali_mem_allocation *descriptor = (mali_mem_allocation *)vma->vm_private_data;
MALI_DEBUG_PRINT(4, ("Open called on vma %p\n", vma));
descriptor->cpu_mapping.ref++;
MALI_DEBUG_PRINT(3, ("Close called on vma %p\n", vma));
- descriptor = (mali_mem_allocation*)vma->vm_private_data;
+ descriptor = (mali_mem_allocation *)vma->vm_private_data;
BUG_ON(!descriptor);
MALI_DEBUG_ASSERT(MALI_MEM_ALLOCATION_VALID_MAGIC == descriptor->magic);
static int mali_kernel_memory_cpu_page_fault_handler(struct vm_area_struct *vma, struct vm_fault *vmf)
{
- void __user * address;
+ void __user *address;
mali_mem_allocation *descriptor;
address = vmf->virtual_address;
*/
MALI_DEBUG_PRINT(1, ("Page-fault in Mali memory region caused by the CPU.\n"));
- MALI_DEBUG_PRINT(1, ("Tried to access %p (process local virtual address) which is not currently mapped to any Mali memory.\n", (void*)address));
+ MALI_DEBUG_PRINT(1, ("Tried to access %p (process local virtual address) which is not currently mapped to any Mali memory.\n", (void *)address));
MALI_IGNORE(address);
MALI_IGNORE(descriptor);
return VM_FAULT_SIGBUS;
}
-struct vm_operations_struct mali_kernel_vm_ops = {
+static struct vm_operations_struct mali_kernel_vm_ops = {
.open = mali_mem_vma_open,
.close = mali_mem_vma_close,
.fault = mali_kernel_memory_cpu_page_fault_handler
}
MALI_DEBUG_PRINT(4, ("MMap() handler: start=0x%08X, phys=0x%08X, size=0x%08X vma->flags 0x%08x\n",
- (unsigned int)vma->vm_start, (unsigned int)(vma->vm_pgoff << PAGE_SHIFT),
- (unsigned int)(vma->vm_end - vma->vm_start), vma->vm_flags));
+ (unsigned int)vma->vm_start, (unsigned int)(vma->vm_pgoff << PAGE_SHIFT),
+ (unsigned int)(vma->vm_end - vma->vm_start), vma->vm_flags));
/* Set some bits which indicate that, the memory is IO memory, meaning
* that no paging is to be performed and the memory should not be
vma->vm_flags |= VM_IO;
vma->vm_flags |= VM_DONTCOPY;
vma->vm_flags |= VM_PFNMAP;
-#if LINUX_VERSION_CODE < KERNEL_VERSION(3,7,0)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 7, 0)
vma->vm_flags |= VM_RESERVED;
#else
vma->vm_flags |= VM_DONTDUMP;
MALI_DEBUG_ASSERT(MALI_MEM_ALLOCATION_VALID_MAGIC == descriptor->magic);
- vma->vm_private_data = (void*)descriptor;
+ vma->vm_private_data = (void *)descriptor;
/* Put on descriptor map */
if (_MALI_OSK_ERR_OK != mali_descriptor_mapping_allocate_mapping(session->descriptor_mapping, descriptor, &descriptor->id)) {
{
mali_mem_allocation *descriptor;
- descriptor = (mali_mem_allocation*)kzalloc(sizeof(mali_mem_allocation), GFP_KERNEL);
+ descriptor = (mali_mem_allocation *)kzalloc(sizeof(mali_mem_allocation), GFP_KERNEL);
if (NULL == descriptor) {
- MALI_DEBUG_PRINT(3,("mali_ukk_mem_mmap: descriptor was NULL\n"));
+ MALI_DEBUG_PRINT(3, ("mali_ukk_mem_mmap: descriptor was NULL\n"));
return NULL;
}
#define MALI_MEM_DESCRIPTORS_INIT 64
#define MALI_MEM_DESCRIPTORS_MAX 65536
-_mali_osk_errcode_t mali_memory_session_begin(struct mali_session_data * session_data)
+_mali_osk_errcode_t mali_memory_session_begin(struct mali_session_data *session_data)
{
MALI_DEBUG_PRINT(5, ("Memory session begin\n"));
}
session_data->memory_lock = _mali_osk_mutex_init(_MALI_OSK_LOCKFLAG_ORDERED,
- _MALI_OSK_LOCK_ORDER_MEM_SESSION);
+ _MALI_OSK_LOCK_ORDER_MEM_SESSION);
if (NULL == session_data->memory_lock) {
mali_descriptor_mapping_destroy(session_data->descriptor_mapping);
*
* session->memory_lock must be held when calling this function.
*/
-static void descriptor_table_cleanup_callback(int descriptor_id, void* map_target)
+static void descriptor_table_cleanup_callback(int descriptor_id, void *map_target)
{
mali_mem_allocation *descriptor;
- descriptor = (mali_mem_allocation*)map_target;
+ descriptor = (mali_mem_allocation *)map_target;
MALI_DEBUG_ASSERT_LOCK_HELD(descriptor->session->memory_lock);
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @param table_page GPU pointer to the allocated page
* @param mapping CPU pointer to the mapping of the allocated page
*/
-MALI_STATIC_INLINE _mali_osk_errcode_t mali_mmu_get_table_page(u32 *table_page, mali_io_address *mapping)
+MALI_STATIC_INLINE _mali_osk_errcode_t
+mali_mmu_get_table_page(mali_dma_addr *table_page, mali_io_address *mapping)
{
return mali_mem_os_get_table_page(table_page, mapping);
}
*
* @param pa the GPU address of the page to release
*/
-MALI_STATIC_INLINE void mali_mmu_release_table_page(u32 phys, void *virt)
+MALI_STATIC_INLINE void
+mali_mmu_release_table_page(mali_dma_addr phys, void *virt)
{
mali_mem_os_release_table_page(phys, virt);
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
return info->base + ((block - info->all_blocks) * MALI_BLOCK_SIZE);
}
-mali_mem_allocator *mali_mem_block_allocator_create(u32 base_address, u32 cpu_usage_adjust, u32 size)
+static mali_mem_allocator *mali_mem_block_allocator_create(u32 base_address, u32 cpu_usage_adjust, u32 size)
{
block_allocator *info;
u32 usable_size;
info->base = base_address;
info->cpu_usage_adjust = cpu_usage_adjust;
- for ( i = 0; i < num_blocks; i++) {
+ for (i = 0; i < num_blocks; i++) {
info->all_blocks[i].next = info->first_free;
info->first_free = &info->all_blocks[i];
}
void mali_mem_block_allocator_destroy(mali_mem_allocator *allocator)
{
- block_allocator *info = (block_allocator*)allocator;
+ block_allocator *info = (block_allocator *)allocator;
info = mali_mem_block_gobal_allocator;
if (NULL == info) return;
descriptor->mali_mapping.addr = mali_addr;
descriptor->size = size;
- descriptor->cpu_mapping.addr = (void __user*)vma->vm_start;
+ descriptor->cpu_mapping.addr = (void __user *)vma->vm_start;
descriptor->cpu_mapping.ref = 1;
if (VM_SHARED == (VM_SHARED & vma->vm_flags)) {
MALI_ERROR(_MALI_OSK_ERR_FAULT);
}
- mali_mem_block_gobal_allocator = (block_allocator*)allocator;
+ mali_mem_block_gobal_allocator = (block_allocator *)allocator;
return _MALI_OSK_ERR_OK;
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
-#include <linux/fs.h> /* file system operations */
-#include <asm/uaccess.h> /* user space access */
+#include <linux/fs.h> /* file system operations */
+#include <asm/uaccess.h> /* user space access */
#include <linux/dma-buf.h>
#include <linux/scatterlist.h>
#include <linux/rbtree.h>
MALI_DEBUG_ASSERT(0 < cookie);
err = mali_descriptor_mapping_get(job->session->descriptor_mapping,
- cookie, (void**)&descriptor);
+ cookie, (void **)&descriptor);
if (_MALI_OSK_ERR_OK != err) {
MALI_DEBUG_PRINT_ERROR(("Mali DMA-buf: Failed to get descriptor for cookie %d\n", cookie));
err = mali_dma_buf_map(mem, mem->session, descriptor->mali_mapping.addr, descriptor->flags);
if (0 != err) {
MALI_DEBUG_PRINT_ERROR(("Mali DMA-buf: Failed to map dma-buf for cookie %d at mali address %x\b",
- cookie, descriptor->mali_mapping.addr));
+ cookie, descriptor->mali_mapping.addr));
ret = -EFAULT;
MALI_DEBUG_ASSERT(NULL == job->dma_bufs[i]);
continue;
mali_mem_allocation *descriptor;
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&args, (void __user *)user_arg, sizeof(_mali_uk_release_dma_buf_s)) ) {
+ if (0 != copy_from_user(&args, (void __user *)user_arg, sizeof(_mali_uk_release_dma_buf_s))) {
return -EFAULT;
}
- MALI_DEBUG_PRINT(3, ("Mali DMA-buf: release descriptor cookie %d\n", args.cookie));
+ MALI_DEBUG_PRINT(3, ("Mali DMA-buf: release descriptor cookie %ld\n", args.cookie));
_mali_osk_mutex_wait(session->memory_lock);
- descriptor = mali_descriptor_mapping_free(session->descriptor_mapping, args.cookie);
+ descriptor = mali_descriptor_mapping_free(session->descriptor_mapping, (u32)args.cookie);
if (NULL != descriptor) {
MALI_DEBUG_PRINT(3, ("Mali DMA-buf: Releasing dma-buf at mali address %x\n", descriptor->mali_mapping.addr));
mali_mem_descriptor_destroy(descriptor);
} else {
- MALI_DEBUG_PRINT_ERROR(("Invalid memory descriptor %d used to release dma-buf\n", args.cookie));
+ MALI_DEBUG_PRINT_ERROR(("Invalid memory descriptor %ld used to release dma-buf\n", args.cookie));
ret = -EINVAL;
}
struct dma_buf *buf;
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&args, (void __user *)user_arg, sizeof(_mali_uk_dma_buf_get_size_s)) ) {
+ if (0 != copy_from_user(&args, (void __user *)user_arg, sizeof(_mali_uk_dma_buf_get_size_s))) {
return -EFAULT;
}
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
+#include "mali_kernel_common.h"
#include "mali_osk.h"
+#include "mali_ukk.h"
#include "mali_memory.h"
#include "mali_kernel_descriptor_mapping.h"
#include "mali_mem_validation.h"
_mali_osk_errcode_t _mali_ukk_map_external_mem(_mali_uk_map_external_mem_s *args)
{
struct mali_session_data *session;
- mali_mem_allocation * descriptor;
+ mali_mem_allocation *descriptor;
int md;
_mali_osk_errcode_t err;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
- session = (struct mali_session_data *)args->ctx;
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
MALI_CHECK_NON_NULL(session, _MALI_OSK_ERR_INVALID_ARGS);
/* check arguments */
if (args->size % _MALI_OSK_MALI_PAGE_SIZE) MALI_ERROR(_MALI_OSK_ERR_INVALID_ARGS);
MALI_DEBUG_PRINT(3,
- ("Requested to map physical memory 0x%x-0x%x into virtual memory 0x%x\n",
- (void*)args->phys_addr,
- (void*)(args->phys_addr + args->size -1),
- (void*)args->mali_address)
- );
+ ("Requested to map physical memory 0x%x-0x%x into virtual memory 0x%x\n",
+ args->phys_addr, (args->phys_addr + args->size - 1),
+ args->mali_address));
/* Validate the mali physical range */
if (_MALI_OSK_ERR_OK != mali_mem_validation_check(args->phys_addr, args->size)) {
MALI_SUCCESS;
}
-_mali_osk_errcode_t _mali_ukk_unmap_external_mem( _mali_uk_unmap_external_mem_s *args )
+_mali_osk_errcode_t _mali_ukk_unmap_external_mem(_mali_uk_unmap_external_mem_s *args)
{
- mali_mem_allocation * descriptor;
- void* old_value;
+ mali_mem_allocation *descriptor;
+ void *old_value;
struct mali_session_data *session;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
- session = (struct mali_session_data *)args->ctx;
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
MALI_CHECK_NON_NULL(session, _MALI_OSK_ERR_INVALID_ARGS);
- if (_MALI_OSK_ERR_OK != mali_descriptor_mapping_get(session->descriptor_mapping, args->cookie, (void**)&descriptor)) {
+ if (_MALI_OSK_ERR_OK != mali_descriptor_mapping_get(session->descriptor_mapping, args->cookie, (void **)&descriptor)) {
MALI_DEBUG_PRINT(1, ("Invalid memory descriptor %d used to unmap external memory\n", args->cookie));
MALI_ERROR(_MALI_OSK_ERR_FAULT);
}
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_OS_MEMORY_KERNEL_BUFFER_SIZE_IN_PAGES (MALI_OS_MEMORY_KERNEL_BUFFER_SIZE_IN_MB * 256)
#define MALI_OS_MEMORY_POOL_TRIM_JIFFIES (10 * CONFIG_HZ) /* Default to 10s */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0)
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,35)
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
+/* Write combine dma_attrs */
+static DEFINE_DMA_ATTRS(dma_attrs_wc);
+#endif
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 0, 0)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 35)
static int mali_mem_os_shrink(int nr_to_scan, gfp_t gfp_mask);
#else
static int mali_mem_os_shrink(struct shrinker *shrinker, int nr_to_scan, gfp_t gfp_mask);
#endif
#else
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 12, 0)
static int mali_mem_os_shrink(struct shrinker *shrinker, struct shrink_control *sc);
+#else
+static unsigned long mali_mem_os_shrink(struct shrinker *shrinker, struct shrink_control *sc);
+static unsigned long mali_mem_os_shrink_count(struct shrinker *shrinker, struct shrink_control *sc);
+#endif
#endif
static void mali_mem_os_trim_pool(struct work_struct *work);
.allocated_pages = ATOMIC_INIT(0),
.allocation_limit = 0,
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 12, 0)
.shrinker.shrink = mali_mem_os_shrink,
+#else
+ .shrinker.count_objects = mali_mem_os_shrink_count,
+ .shrinker.scan_objects = mali_mem_os_shrink,
+#endif
.shrinker.seeks = DEFAULT_SEEKS,
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,7,0)
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 7, 0)
.timed_shrinker = __DELAYED_WORK_INITIALIZER(mali_mem_os_allocator.timed_shrinker, mali_mem_os_trim_pool, TIMER_DEFERRABLE),
-#elif LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
+#elif LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 38)
.timed_shrinker = __DEFERRED_WORK_INITIALIZER(mali_mem_os_allocator.timed_shrinker, mali_mem_os_trim_pool),
#else
.timed_shrinker = __DELAYED_WORK_INITIALIZER(mali_mem_os_allocator.timed_shrinker, mali_mem_os_trim_pool),
/* Allocate new pages, if needed. */
for (i = 0; i < remaining; i++) {
dma_addr_t dma_addr;
+ gfp_t flags = __GFP_ZERO | __GFP_REPEAT | __GFP_NOWARN | __GFP_COLD;
+ int err;
- new_page = alloc_page(GFP_HIGHUSER | __GFP_ZERO | __GFP_REPEAT | __GFP_NOWARN | __GFP_COLD);
+#if defined(CONFIG_ARM) && !defined(CONFIG_ARM_LPAE)
+ flags |= GFP_HIGHUSER;
+#else
+ flags |= GFP_DMA32;
+#endif
+
+ new_page = alloc_page(flags);
if (unlikely(NULL == new_page)) {
/* Calculate the number of pages actually allocated, and free them. */
/* Ensure page is flushed from CPU caches. */
dma_addr = dma_map_page(&mali_platform_device->dev, new_page,
- 0, _MALI_OSK_MALI_PAGE_SIZE, DMA_TO_DEVICE);
+ 0, _MALI_OSK_MALI_PAGE_SIZE, DMA_TO_DEVICE);
+
+ err = dma_mapping_error(&mali_platform_device->dev, dma_addr);
+ if (unlikely(err)) {
+ MALI_DEBUG_PRINT_ERROR(("OS Mem: Failed to DMA map page %p: %u",
+ new_page, err));
+ __free_page(new_page);
+ descriptor->os_mem.count = (page_count - remaining) + i;
+ atomic_add(descriptor->os_mem.count, &mali_mem_os_allocator.allocated_pages);
+ mali_mem_os_free(descriptor);
+ return -EFAULT;
+ }
/* Store page phys addr */
SetPagePrivate(new_page);
}
list_for_each_entry(page, &descriptor->os_mem.pages, lru) {
- u32 phys = page_private(page);
- mali_mmu_pagedir_update(pagedir, virt, phys, MALI_MMU_PAGE_SIZE, prop);
+ dma_addr_t phys = page_private(page);
+
+#if defined(CONFIG_ARCH_DMA_ADDR_T_64BIT)
+ /* Verify that the "physical" address is 32-bit and
+ * usable for Mali, when on a system with bus addresses
+ * wider than 32-bit. */
+ MALI_DEBUG_ASSERT(0 == (phys >> 32));
+#endif
+
+ mali_mmu_pagedir_update(pagedir, virt, (mali_dma_addr)phys, MALI_MMU_PAGE_SIZE, prop);
virt += MALI_MMU_PAGE_SIZE;
}
if (atomic_read(&mali_mem_os_allocator.allocated_pages) * _MALI_OSK_MALI_PAGE_SIZE + size > mali_mem_os_allocator.allocation_limit) {
MALI_DEBUG_PRINT(2, ("Mali Mem: Unable to allocate %u bytes. Currently allocated: %lu, max limit %lu\n",
- size,
- atomic_read(&mali_mem_os_allocator.allocated_pages) * _MALI_OSK_MALI_PAGE_SIZE,
- mali_mem_os_allocator.allocation_limit));
+ size,
+ atomic_read(&mali_mem_os_allocator.allocated_pages) * _MALI_OSK_MALI_PAGE_SIZE,
+ mali_mem_os_allocator.allocation_limit));
return NULL;
}
descriptor->mali_mapping.addr = mali_addr;
descriptor->size = size;
- descriptor->cpu_mapping.addr = (void __user*)vma->vm_start;
+ descriptor->cpu_mapping.addr = (void __user *)vma->vm_start;
descriptor->cpu_mapping.ref = 1;
if (VM_SHARED == (VM_SHARED & vma->vm_flags)) {
#define MALI_MEM_OS_PAGE_TABLE_PAGE_POOL_SIZE 128
static struct {
struct {
- u32 phys;
+ mali_dma_addr phys;
mali_io_address mapping;
} page[MALI_MEM_OS_PAGE_TABLE_PAGE_POOL_SIZE];
- u32 count;
+ size_t count;
spinlock_t lock;
} mali_mem_page_table_page_pool = {
.count = 0,
.lock = __SPIN_LOCK_UNLOCKED(pool_lock),
};
-_mali_osk_errcode_t mali_mem_os_get_table_page(u32 *phys, mali_io_address *mapping)
+_mali_osk_errcode_t mali_mem_os_get_table_page(mali_dma_addr *phys, mali_io_address *mapping)
{
_mali_osk_errcode_t ret = _MALI_OSK_ERR_NOMEM;
+ dma_addr_t tmp_phys;
spin_lock(&mali_mem_page_table_page_pool.lock);
if (0 < mali_mem_page_table_page_pool.count) {
spin_unlock(&mali_mem_page_table_page_pool.lock);
if (_MALI_OSK_ERR_OK != ret) {
- *mapping = dma_alloc_writecombine(&mali_platform_device->dev, _MALI_OSK_MALI_PAGE_SIZE, phys, GFP_KERNEL);
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
+ *mapping = dma_alloc_attrs(&mali_platform_device->dev,
+ _MALI_OSK_MALI_PAGE_SIZE, &tmp_phys,
+ GFP_KERNEL, &dma_attrs_wc);
+#else
+ *mapping = dma_alloc_writecombine(&mali_platform_device->dev,
+ _MALI_OSK_MALI_PAGE_SIZE, &tmp_phys, GFP_KERNEL);
+#endif
if (NULL != *mapping) {
ret = _MALI_OSK_ERR_OK;
+
+#if defined(CONFIG_ARCH_DMA_ADDR_T_64BIT)
+ /* Verify that the "physical" address is 32-bit and
+ * usable for Mali, when on a system with bus addresses
+ * wider than 32-bit. */
+ MALI_DEBUG_ASSERT(0 == (tmp_phys >> 32));
+#endif
+
+ *phys = (mali_dma_addr)tmp_phys;
}
}
return ret;
}
-void mali_mem_os_release_table_page(u32 phys, void *virt)
+void mali_mem_os_release_table_page(mali_dma_addr phys, void *virt)
{
spin_lock(&mali_mem_page_table_page_pool.lock);
if (MALI_MEM_OS_PAGE_TABLE_PAGE_POOL_SIZE > mali_mem_page_table_page_pool.count) {
} else {
spin_unlock(&mali_mem_page_table_page_pool.lock);
- dma_free_writecombine(&mali_platform_device->dev, _MALI_OSK_MALI_PAGE_SIZE, virt, phys);
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
+ dma_free_attrs(&mali_platform_device->dev,
+ _MALI_OSK_MALI_PAGE_SIZE, virt, phys,
+ &dma_attrs_wc);
+#else
+ dma_free_writecombine(&mali_platform_device->dev,
+ _MALI_OSK_MALI_PAGE_SIZE, virt, phys);
+#endif
}
}
BUG_ON(page_count(page) != 1);
dma_unmap_page(&mali_platform_device->dev, page_private(page),
- _MALI_OSK_MALI_PAGE_SIZE, DMA_TO_DEVICE);
+ _MALI_OSK_MALI_PAGE_SIZE, DMA_TO_DEVICE);
ClearPagePrivate(page);
*/
static void mali_mem_os_page_table_pool_free(size_t nr_to_free)
{
- u32 phys_arr[MALI_MEM_OS_CHUNK_TO_FREE];
+ mali_dma_addr phys_arr[MALI_MEM_OS_CHUNK_TO_FREE];
void *virt_arr[MALI_MEM_OS_CHUNK_TO_FREE];
u32 i;
/* After releasing the spinlock: free the pages we removed from the pool. */
for (i = 0; i < nr_to_free; i++) {
- dma_free_writecombine(&mali_platform_device->dev, _MALI_OSK_MALI_PAGE_SIZE, virt_arr[i], phys_arr[i]);
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
+ dma_free_attrs(&mali_platform_device->dev, _MALI_OSK_MALI_PAGE_SIZE,
+ virt_arr[i], (dma_addr_t)phys_arr[i], &dma_attrs_wc);
+#else
+ dma_free_writecombine(&mali_platform_device->dev,
+ _MALI_OSK_MALI_PAGE_SIZE,
+ virt_arr[i], (dma_addr_t)phys_arr[i]);
+#endif
}
}
mali_mem_os_page_table_pool_free(nr_to_free);
}
-#if LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0)
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,35)
+static unsigned long mali_mem_os_shrink_count(struct shrinker *shrinker, struct shrink_control *sc)
+{
+ return mali_mem_os_allocator.pool_count + mali_mem_page_table_page_pool.count;
+}
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 0, 0)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 35)
static int mali_mem_os_shrink(int nr_to_scan, gfp_t gfp_mask)
#else
static int mali_mem_os_shrink(struct shrinker *shrinker, int nr_to_scan, gfp_t gfp_mask)
-#endif
+#endif /* Linux < 2.6.35 */
#else
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 12, 0)
static int mali_mem_os_shrink(struct shrinker *shrinker, struct shrink_control *sc)
-#endif
+#else
+static unsigned long mali_mem_os_shrink(struct shrinker *shrinker, struct shrink_control *sc)
+#endif /* Linux < 3.12.0 */
+#endif /* Linux < 3.0.0 */
{
struct page *page, *tmp;
unsigned long flags;
struct list_head *le, pages;
-#if LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 0, 0)
int nr = nr_to_scan;
#else
int nr = sc->nr_to_scan;
#endif
if (0 == nr) {
- return mali_mem_os_allocator.pool_count + mali_mem_page_table_page_pool.count;
- }
-
- if (0 == mali_mem_os_allocator.pool_count) {
- /* No pages availble */
- return 0;
+ return mali_mem_os_shrink_count(shrinker, sc);
}
if (0 == spin_trylock_irqsave(&mali_mem_os_allocator.pool_lock, flags)) {
return -1;
}
+ if (0 == mali_mem_os_allocator.pool_count) {
+ /* No pages availble */
+ spin_unlock_irqrestore(&mali_mem_os_allocator.pool_lock, flags);
+ return 0;
+ }
+
/* Release from general page pool */
nr = min((size_t)nr, mali_mem_os_allocator.pool_count);
mali_mem_os_allocator.pool_count -= nr;
spin_lock(&mali_mem_os_allocator.pool_lock);
if (MALI_OS_MEMORY_KERNEL_BUFFER_SIZE_IN_PAGES < mali_mem_os_allocator.pool_count) {
size_t count = mali_mem_os_allocator.pool_count - MALI_OS_MEMORY_KERNEL_BUFFER_SIZE_IN_PAGES;
+ const size_t min_to_free = min(64, MALI_OS_MEMORY_KERNEL_BUFFER_SIZE_IN_PAGES);
+
/* Free half the pages on the pool above the static limit. Or 64 pages, 256KB. */
- nr_to_free = max(count / 2, (size_t)64);
+ nr_to_free = max(count / 2, min_to_free);
mali_mem_os_allocator.pool_count -= nr_to_free;
list_for_each(le, &mali_mem_os_allocator.pool_pages) {
return _MALI_OSK_ERR_NOMEM;
}
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 8, 0)
+ dma_set_attr(DMA_ATTR_WRITE_COMBINE, &dma_attrs_wc);
+#endif
+
register_shrinker(&mali_mem_os_allocator.shrinker);
return _MALI_OSK_ERR_OK;
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*/
void mali_mem_os_release(mali_mem_allocation *descriptor);
-_mali_osk_errcode_t mali_mem_os_get_table_page(u32 *phys, mali_io_address *mapping);
+_mali_osk_errcode_t mali_mem_os_get_table_page(mali_dma_addr *phys, mali_io_address *mapping);
-void mali_mem_os_release_table_page(u32 phys, void *virt);
+void mali_mem_os_release_table_page(mali_dma_addr phys, void *virt);
_mali_osk_errcode_t mali_mem_os_init(void);
void mali_mem_os_term(void);
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
return -EINVAL;
}
- ump_blocks = _mali_osk_malloc(sizeof(*ump_blocks)*nr_blocks);
+ ump_blocks = _mali_osk_malloc(sizeof(*ump_blocks) * nr_blocks);
if (NULL == ump_blocks) {
return -ENOMEM;
}
return -ENOMEM;
}
- for(i = 0; i < nr_blocks; ++i) {
+ for (i = 0; i < nr_blocks; ++i) {
u32 virt = descriptor->mali_mapping.addr + offset;
MALI_DEBUG_PRINT(7, ("Mapping in 0x%08x size %d\n", ump_blocks[i].addr , ump_blocks[i].size));
mali_mmu_pagedir_update(pagedir, virt, ump_blocks[i].addr,
- ump_blocks[i].size, prop);
+ ump_blocks[i].size, prop);
offset += ump_blocks[i].size;
}
int md, ret;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
- session = (struct mali_session_data *)args->ctx;
- MALI_CHECK_NON_NULL(session, _MALI_OSK_ERR_INVALID_ARGS);
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
/* check arguments */
/* NULL might be a valid Mali address */
if (args->size % _MALI_OSK_MALI_PAGE_SIZE) MALI_ERROR(_MALI_OSK_ERR_INVALID_ARGS);
MALI_DEBUG_PRINT(3,
- ("Requested to map ump memory with secure id %d into virtual memory 0x%08X, size 0x%08X\n",
- args->secure_id, args->mali_address, args->size));
+ ("Requested to map ump memory with secure id %d into virtual memory 0x%08X, size 0x%08X\n",
+ args->secure_id, args->mali_address, args->size));
ump_mem = ump_dd_handle_create_from_secure_id((int)args->secure_id);
args->cookie = md;
- MALI_DEBUG_PRINT(5,("Returning from UMP attach\n"));
+ MALI_DEBUG_PRINT(5, ("Returning from UMP attach\n"));
MALI_SUCCESS;
}
_mali_osk_errcode_t _mali_ukk_release_ump_mem(_mali_uk_release_ump_mem_s *args)
{
- mali_mem_allocation * descriptor;
+ mali_mem_allocation *descriptor;
struct mali_session_data *session;
MALI_DEBUG_ASSERT_POINTER(args);
- MALI_CHECK_NON_NULL(args->ctx, _MALI_OSK_ERR_INVALID_ARGS);
+ MALI_DEBUG_ASSERT(NULL != (void *)(uintptr_t)args->ctx);
- session = (struct mali_session_data *)args->ctx;
- MALI_CHECK_NON_NULL(session, _MALI_OSK_ERR_INVALID_ARGS);
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
- if (_MALI_OSK_ERR_OK != mali_descriptor_mapping_get(session->descriptor_mapping, args->cookie, (void**)&descriptor)) {
+ if (_MALI_OSK_ERR_OK != mali_descriptor_mapping_get(session->descriptor_mapping, args->cookie, (void **)&descriptor)) {
MALI_DEBUG_PRINT(1, ("Invalid memory descriptor %d used to release ump memory\n", args->cookie));
MALI_ERROR(_MALI_OSK_ERR_FAULT);
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include <asm/atomic.h>
#include "mali_kernel_common.h"
-void _mali_osk_atomic_dec( _mali_osk_atomic_t *atom )
+void _mali_osk_atomic_dec(_mali_osk_atomic_t *atom)
{
atomic_dec((atomic_t *)&atom->u.val);
}
-u32 _mali_osk_atomic_dec_return( _mali_osk_atomic_t *atom )
+u32 _mali_osk_atomic_dec_return(_mali_osk_atomic_t *atom)
{
return atomic_dec_return((atomic_t *)&atom->u.val);
}
-void _mali_osk_atomic_inc( _mali_osk_atomic_t *atom )
+void _mali_osk_atomic_inc(_mali_osk_atomic_t *atom)
{
atomic_inc((atomic_t *)&atom->u.val);
}
-u32 _mali_osk_atomic_inc_return( _mali_osk_atomic_t *atom )
+u32 _mali_osk_atomic_inc_return(_mali_osk_atomic_t *atom)
{
return atomic_inc_return((atomic_t *)&atom->u.val);
}
-_mali_osk_errcode_t _mali_osk_atomic_init( _mali_osk_atomic_t *atom, u32 val )
+_mali_osk_errcode_t _mali_osk_atomic_init(_mali_osk_atomic_t *atom, u32 val)
{
MALI_CHECK_NON_NULL(atom, _MALI_OSK_ERR_INVALID_ARGS);
atomic_set((atomic_t *)&atom->u.val, val);
return _MALI_OSK_ERR_OK;
}
-u32 _mali_osk_atomic_read( _mali_osk_atomic_t *atom )
+u32 _mali_osk_atomic_read(_mali_osk_atomic_t *atom)
{
return atomic_read((atomic_t *)&atom->u.val);
}
-void _mali_osk_atomic_term( _mali_osk_atomic_t *atom )
+void _mali_osk_atomic_term(_mali_osk_atomic_t *atom)
{
MALI_IGNORE(atom);
}
-u32 _mali_osk_atomic_xchg( _mali_osk_atomic_t *atom, u32 val )
+u32 _mali_osk_atomic_xchg(_mali_osk_atomic_t *atom, u32 val)
{
- return atomic_xchg((atomic_t*)&atom->u.val, val);
+ return atomic_xchg((atomic_t *)&atom->u.val, val);
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
} mali_osk_irq_object_t;
typedef irqreturn_t (*irq_handler_func_t)(int, void *, struct pt_regs *);
-static irqreturn_t irq_handler_upper_half (int port_name, void* dev_id ); /* , struct pt_regs *regs*/
+static irqreturn_t irq_handler_upper_half(int port_name, void *dev_id); /* , struct pt_regs *regs*/
#if MESON_CPU_TYPE == MESON_CPU_TYPE_MESON6
u32 get_irqnum(struct _mali_osk_irq_t_struct* irq)
#endif
#if defined(DEBUG)
-#if 0
struct test_interrupt_data {
_mali_osk_irq_ack_t ack_func;
}
static _mali_osk_errcode_t test_interrupt(u32 irqnum,
- _mali_osk_irq_trigger_t trigger_func,
- _mali_osk_irq_ack_t ack_func,
- void *probe_data,
- const char *description)
+ _mali_osk_irq_trigger_t trigger_func,
+ _mali_osk_irq_ack_t ack_func,
+ void *probe_data,
+ const char *description)
{
unsigned long irq_flags = 0;
struct test_interrupt_data data = {
return _MALI_OSK_ERR_FAULT;
}
}
-#endif
#endif /* defined(DEBUG) */
-_mali_osk_irq_t *_mali_osk_irq_init( u32 irqnum, _mali_osk_irq_uhandler_t uhandler, void *int_data, _mali_osk_irq_trigger_t trigger_func, _mali_osk_irq_ack_t ack_func, void *probe_data, const char *description )
+_mali_osk_irq_t *_mali_osk_irq_init(u32 irqnum, _mali_osk_irq_uhandler_t uhandler, void *int_data, _mali_osk_irq_trigger_t trigger_func, _mali_osk_irq_ack_t ack_func, void *probe_data, const char *description)
{
mali_osk_irq_object_t *irq_object;
unsigned long irq_flags = 0;
if (-1 == irqnum) {
/* Probe for IRQ */
- if ( (NULL != trigger_func) && (NULL != ack_func) ) {
+ if ((NULL != trigger_func) && (NULL != ack_func)) {
unsigned long probe_count = 3;
_mali_osk_errcode_t err;
int irq;
}
#if defined(DEBUG)
-#if 0
/* Verify that the configured interrupt settings are working */
if (_MALI_OSK_ERR_OK != test_interrupt(irqnum, trigger_func, ack_func, probe_data, description)) {
MALI_DEBUG_PRINT(2, ("Test of IRQ handler for core '%s' failed\n", description));
kfree(irq_object);
return NULL;
}
-#endif
#endif
if (0 != request_irq(irqnum, irq_handler_upper_half, irq_flags, description, irq_object)) {
return irq_object;
}
-void _mali_osk_irq_term( _mali_osk_irq_t *irq )
+void _mali_osk_irq_term(_mali_osk_irq_t *irq)
{
mali_osk_irq_object_t *irq_object = (mali_osk_irq_object_t *)irq;
free_irq(irq_object->irqnum, irq_object);
* Then we schedule the mali_core_irq_handler_bottom_half to run as high priority
* work queue job.
*/
-static irqreturn_t irq_handler_upper_half (int port_name, void* dev_id ) /* , struct pt_regs *regs*/
+static irqreturn_t irq_handler_upper_half(int port_name, void *dev_id) /* , struct pt_regs *regs*/
{
irqreturn_t ret = IRQ_NONE;
mali_osk_irq_object_t *irq_object = (mali_osk_irq_object_t *)dev_id;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
static DEFINE_SPINLOCK(lock_tracking_lock);
static mali_bool add_lock_to_log_and_check(struct _mali_osk_lock_debug_s *lock, uint32_t tid);
static void remove_lock_from_log(struct _mali_osk_lock_debug_s *lock, uint32_t tid);
-static const char * const lock_order_to_string(_mali_osk_lock_order_t order);
+static const char *const lock_order_to_string(_mali_osk_lock_order_t order);
#endif /* LOCK_ORDER_CHECKING */
void _mali_osk_locks_debug_init(struct _mali_osk_lock_debug_s *checker, _mali_osk_lock_flags_t flags, _mali_osk_lock_order_t order)
/* Traverse the locks taken and find the lock of the highest order.
* Since several threads may hold locks, each lock's owner must be
* checked so that locks not owned by this thread can be ignored. */
- for(;;) {
- MALI_DEBUG_ASSERT_POINTER( l );
+ for (;;) {
+ MALI_DEBUG_ASSERT_POINTER(l);
if (tid == l->owner && l->order >= highest_order_for_tid) {
highest_order_for_tid = l->order;
highest_order_lock = l;
dump_lock_tracking_list();
}
- if (len+1 != tracking_list_length()) {
+ if (len + 1 != tracking_list_length()) {
printk(KERN_ERR "************ lock: %p\n", lock);
printk(KERN_ERR "************ before: %d *** after: %d ****\n", len, tracking_list_length());
dump_lock_tracking_list();
lock->next = NULL;
- if (len-1 != tracking_list_length()) {
+ if (len - 1 != tracking_list_length()) {
printk(KERN_ERR "************ lock: %p\n", lock);
printk(KERN_ERR "************ before: %d *** after: %d ****\n", len, tracking_list_length());
dump_lock_tracking_list();
spin_unlock_irqrestore(&lock_tracking_lock, local_lock_flag);
}
-static const char * const lock_order_to_string(_mali_osk_lock_order_t order)
+static const char *const lock_order_to_string(_mali_osk_lock_order_t order)
{
switch (order) {
case _MALI_OSK_LOCK_ORDER_SESSIONS:
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
void _mali_osk_locks_debug_add(struct _mali_osk_lock_debug_s *checker);
void _mali_osk_locks_debug_remove(struct _mali_osk_lock_debug_s *checker);
- /** @brief This function can return a given lock's owner when DEBUG is enabled. */
+ /** @brief This function can return a given lock's owner when DEBUG is enabled. */
static inline u32 _mali_osk_lock_get_owner(struct _mali_osk_lock_debug_s *lock)
{
return lock->owner;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_osk.h"
#include "mali_ukk.h"
-void _mali_osk_mem_barrier( void )
+void _mali_osk_mem_barrier(void)
{
mb();
}
-void _mali_osk_write_mem_barrier( void )
+void _mali_osk_write_mem_barrier(void)
{
wmb();
}
-mali_io_address _mali_osk_mem_mapioregion( u32 phys, u32 size, const char *description )
+mali_io_address _mali_osk_mem_mapioregion(u32 phys, u32 size, const char *description)
{
return (mali_io_address)ioremap_nocache(phys, size);
}
-void _mali_osk_mem_unmapioregion( u32 phys, u32 size, mali_io_address virt )
+void _mali_osk_mem_unmapioregion(u32 phys, u32 size, mali_io_address virt)
{
- iounmap((void*)virt);
+ iounmap((void *)virt);
}
-_mali_osk_errcode_t inline _mali_osk_mem_reqregion( u32 phys, u32 size, const char *description )
+_mali_osk_errcode_t inline _mali_osk_mem_reqregion(u32 phys, u32 size, const char *description)
{
#if MALI_LICENSE_IS_GPL
return _MALI_OSK_ERR_OK; /* GPL driver gets the mem region for the resources registered automatically */
#endif
}
-void inline _mali_osk_mem_unreqregion( u32 phys, u32 size )
+void inline _mali_osk_mem_unreqregion(u32 phys, u32 size)
{
#if !MALI_LICENSE_IS_GPL
release_mem_region(phys, size);
#endif
}
-void inline _mali_osk_mem_iowrite32_relaxed( volatile mali_io_address addr, u32 offset, u32 val )
+void inline _mali_osk_mem_iowrite32_relaxed(volatile mali_io_address addr, u32 offset, u32 val)
{
- __raw_writel(cpu_to_le32(val),((u8*)addr) + offset);
+ __raw_writel(cpu_to_le32(val), ((u8 *)addr) + offset);
}
-u32 inline _mali_osk_mem_ioread32( volatile mali_io_address addr, u32 offset )
+u32 inline _mali_osk_mem_ioread32(volatile mali_io_address addr, u32 offset)
{
- return ioread32(((u8*)addr) + offset);
+ return ioread32(((u8 *)addr) + offset);
}
-void inline _mali_osk_mem_iowrite32( volatile mali_io_address addr, u32 offset, u32 val )
+void inline _mali_osk_mem_iowrite32(volatile mali_io_address addr, u32 offset, u32 val)
{
- iowrite32(val, ((u8*)addr) + offset);
+ iowrite32(val, ((u8 *)addr) + offset);
}
-void _mali_osk_cache_flushall( void )
+void _mali_osk_cache_flushall(void)
{
/** @note Cached memory is not currently supported in this implementation */
}
-void _mali_osk_cache_ensure_uncached_range_flushed( void *uncached_mapping, u32 offset, u32 size )
+void _mali_osk_cache_ensure_uncached_range_flushed(void *uncached_mapping, u32 offset, u32 size)
{
_mali_osk_write_mem_barrier();
}
-u32 _mali_osk_mem_write_safe(void *dest, const void *src, u32 size)
+u32 _mali_osk_mem_write_safe(void __user *dest, const void __user *src, u32 size)
{
#define MALI_MEM_SAFE_COPY_BLOCK_SIZE 4096
u32 retval = 0;
size_to_copy = bytes_left_to_copy;
}
- bytes_left = copy_from_user(temp_buf, ((char*)src) + i, size_to_copy);
+ bytes_left = copy_from_user(temp_buf, ((char *)src) + i, size_to_copy);
size_copied = size_to_copy - bytes_left;
- bytes_left = copy_to_user(((char*)dest) + i, temp_buf, size_copied);
+ bytes_left = copy_to_user(((char *)dest) + i, temp_buf, size_copied);
size_copied -= bytes_left;
bytes_left_to_copy -= size_copied;
_mali_osk_errcode_t _mali_ukk_mem_write_safe(_mali_uk_mem_write_safe_s *args)
{
+ void __user *src;
+ void __user *dst;
+ struct mali_session_data *session;
+
MALI_DEBUG_ASSERT_POINTER(args);
- if (NULL == args->ctx) {
+ session = (struct mali_session_data *)(uintptr_t)args->ctx;
+
+ if (NULL == session) {
return _MALI_OSK_ERR_INVALID_ARGS;
}
+ src = (void __user *)(uintptr_t)args->src;
+ dst = (void __user *)(uintptr_t)args->dest;
+
/* Return number of bytes actually copied */
- args->size = _mali_osk_mem_write_safe(args->dest, args->src, args->size);
+ args->size = _mali_osk_mem_write_safe(dst, src, args->size);
return _MALI_OSK_ERR_OK;
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/* Any (optional) IRQ resource belonging to this resource will follow */
if ((i + 1) < mali_platform_device->num_resources &&
- IORESOURCE_IRQ == resource_type(&(mali_platform_device->resource[i+1]))) {
- res->irq = mali_platform_device->resource[i+1].start;
+ IORESOURCE_IRQ == resource_type(&(mali_platform_device->resource[i + 1]))) {
+ res->irq = mali_platform_device->resource[i + 1].start;
} else {
res->irq = -1;
}
return ret;
}
-_mali_osk_errcode_t _mali_osk_device_data_get(struct _mali_osk_device_data *data)
+_mali_osk_errcode_t _mali_osk_device_data_get(_mali_osk_device_data *data)
{
MALI_DEBUG_ASSERT_POINTER(data);
if (NULL != mali_platform_device) {
- struct mali_gpu_device_data* os_data = NULL;
+ struct mali_gpu_device_data *os_data = NULL;
- os_data = (struct mali_gpu_device_data*)mali_platform_device->dev.platform_data;
+ os_data = (struct mali_gpu_device_data *)mali_platform_device->dev.platform_data;
if (NULL != os_data) {
/* Copy data from OS dependant struct to Mali neutral struct (identical!) */
- data->dedicated_mem_start = os_data->dedicated_mem_start;
- data->dedicated_mem_size = os_data->dedicated_mem_size;
- data->shared_mem_size = os_data->shared_mem_size;
- data->fb_start = os_data->fb_start;
- data->fb_size = os_data->fb_size;
- data->max_job_runtime = os_data->max_job_runtime;
- data->utilization_interval = os_data->utilization_interval;
- data->utilization_callback = os_data->utilization_callback;
- data->pmu_switch_delay = os_data->pmu_switch_delay;
- data->set_freq_callback = os_data->set_freq_callback;
-
- memcpy(data->pmu_domain_config, os_data->pmu_domain_config, sizeof(os_data->pmu_domain_config));
+ BUILD_BUG_ON(sizeof(*os_data) != sizeof(*data));
+ _mali_osk_memcpy(data, os_data, sizeof(*os_data));
+
return _MALI_OSK_ERR_OK;
}
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_osk.h"
#include <linux/bitops.h>
-u32 _mali_osk_clz( u32 input )
+u32 _mali_osk_clz(u32 input)
{
- return 32-fls(input);
+ return 32 - fls(input);
}
-u32 _mali_osk_fls( u32 input )
+u32 _mali_osk_fls(u32 input)
{
return fls(input);
}
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include <linux/slab.h>
#include <linux/vmalloc.h>
-void inline *_mali_osk_calloc( u32 n, u32 size )
+void inline *_mali_osk_calloc(u32 n, u32 size)
{
return kcalloc(n, size, GFP_KERNEL);
}
-void inline *_mali_osk_malloc( u32 size )
+void inline *_mali_osk_malloc(u32 size)
{
return kmalloc(size, GFP_KERNEL);
}
-void inline _mali_osk_free( void *ptr )
+void inline _mali_osk_free(void *ptr)
{
kfree(ptr);
}
-void inline *_mali_osk_valloc( u32 size )
+void inline *_mali_osk_valloc(u32 size)
{
return vmalloc(size);
}
-void inline _mali_osk_vfree( void *ptr )
+void inline _mali_osk_vfree(void *ptr)
{
vfree(ptr);
}
-void inline *_mali_osk_memcpy( void *dst, const void *src, u32 len )
+void inline *_mali_osk_memcpy(void *dst, const void *src, u32 len)
{
return memcpy(dst, src, len);
}
-void inline *_mali_osk_memset( void *s, u32 c, u32 n )
+void inline *_mali_osk_memset(void *s, u32 c, u32 n)
{
return memset(s, c, n);
}
-mali_bool _mali_osk_mem_check_allocated( u32 max_allocated )
+mali_bool _mali_osk_mem_check_allocated(u32 max_allocated)
{
/* No need to prevent an out-of-memory dialogue appearing on Linux,
* so we always return MALI_TRUE.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include <asm/uaccess.h>
#include <asm/cacheflush.h>
#include <linux/sched.h>
+#include <linux/seq_file.h>
#include <linux/module.h>
#include "mali_osk.h"
-void _mali_osk_dbgmsg( const char *fmt, ... )
+#if !defined(CONFIG_MALI_QUIET)
+void _mali_osk_dbgmsg(const char *fmt, ...)
{
va_list args;
va_start(args, fmt);
vprintk(fmt, args);
va_end(args);
}
+#endif /* !defined(CONFIG_MALI_QUIET) */
-u32 _mali_osk_snprintf( char *buf, u32 size, const char *fmt, ... )
+u32 _mali_osk_snprintf(char *buf, u32 size, const char *fmt, ...)
{
int res;
va_list args;
return res;
}
+void _mali_osk_ctxprintf(_mali_osk_print_ctx *print_ctx, const char *fmt, ...)
+{
+ va_list args;
+ char buf[512];
+
+ va_start(args, fmt);
+ vscnprintf(buf,512,fmt,args);
+ seq_printf(print_ctx,buf);
+ va_end(args);
+}
+
void _mali_osk_abort(void)
{
/* make a simple fault by dereferencing a NULL pointer */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_notification_t data; /**< Notification data */
} _mali_osk_notification_wrapper_t;
-_mali_osk_notification_queue_t *_mali_osk_notification_queue_init( void )
+_mali_osk_notification_queue_t *_mali_osk_notification_queue_init(void)
{
- _mali_osk_notification_queue_t * result;
+ _mali_osk_notification_queue_t *result;
result = (_mali_osk_notification_queue_t *)kmalloc(sizeof(_mali_osk_notification_queue_t), GFP_KERNEL);
if (NULL == result) return NULL;
return result;
}
-_mali_osk_notification_t *_mali_osk_notification_create( u32 type, u32 size )
+_mali_osk_notification_t *_mali_osk_notification_create(u32 type, u32 size)
{
/* OPT Recycling of notification objects */
_mali_osk_notification_wrapper_t *notification;
- notification = (_mali_osk_notification_wrapper_t *)kmalloc( sizeof(_mali_osk_notification_wrapper_t) + size,
- GFP_KERNEL | __GFP_HIGH | __GFP_REPEAT);
+ notification = (_mali_osk_notification_wrapper_t *)kmalloc(sizeof(_mali_osk_notification_wrapper_t) + size,
+ GFP_KERNEL | __GFP_HIGH | __GFP_REPEAT);
if (NULL == notification) {
MALI_DEBUG_PRINT(1, ("Failed to create a notification object\n"));
return NULL;
INIT_LIST_HEAD(¬ification->list);
if (0 != size) {
- notification->data.result_buffer = ((u8*)notification) + sizeof(_mali_osk_notification_wrapper_t);
+ notification->data.result_buffer = ((u8 *)notification) + sizeof(_mali_osk_notification_wrapper_t);
} else {
notification->data.result_buffer = NULL;
}
return &(notification->data);
}
-void _mali_osk_notification_delete( _mali_osk_notification_t *object )
+void _mali_osk_notification_delete(_mali_osk_notification_t *object)
{
_mali_osk_notification_wrapper_t *notification;
- MALI_DEBUG_ASSERT_POINTER( object );
+ MALI_DEBUG_ASSERT_POINTER(object);
- notification = container_of( object, _mali_osk_notification_wrapper_t, data );
+ notification = container_of(object, _mali_osk_notification_wrapper_t, data);
/* Free the container */
kfree(notification);
}
-void _mali_osk_notification_queue_term( _mali_osk_notification_queue_t *queue )
+void _mali_osk_notification_queue_term(_mali_osk_notification_queue_t *queue)
{
_mali_osk_notification_t *result;
- MALI_DEBUG_ASSERT_POINTER( queue );
+ MALI_DEBUG_ASSERT_POINTER(queue);
while (_MALI_OSK_ERR_OK == _mali_osk_notification_queue_dequeue(queue, &result)) {
- _mali_osk_notification_delete( result );
+ _mali_osk_notification_delete(result);
}
/* not much to do, just free the memory */
kfree(queue);
}
-void _mali_osk_notification_queue_send( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t *object )
+void _mali_osk_notification_queue_send(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t *object)
{
#if defined(MALI_UPPER_HALF_SCHEDULING)
unsigned long irq_flags;
#endif
_mali_osk_notification_wrapper_t *notification;
- MALI_DEBUG_ASSERT_POINTER( queue );
- MALI_DEBUG_ASSERT_POINTER( object );
+ MALI_DEBUG_ASSERT_POINTER(queue);
+ MALI_DEBUG_ASSERT_POINTER(object);
- notification = container_of( object, _mali_osk_notification_wrapper_t, data );
+ notification = container_of(object, _mali_osk_notification_wrapper_t, data);
#if defined(MALI_UPPER_HALF_SCHEDULING)
spin_lock_irqsave(&queue->mutex, irq_flags);
wake_up(&queue->receive_queue);
}
-_mali_osk_errcode_t _mali_osk_notification_queue_dequeue( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result )
+_mali_osk_errcode_t _mali_osk_notification_queue_dequeue(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result)
{
#if defined(MALI_UPPER_HALF_SCHEDULING)
unsigned long irq_flags;
return ret;
}
-_mali_osk_errcode_t _mali_osk_notification_queue_receive( _mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result )
+_mali_osk_errcode_t _mali_osk_notification_queue_receive(_mali_osk_notification_queue_t *queue, _mali_osk_notification_t **result)
{
/* check input */
- MALI_DEBUG_ASSERT_POINTER( queue );
- MALI_DEBUG_ASSERT_POINTER( result );
+ MALI_DEBUG_ASSERT_POINTER(queue);
+ MALI_DEBUG_ASSERT_POINTER(result);
/* default result */
*result = NULL;
if (wait_event_interruptible(queue->receive_queue,
- _MALI_OSK_ERR_OK == _mali_osk_notification_queue_dequeue(queue, result))) {
+ _MALI_OSK_ERR_OK == _mali_osk_notification_queue_dequeue(queue, result))) {
return _MALI_OSK_ERR_RESTARTSYSCALL;
}
/**
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
int err;
MALI_DEBUG_ASSERT_POINTER(mali_platform_device);
err = pm_runtime_get_sync(&(mali_platform_device->dev));
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 37))
pm_runtime_mark_last_busy(&(mali_platform_device->dev));
#endif
if (0 > err) {
#ifdef CONFIG_PM_RUNTIME
MALI_DEBUG_ASSERT_POINTER(mali_platform_device);
_mali_osk_atomic_dec(&mali_pm_ref_count);
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 37))
pm_runtime_mark_last_busy(&(mali_platform_device->dev));
pm_runtime_put_autosuspend(&(mali_platform_device->dev));
#else
{
#ifdef CONFIG_PM_RUNTIME
MALI_DEBUG_ASSERT_POINTER(mali_platform_device);
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 37))
pm_runtime_put_autosuspend(&(mali_platform_device->dev));
#else
pm_runtime_put(&(mali_platform_device->dev));
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/* Nothing to do */
}
-_mali_osk_errcode_t _mali_osk_profiling_start(u32 * limit)
-{
- /* Nothing to do */
- return _MALI_OSK_ERR_OK;
-}
-
-_mali_osk_errcode_t _mali_osk_profiling_stop(u32 *count)
-{
- /* Nothing to do */
- return _MALI_OSK_ERR_OK;
-}
-
-u32 _mali_osk_profiling_get_count(void)
-{
- return 0;
-}
-
-_mali_osk_errcode_t _mali_osk_profiling_get_event(u32 index, u64* timestamp, u32* event_id, u32 data[5])
-{
- /* Nothing to do */
- return _MALI_OSK_ERR_OK;
-}
-
-_mali_osk_errcode_t _mali_osk_profiling_clear(void)
-{
- /* Nothing to do */
- return _MALI_OSK_ERR_OK;
-}
-
-mali_bool _mali_osk_profiling_is_recording(void)
-{
- return MALI_FALSE;
-}
-
-mali_bool _mali_osk_profiling_have_recording(void)
-{
- return MALI_FALSE;
-}
-
void _mali_osk_profiling_report_sw_counters(u32 *counters)
{
trace_mali_sw_counters(_mali_osk_get_pid(), _mali_osk_get_tid(), NULL, counters);
}
-
-_mali_osk_errcode_t _mali_ukk_profiling_start(_mali_uk_profiling_start_s *args)
+void _mali_osk_profiling_memory_usage_get(u32 *memory_usage)
{
- return _mali_osk_profiling_start(&args->limit);
+ *memory_usage = _mali_ukk_report_memory_usage();
}
_mali_osk_errcode_t _mali_ukk_profiling_add_event(_mali_uk_profiling_add_event_s *args)
return _MALI_OSK_ERR_OK;
}
-_mali_osk_errcode_t _mali_ukk_profiling_stop(_mali_uk_profiling_stop_s *args)
+_mali_osk_errcode_t _mali_ukk_sw_counters_report(_mali_uk_sw_counters_report_s *args)
{
- return _mali_osk_profiling_stop(&args->count);
-}
+ u32 *counters = (u32 *)(uintptr_t)args->counters;
-_mali_osk_errcode_t _mali_ukk_profiling_get_event(_mali_uk_profiling_get_event_s *args)
-{
- return _mali_osk_profiling_get_event(args->index, &args->timestamp, &args->event_id, args->data);
-}
+ _mali_osk_profiling_report_sw_counters(counters);
-_mali_osk_errcode_t _mali_ukk_profiling_clear(_mali_uk_profiling_clear_s *args)
-{
- return _mali_osk_profiling_clear();
+ return _MALI_OSK_ERR_OK;
}
-_mali_osk_errcode_t _mali_ukk_sw_counters_report(_mali_uk_sw_counters_report_s *args)
+_mali_osk_errcode_t _mali_ukk_profiling_memory_usage_get(_mali_uk_profiling_memory_usage_get_s *args)
{
- _mali_osk_profiling_report_sw_counters(args->counters);
+ _mali_osk_profiling_memory_usage_get(&args->memory_usage);
return _MALI_OSK_ERR_OK;
}
}
} else if (COUNTER_L2_0_C0 <= counter_id && COUNTER_L2_2_C1 >= counter_id) {
u32 core_id = (counter_id - COUNTER_L2_0_C0) >> 1;
- struct mali_l2_cache_core* l2_cache_core = mali_l2_cache_core_get_glob_l2_core(core_id);
+ struct mali_l2_cache_core *l2_cache_core = mali_l2_cache_core_get_glob_l2_core(core_id);
if (NULL != l2_cache_core) {
u32 counter_src = (counter_id - COUNTER_L2_0_C0) & 1;
if (MALI_TRUE == mali_l2_cache_lock_power_state(l2_cache)) {
/* It is now safe to access the L2 cache core in order to retrieve the counters */
mali_l2_cache_core_get_counter_values(l2_cache,
- &values->cores[i].source0,
- &values->cores[i].value0,
- &values->cores[i].source1,
- &values->cores[i].value1);
+ &values->cores[i].source0,
+ &values->cores[i].value0,
+ &values->cores[i].source1,
+ &values->cores[i].value1);
} else {
/* The core was not available, set the right bit in the mask. */
ret |= (1 << i);
*/
void _mali_profiling_control(u32 action, u32 value)
{
- switch(action) {
+ switch (action) {
case FBDUMP_CONTROL_ENABLE:
mali_set_user_setting(_MALI_UK_USER_SETTING_COLORBUFFER_CAPTURE_ENABLED, (value == 0 ? MALI_FALSE : MALI_TRUE));
break;
mali_set_user_setting(_MALI_UK_USER_SETTING_BUFFER_CAPTURE_RESIZE_FACTOR, value);
break;
default:
- break; /* Ignore unimplemented actions */
+ break; /* Ignore unimplemented actions */
}
}
values->num_of_vp_cores = 1;
}
+
EXPORT_SYMBOL(_mali_profiling_set_event);
EXPORT_SYMBOL(_mali_profiling_get_l2_counters);
EXPORT_SYMBOL(_mali_profiling_control);
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI_STATIC_INLINE static inline
#define MALI_NON_STATIC_INLINE inline
-typedef struct dma_pool * mali_dma_pool;
+typedef struct dma_pool *mali_dma_pool;
+
+typedef u32 mali_dma_addr;
MALI_STATIC_INLINE mali_dma_pool mali_dma_pool_create(u32 size, u32 alignment, u32 boundary)
{
- return dma_pool_create("mali-dma", &mali_platform_device->dev, size, alignment, boundary);
+ return dma_pool_create("mali-dma", &mali_platform_device->dev,
+ (size_t)size, (size_t)alignment, (size_t)boundary);
}
MALI_STATIC_INLINE void mali_dma_pool_destroy(mali_dma_pool pool)
dma_pool_destroy(pool);
}
-MALI_STATIC_INLINE mali_io_address mali_dma_pool_alloc(mali_dma_pool pool, u32 *phys_addr)
+MALI_STATIC_INLINE mali_io_address mali_dma_pool_alloc(mali_dma_pool pool, mali_dma_addr *phys_addr)
{
- return dma_pool_alloc(pool, GFP_KERNEL, phys_addr);
+ void *ret;
+ dma_addr_t phys;
+
+ ret = dma_pool_alloc(pool, GFP_KERNEL, &phys);
+#if defined(CONFIG_ARCH_DMA_ADDR_T_64BIT)
+ /* Verify that the "physical" address is 32-bit and
+ * usable for Mali, when on a system with bus addresses
+ * wider than 32-bit. */
+ BUG_ON(0 != (phys >> 32));
+#endif
+ *phys_addr = phys;
+
+ return ret;
}
-MALI_STATIC_INLINE void mali_dma_pool_free(mali_dma_pool pool, void* virt_addr, u32 phys_addr)
+MALI_STATIC_INLINE void mali_dma_pool_free(mali_dma_pool pool, void *virt_addr, mali_dma_addr phys_addr)
{
- dma_pool_free(pool, virt_addr, phys_addr);
+ dma_pool_free(pool, virt_addr, (dma_addr_t)phys_addr);
}
{
unsigned int value;
/* Reading the CCNT Register - CPU clock counter */
- asm volatile ("MRC p15, 0, %0, c9, c13, 0\t\n": "=r"(value));
+ asm volatile("MRC p15, 0, %0, c9, c13, 0\t\n": "=r"(value));
return value;
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include <linux/time.h>
#include <asm/delay.h>
-int _mali_osk_time_after( u32 ticka, u32 tickb )
+int _mali_osk_time_after(u32 ticka, u32 tickb)
{
return time_after((unsigned long)ticka, (unsigned long)tickb);
}
-u32 _mali_osk_time_mstoticks( u32 ms )
+u32 _mali_osk_time_mstoticks(u32 ms)
{
return msecs_to_jiffies(ms);
}
-u32 _mali_osk_time_tickstoms( u32 ticks )
+u32 _mali_osk_time_tickstoms(u32 ticks)
{
return jiffies_to_msecs(ticks);
}
-u32 _mali_osk_time_tickcount( void )
+u32 _mali_osk_time_tickcount(void)
{
return jiffies;
}
-void _mali_osk_time_ubusydelay( u32 usecs )
+void _mali_osk_time_ubusydelay(u32 usecs)
{
udelay(usecs);
}
-u64 _mali_osk_time_get_ns( void )
+u64 _mali_osk_time_get_ns(void)
{
struct timespec tsval;
getnstimeofday(&tsval);
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
_mali_osk_timer_t *_mali_osk_timer_init(void)
{
- _mali_osk_timer_t *t = (_mali_osk_timer_t*)kmalloc(sizeof(_mali_osk_timer_t), GFP_KERNEL);
+ _mali_osk_timer_t *t = (_mali_osk_timer_t *)kmalloc(sizeof(_mali_osk_timer_t), GFP_KERNEL);
if (NULL != t) init_timer(&t->timer);
return t;
}
-void _mali_osk_timer_add( _mali_osk_timer_t *tim, u32 ticks_to_expire )
+void _mali_osk_timer_add(_mali_osk_timer_t *tim, u32 ticks_to_expire)
{
MALI_DEBUG_ASSERT_POINTER(tim);
tim->timer.expires = jiffies + ticks_to_expire;
add_timer(&(tim->timer));
}
-void _mali_osk_timer_mod( _mali_osk_timer_t *tim, u32 ticks_to_expire)
+void _mali_osk_timer_mod(_mali_osk_timer_t *tim, u32 ticks_to_expire)
{
MALI_DEBUG_ASSERT_POINTER(tim);
mod_timer(&(tim->timer), jiffies + ticks_to_expire);
}
-void _mali_osk_timer_del( _mali_osk_timer_t *tim )
+void _mali_osk_timer_del(_mali_osk_timer_t *tim)
{
MALI_DEBUG_ASSERT_POINTER(tim);
del_timer_sync(&(tim->timer));
}
-void _mali_osk_timer_del_async( _mali_osk_timer_t *tim )
+void _mali_osk_timer_del_async(_mali_osk_timer_t *tim)
{
MALI_DEBUG_ASSERT_POINTER(tim);
del_timer(&(tim->timer));
}
-mali_bool _mali_osk_timer_pending( _mali_osk_timer_t *tim )
+mali_bool _mali_osk_timer_pending(_mali_osk_timer_t *tim)
{
MALI_DEBUG_ASSERT_POINTER(tim);
return 1 == timer_pending(&(tim->timer));
}
-void _mali_osk_timer_setcallback( _mali_osk_timer_t *tim, _mali_osk_timer_callback_t callback, void *data )
+void _mali_osk_timer_setcallback(_mali_osk_timer_t *tim, _mali_osk_timer_callback_t callback, void *data)
{
MALI_DEBUG_ASSERT_POINTER(tim);
tim->timer.data = (unsigned long)data;
tim->timer.function = (timer_timeout_function_t)callback;
}
-void _mali_osk_timer_term( _mali_osk_timer_t *tim )
+void _mali_osk_timer_term(_mali_osk_timer_t *tim)
{
MALI_DEBUG_ASSERT_POINTER(tim);
kfree(tim);
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
wait_queue_head_t wait_queue;
};
-_mali_osk_wait_queue_t* _mali_osk_wait_queue_init( void )
+_mali_osk_wait_queue_t *_mali_osk_wait_queue_init(void)
{
- _mali_osk_wait_queue_t* ret = NULL;
+ _mali_osk_wait_queue_t *ret = NULL;
ret = kmalloc(sizeof(_mali_osk_wait_queue_t), GFP_KERNEL);
return ret;
}
-void _mali_osk_wait_queue_wait_event( _mali_osk_wait_queue_t *queue, mali_bool (*condition)(void *), void *data )
+void _mali_osk_wait_queue_wait_event(_mali_osk_wait_queue_t *queue, mali_bool(*condition)(void *), void *data)
{
- MALI_DEBUG_ASSERT_POINTER( queue );
+ MALI_DEBUG_ASSERT_POINTER(queue);
MALI_DEBUG_PRINT(6, ("Adding to wait queue %p\n", queue));
wait_event(queue->wait_queue, condition(data));
}
-void _mali_osk_wait_queue_wait_event_timeout( _mali_osk_wait_queue_t *queue, mali_bool (*condition)(void *), void *data, u32 timeout )
+void _mali_osk_wait_queue_wait_event_timeout(_mali_osk_wait_queue_t *queue, mali_bool(*condition)(void *), void *data, u32 timeout)
{
- MALI_DEBUG_ASSERT_POINTER( queue );
+ MALI_DEBUG_ASSERT_POINTER(queue);
MALI_DEBUG_PRINT(6, ("Adding to wait queue %p\n", queue));
wait_event_timeout(queue->wait_queue, condition(data), _mali_osk_time_mstoticks(timeout));
}
-void _mali_osk_wait_queue_wake_up( _mali_osk_wait_queue_t *queue )
+void _mali_osk_wait_queue_wake_up(_mali_osk_wait_queue_t *queue)
{
- MALI_DEBUG_ASSERT_POINTER( queue );
+ MALI_DEBUG_ASSERT_POINTER(queue);
/* if queue is empty, don't attempt to wake up its elements */
if (!waitqueue_active(&queue->wait_queue)) return;
MALI_DEBUG_PRINT(6, ("... elements in wait queue %p woken up\n", queue));
}
-void _mali_osk_wait_queue_term( _mali_osk_wait_queue_t *queue )
+void _mali_osk_wait_queue_term(_mali_osk_wait_queue_t *queue)
{
/* Parameter validation */
- MALI_DEBUG_ASSERT_POINTER( queue );
+ MALI_DEBUG_ASSERT_POINTER(queue);
/* Linux requires no explicit termination of wait queues */
kfree(queue);
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* Implementation of the OS abstraction layer for the kernel device driver
*/
-#include <linux/slab.h> /* For memory allocation */
+#include <linux/slab.h> /* For memory allocation */
#include <linux/workqueue.h>
#include <linux/version.h>
#include <linux/sched.h>
} mali_osk_wq_delayed_work_object_t;
#if MALI_LICENSE_IS_GPL
-struct workqueue_struct *mali_wq_normal = NULL;
-struct workqueue_struct *mali_wq_high = NULL;
+static struct workqueue_struct *mali_wq_normal = NULL;
+static struct workqueue_struct *mali_wq_high = NULL;
#endif
static void _mali_osk_wq_work_func(struct work_struct *work);
MALI_DEBUG_ASSERT(NULL == mali_wq_normal);
MALI_DEBUG_ASSERT(NULL == mali_wq_high);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36)
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 36)
mali_wq_normal = alloc_workqueue("mali", WQ_UNBOUND, 0);
- mali_wq_high = alloc_workqueue("mali_high_pri", WQ_HIGHPRI, 0);
+ mali_wq_high = alloc_workqueue("mali_high_pri", WQ_HIGHPRI | WQ_UNBOUND, 0);
#else
mali_wq_normal = create_workqueue("mali");
mali_wq_high = create_workqueue("mali_high_pri");
#endif
}
-_mali_osk_wq_work_t *_mali_osk_wq_create_work( _mali_osk_wq_work_handler_t handler, void *data )
+_mali_osk_wq_work_t *_mali_osk_wq_create_work(_mali_osk_wq_work_handler_t handler, void *data)
{
mali_osk_wq_work_object_t *work = kmalloc(sizeof(mali_osk_wq_work_object_t), GFP_KERNEL);
work->data = data;
work->high_pri = MALI_FALSE;
- INIT_WORK( &work->work_handle, _mali_osk_wq_work_func);
+ INIT_WORK(&work->work_handle, _mali_osk_wq_work_func);
return work;
}
-_mali_osk_wq_work_t *_mali_osk_wq_create_work_high_pri( _mali_osk_wq_work_handler_t handler, void *data )
+_mali_osk_wq_work_t *_mali_osk_wq_create_work_high_pri(_mali_osk_wq_work_handler_t handler, void *data)
{
mali_osk_wq_work_object_t *work = kmalloc(sizeof(mali_osk_wq_work_object_t), GFP_KERNEL);
work->data = data;
work->high_pri = MALI_TRUE;
- INIT_WORK( &work->work_handle, _mali_osk_wq_work_func );
+ INIT_WORK(&work->work_handle, _mali_osk_wq_work_func);
return work;
}
-void _mali_osk_wq_delete_work( _mali_osk_wq_work_t *work )
+void _mali_osk_wq_delete_work(_mali_osk_wq_work_t *work)
{
mali_osk_wq_work_object_t *work_object = (mali_osk_wq_work_object_t *)work;
_mali_osk_wq_flush();
kfree(work_object);
}
-void _mali_osk_wq_delete_work_nonflush( _mali_osk_wq_work_t *work )
+void _mali_osk_wq_delete_work_nonflush(_mali_osk_wq_work_t *work)
{
mali_osk_wq_work_object_t *work_object = (mali_osk_wq_work_object_t *)work;
kfree(work_object);
}
-void _mali_osk_wq_schedule_work( _mali_osk_wq_work_t *work )
+void _mali_osk_wq_schedule_work(_mali_osk_wq_work_t *work)
{
mali_osk_wq_work_object_t *work_object = (mali_osk_wq_work_object_t *)work;
#if MALI_LICENSE_IS_GPL
#endif
}
-void _mali_osk_wq_schedule_work_high_pri( _mali_osk_wq_work_t *work )
+void _mali_osk_wq_schedule_work_high_pri(_mali_osk_wq_work_t *work)
{
mali_osk_wq_work_object_t *work_object = (mali_osk_wq_work_object_t *)work;
#if MALI_LICENSE_IS_GPL
#endif
}
-static void _mali_osk_wq_work_func( struct work_struct *work )
+static void _mali_osk_wq_work_func(struct work_struct *work)
{
mali_osk_wq_work_object_t *work_object;
work_object = _MALI_OSK_CONTAINER_OF(work, mali_osk_wq_work_object_t, work_handle);
- /* We want higher priority than the Dynamic Priority, setting it to the lowest of the RT priorities */
+#if MALI_LICENSE_IS_GPL
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36)
+ /* We want highest Dynamic priority of the thread so that the Jobs depending
+ ** on this thread could be scheduled in time. Without this, this thread might
+ ** sometimes need to wait for some threads in user mode to finish its round-robin
+ ** time, causing *bubble* in the Mali pipeline. Thanks to the new implementation
+ ** of high-priority workqueue in new kernel, this only happens in older kernel.
+ */
if (MALI_TRUE == work_object->high_pri) {
set_user_nice(current, -19);
}
+#endif
+#endif /* MALI_LICENSE_IS_GPL */
work_object->handler(work_object->data);
}
-static void _mali_osk_wq_delayed_work_func( struct work_struct *work )
+static void _mali_osk_wq_delayed_work_func(struct work_struct *work)
{
mali_osk_wq_delayed_work_object_t *work_object;
work_object->handler(work_object->data);
}
-mali_osk_wq_delayed_work_object_t *_mali_osk_wq_delayed_create_work( _mali_osk_wq_work_handler_t handler, void *data)
+mali_osk_wq_delayed_work_object_t *_mali_osk_wq_delayed_create_work(_mali_osk_wq_work_handler_t handler, void *data)
{
mali_osk_wq_delayed_work_object_t *work = kmalloc(sizeof(mali_osk_wq_delayed_work_object_t), GFP_KERNEL);
return work;
}
-void _mali_osk_wq_delayed_delete_work_nonflush( _mali_osk_wq_delayed_work_t *work )
+void _mali_osk_wq_delayed_delete_work_nonflush(_mali_osk_wq_delayed_work_t *work)
{
mali_osk_wq_delayed_work_object_t *work_object = (mali_osk_wq_delayed_work_object_t *)work;
kfree(work_object);
}
-void _mali_osk_wq_delayed_cancel_work_async( _mali_osk_wq_delayed_work_t *work )
+void _mali_osk_wq_delayed_cancel_work_async(_mali_osk_wq_delayed_work_t *work)
{
mali_osk_wq_delayed_work_object_t *work_object = (mali_osk_wq_delayed_work_object_t *)work;
cancel_delayed_work(&work_object->work);
}
-void _mali_osk_wq_delayed_cancel_work_sync( _mali_osk_wq_delayed_work_t *work )
+void _mali_osk_wq_delayed_cancel_work_sync(_mali_osk_wq_delayed_work_t *work)
{
mali_osk_wq_delayed_work_object_t *work_object = (mali_osk_wq_delayed_work_object_t *)work;
cancel_delayed_work_sync(&work_object->work);
}
-void _mali_osk_wq_delayed_schedule_work( _mali_osk_wq_delayed_work_t *work, u32 delay )
+void _mali_osk_wq_delayed_schedule_work(_mali_osk_wq_delayed_work_t *work, u32 delay)
{
mali_osk_wq_delayed_work_object_t *work_object = (mali_osk_wq_delayed_work_object_t *)work;
/**
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012 ARM Limited. All rights reserved.
+ * Copyright (C) 2012, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
static _mali_osk_mutex_t *lock = NULL;
static mali_profiling_state prof_state = MALI_PROFILING_STATE_UNINITIALIZED;
-static mali_profiling_entry* profile_entries = NULL;
+static mali_profiling_entry *profile_entries = NULL;
static _mali_osk_atomic_t profile_insert_index;
static u32 profile_mask = 0;
static inline void add_event(u32 event_id, u32 data0, u32 data1, u32 data2, u32 data3, u32 data4);
void probe_mali_timeline_event(void *data, TP_PROTO(unsigned int event_id, unsigned int d0, unsigned int d1, unsigned
- int d2, unsigned int d3, unsigned int d4))
+ int d2, unsigned int d3, unsigned int d4))
{
add_event(event_id, d0, d1, d2, d3, d4);
}
}
}
-_mali_osk_errcode_t _mali_internal_profiling_start(u32 * limit)
+_mali_osk_errcode_t _mali_internal_profiling_start(u32 *limit)
{
_mali_osk_errcode_t ret;
mali_profiling_entry *new_profile_entries;
/* If event is "leave API function", add current memory usage to the event
* as data point 4. This is used in timeline profiling to indicate how
* much memory was used when leaving a function. */
- if (event_id == (MALI_PROFILING_EVENT_TYPE_SINGLE|MALI_PROFILING_EVENT_CHANNEL_SOFTWARE|MALI_PROFILING_EVENT_REASON_SINGLE_SW_LEAVE_API_FUNC)) {
+ if (event_id == (MALI_PROFILING_EVENT_TYPE_SINGLE | MALI_PROFILING_EVENT_CHANNEL_SOFTWARE | MALI_PROFILING_EVENT_REASON_SINGLE_SW_LEAVE_API_FUNC)) {
profile_entries[cur_index].data[4] = _mali_ukk_report_memory_usage();
}
}
-_mali_osk_errcode_t _mali_internal_profiling_stop(u32 * count)
+_mali_osk_errcode_t _mali_internal_profiling_stop(u32 *count)
{
_mali_osk_mutex_wait(lock);
return retval;
}
-_mali_osk_errcode_t _mali_internal_profiling_get_event(u32 index, u64* timestamp, u32* event_id, u32 data[5])
+_mali_osk_errcode_t _mali_internal_profiling_get_event(u32 index, u64 *timestamp, u32 *event_id, u32 data[5])
{
u32 raw_index = _mali_osk_atomic_read(&profile_insert_index);
return _MALI_OSK_ERR_INVALID_ARGS; /* invalid to call this function in this state */
}
- if(index >= raw_index) {
+ if (index >= raw_index) {
_mali_osk_mutex_signal(lock);
return _MALI_OSK_ERR_FAULT;
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
mali_bool _mali_internal_profiling_is_recording(void);
mali_bool _mali_internal_profiling_have_recording(void);
_mali_osk_errcode_t _mali_internal_profiling_clear(void);
-_mali_osk_errcode_t _mali_internal_profiling_get_event(u32 index, u64* timestamp, u32* event_id, u32 data[5]);
+_mali_osk_errcode_t _mali_internal_profiling_get_event(u32 index, u64 *timestamp, u32 *event_id, u32 data[5]);
u32 _mali_internal_profiling_get_count(void);
-int _mali_internal_profiling_stop(u32 * count);
-int _mali_internal_profiling_start(u32 * limit);
+int _mali_internal_profiling_stop(u32 *count);
+int _mali_internal_profiling_start(u32 *limit);
#ifdef __cplusplus
}
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
MALI_DEBUG_ASSERT_POINTER(mptb->flag);
a = mpta->flag->point;
- b = mpta->flag->point;
+ b = mptb->flag->point;
if (a == b) return 0;
MALI_DEBUG_ASSERT_POINTER(sync_pt);
mpt = to_mali_sync_pt(sync_pt);
- MALI_DEBUG_ASSERT_POINTER(mpt->flag);
- seq_printf(s, "%u", mpt->flag->point);
+ /* It is possible this sync point is just under construct,
+ * make sure the flag is valid before accessing it
+ */
+ if (mpt->flag) {
+ seq_printf(s, "%u", mpt->flag->point);
+ } else {
+ seq_printf(s, "uninitialized");
+ }
}
static struct sync_timeline_ops mali_timeline_ops = {
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#ifndef _MALI_SYNC_H_
#define _MALI_SYNC_H_
-#include <linux/version.h>
-
#if defined(CONFIG_SYNC)
#include <linux/seq_file.h>
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,10)
-#include <sync.h>
-#else
+#include <linux/version.h>
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3, 10, 0)
#include <linux/sync.h>
+#else
+#include <sync.h>
#endif
+
#include "mali_osk.h"
struct mali_sync_flag;
/*
- * Copyright (C) 2012 ARM Limited. All rights reserved.
+ * Copyright (C) 2012, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
if (0 != get_user(kargs.version, &uargs->version)) return -EFAULT;
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_api_version(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
return 0;
}
+int get_api_version_v2_wrapper(struct mali_session_data *session_data, _mali_uk_get_api_version_v2_s __user *uargs)
+{
+ _mali_uk_get_api_version_v2_s kargs;
+ _mali_osk_errcode_t err;
+
+ MALI_CHECK_NON_NULL(uargs, -EINVAL);
+
+ if (0 != get_user(kargs.version, &uargs->version)) return -EFAULT;
+
+ kargs.ctx = (uintptr_t)session_data;
+ err = _mali_ukk_get_api_version_v2(&kargs);
+ if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
+
+ if (0 != put_user(kargs.version, &uargs->version)) return -EFAULT;
+ if (0 != put_user(kargs.compatible, &uargs->compatible)) return -EFAULT;
+
+ return 0;
+}
+
int wait_for_notification_wrapper(struct mali_session_data *session_data, _mali_uk_wait_for_notification_s __user *uargs)
{
_mali_uk_wait_for_notification_s kargs;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_wait_for_notification(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
- if(_MALI_NOTIFICATION_CORE_SHUTDOWN_IN_PROGRESS != kargs.type) {
- kargs.ctx = NULL; /* prevent kernel address to be returned to user space */
+ if (_MALI_NOTIFICATION_CORE_SHUTDOWN_IN_PROGRESS != kargs.type) {
+ kargs.ctx = (uintptr_t)NULL; /* prevent kernel address to be returned to user space */
if (0 != copy_to_user(uargs, &kargs, sizeof(_mali_uk_wait_for_notification_s))) return -EFAULT;
} else {
if (0 != put_user(kargs.type, &uargs->type)) return -EFAULT;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
if (0 != get_user(kargs.type, &uargs->type)) {
return -EFAULT;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_user_settings(&kargs);
if (_MALI_OSK_ERR_OK != err) {
return map_errcode(err);
}
- kargs.ctx = NULL; /* prevent kernel address to be returned to user space */
+ kargs.ctx = 0; /* prevent kernel address to be returned to user space */
if (0 != copy_to_user(uargs, &kargs, sizeof(_mali_uk_get_user_settings_s))) return -EFAULT;
return 0;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_request_high_priority(&kargs);
- kargs.ctx = NULL;
+ kargs.ctx = 0;
return map_errcode(err);
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
MALI_CHECK_NON_NULL(uargs, -EINVAL);
MALI_CHECK_NON_NULL(session_data, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_gp_core_version(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
if (0 != copy_from_user(&kargs, uargs, sizeof(_mali_uk_gp_suspend_response_s))) return -EFAULT;
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_gp_suspend_response(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
MALI_CHECK_NON_NULL(uargs, -EINVAL);
MALI_CHECK_NON_NULL(session_data, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_gp_number_of_cores(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_session.h"
#include "mali_ukk_wrappers.h"
-int mem_write_safe_wrapper(struct mali_session_data *session_data, _mali_uk_mem_write_safe_s __user * uargs)
+int mem_write_safe_wrapper(struct mali_session_data *session_data, _mali_uk_mem_write_safe_s __user *uargs)
{
_mali_uk_mem_write_safe_s kargs;
_mali_osk_errcode_t err;
return -EFAULT;
}
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
/* Check if we can access the buffers */
if (!access_ok(VERIFY_WRITE, kargs.dest, kargs.size)
return 0;
}
-int mem_map_ext_wrapper(struct mali_session_data *session_data, _mali_uk_map_external_mem_s __user * argument)
+int mem_map_ext_wrapper(struct mali_session_data *session_data, _mali_uk_map_external_mem_s __user *argument)
{
_mali_uk_map_external_mem_s uk_args;
_mali_osk_errcode_t err_code;
/* validate input */
/* the session_data pointer was validated by caller */
- MALI_CHECK_NON_NULL( argument, -EINVAL);
+ MALI_CHECK_NON_NULL(argument, -EINVAL);
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_map_external_mem_s)) ) {
+ if (0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_map_external_mem_s))) {
return -EFAULT;
}
- uk_args.ctx = session_data;
- err_code = _mali_ukk_map_external_mem( &uk_args );
+ uk_args.ctx = (uintptr_t)session_data;
+ err_code = _mali_ukk_map_external_mem(&uk_args);
if (0 != put_user(uk_args.cookie, &argument->cookie)) {
if (_MALI_OSK_ERR_OK == err_code) {
/* Rollback */
_mali_uk_unmap_external_mem_s uk_args_unmap;
- uk_args_unmap.ctx = session_data;
+ uk_args_unmap.ctx = (uintptr_t)session_data;
uk_args_unmap.cookie = uk_args.cookie;
- err_code = _mali_ukk_unmap_external_mem( &uk_args_unmap );
+ err_code = _mali_ukk_unmap_external_mem(&uk_args_unmap);
if (_MALI_OSK_ERR_OK != err_code) {
MALI_DEBUG_PRINT(4, ("reverting _mali_ukk_unmap_external_mem, as a result of failing put_user(), failed\n"));
}
return map_errcode(err_code);
}
-int mem_unmap_ext_wrapper(struct mali_session_data *session_data, _mali_uk_unmap_external_mem_s __user * argument)
+int mem_unmap_ext_wrapper(struct mali_session_data *session_data, _mali_uk_unmap_external_mem_s __user *argument)
{
_mali_uk_unmap_external_mem_s uk_args;
_mali_osk_errcode_t err_code;
/* validate input */
/* the session_data pointer was validated by caller */
- MALI_CHECK_NON_NULL( argument, -EINVAL);
+ MALI_CHECK_NON_NULL(argument, -EINVAL);
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_unmap_external_mem_s)) ) {
+ if (0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_unmap_external_mem_s))) {
return -EFAULT;
}
- uk_args.ctx = session_data;
- err_code = _mali_ukk_unmap_external_mem( &uk_args );
+ uk_args.ctx = (uintptr_t)session_data;
+ err_code = _mali_ukk_unmap_external_mem(&uk_args);
/* Return the error that _mali_ukk_free_big_block produced */
return map_errcode(err_code);
}
#if defined(CONFIG_MALI400_UMP)
-int mem_release_ump_wrapper(struct mali_session_data *session_data, _mali_uk_release_ump_mem_s __user * argument)
+int mem_release_ump_wrapper(struct mali_session_data *session_data, _mali_uk_release_ump_mem_s __user *argument)
{
_mali_uk_release_ump_mem_s uk_args;
_mali_osk_errcode_t err_code;
/* validate input */
/* the session_data pointer was validated by caller */
- MALI_CHECK_NON_NULL( argument, -EINVAL);
+ MALI_CHECK_NON_NULL(argument, -EINVAL);
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_release_ump_mem_s)) ) {
+ if (0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_release_ump_mem_s))) {
return -EFAULT;
}
- uk_args.ctx = session_data;
- err_code = _mali_ukk_release_ump_mem( &uk_args );
+ uk_args.ctx = (uintptr_t)session_data;
+ err_code = _mali_ukk_release_ump_mem(&uk_args);
/* Return the error that _mali_ukk_free_big_block produced */
return map_errcode(err_code);
}
-int mem_attach_ump_wrapper(struct mali_session_data *session_data, _mali_uk_attach_ump_mem_s __user * argument)
+int mem_attach_ump_wrapper(struct mali_session_data *session_data, _mali_uk_attach_ump_mem_s __user *argument)
{
_mali_uk_attach_ump_mem_s uk_args;
_mali_osk_errcode_t err_code;
/* validate input */
/* the session_data pointer was validated by caller */
- MALI_CHECK_NON_NULL( argument, -EINVAL);
+ MALI_CHECK_NON_NULL(argument, -EINVAL);
/* get call arguments from user space. copy_from_user returns how many bytes which where NOT copied */
- if ( 0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_attach_ump_mem_s)) ) {
+ if (0 != copy_from_user(&uk_args, (void __user *)argument, sizeof(_mali_uk_attach_ump_mem_s))) {
return -EFAULT;
}
- uk_args.ctx = session_data;
- err_code = _mali_ukk_attach_ump_mem( &uk_args );
+ uk_args.ctx = (uintptr_t)session_data;
+ err_code = _mali_ukk_attach_ump_mem(&uk_args);
if (0 != put_user(uk_args.cookie, &argument->cookie)) {
if (_MALI_OSK_ERR_OK == err_code) {
/* Rollback */
_mali_uk_release_ump_mem_s uk_args_unmap;
- uk_args_unmap.ctx = session_data;
+ uk_args_unmap.ctx = (uintptr_t)session_data;
uk_args_unmap.cookie = uk_args.cookie;
- err_code = _mali_ukk_release_ump_mem( &uk_args_unmap );
+ err_code = _mali_ukk_release_ump_mem(&uk_args_unmap);
if (_MALI_OSK_ERR_OK != err_code) {
MALI_DEBUG_PRINT(4, ("reverting _mali_ukk_attach_mem, as a result of failing put_user(), failed\n"));
}
}
#endif /* CONFIG_MALI400_UMP */
-int mem_query_mmu_page_table_dump_size_wrapper(struct mali_session_data *session_data, _mali_uk_query_mmu_page_table_dump_size_s __user * uargs)
+int mem_query_mmu_page_table_dump_size_wrapper(struct mali_session_data *session_data, _mali_uk_query_mmu_page_table_dump_size_s __user *uargs)
{
_mali_uk_query_mmu_page_table_dump_size_s kargs;
_mali_osk_errcode_t err;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
MALI_CHECK_NON_NULL(session_data, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_query_mmu_page_table_dump_size(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
return 0;
}
-int mem_dump_mmu_page_table_wrapper(struct mali_session_data *session_data, _mali_uk_dump_mmu_page_table_s __user * uargs)
+int mem_dump_mmu_page_table_wrapper(struct mali_session_data *session_data, _mali_uk_dump_mmu_page_table_s __user *uargs)
{
_mali_uk_dump_mmu_page_table_s kargs;
_mali_osk_errcode_t err;
- void *buffer;
+ void __user *user_buffer;
+ void *buffer = NULL;
int rc = -EFAULT;
/* validate input */
MALI_CHECK_NON_NULL(uargs, -EINVAL);
/* the session_data pointer was validated by caller */
- kargs.buffer = NULL;
+ if (0 != copy_from_user(&kargs, uargs, sizeof(_mali_uk_dump_mmu_page_table_s)))
+ goto err_exit;
- /* get location of user buffer */
- if (0 != get_user(buffer, &uargs->buffer)) goto err_exit;
- /* get size of mmu page table info buffer from user space */
- if ( 0 != get_user(kargs.size, &uargs->size) ) goto err_exit;
- /* verify we can access the whole of the user buffer */
- if (!access_ok(VERIFY_WRITE, buffer, kargs.size)) goto err_exit;
+ user_buffer = (void __user *)(uintptr_t)kargs.buffer;
+ if (!access_ok(VERIFY_WRITE, user_buffer, kargs.size))
+ goto err_exit;
/* allocate temporary buffer (kernel side) to store mmu page table info */
- MALI_CHECK(kargs.size > 0, -ENOMEM);
- kargs.buffer = _mali_osk_valloc(kargs.size);
- if (NULL == kargs.buffer) {
+ if (kargs.size <= 0)
+ return -EINVAL;
+ /* Allow at most 8MiB buffers, this is more than enough to dump a fully
+ * populated page table. */
+ if (kargs.size > SZ_8M)
+ return -EINVAL;
+
+ buffer = (void *)(uintptr_t)_mali_osk_valloc(kargs.size);
+ if (NULL == buffer) {
rc = -ENOMEM;
goto err_exit;
}
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
+ kargs.buffer = (uintptr_t)buffer;
err = _mali_ukk_dump_mmu_page_table(&kargs);
if (_MALI_OSK_ERR_OK != err) {
rc = map_errcode(err);
}
/* copy mmu page table info back to user space and update pointers */
- if (0 != copy_to_user(uargs->buffer, kargs.buffer, kargs.size) ) goto err_exit;
- if (0 != put_user((kargs.register_writes - (u32 *)kargs.buffer) + (u32 *)uargs->buffer, &uargs->register_writes)) goto err_exit;
- if (0 != put_user((kargs.page_table_dump - (u32 *)kargs.buffer) + (u32 *)uargs->buffer, &uargs->page_table_dump)) goto err_exit;
- if (0 != put_user(kargs.register_writes_size, &uargs->register_writes_size)) goto err_exit;
- if (0 != put_user(kargs.page_table_dump_size, &uargs->page_table_dump_size)) goto err_exit;
+ if (0 != copy_to_user(user_buffer, buffer, kargs.size))
+ goto err_exit;
+
+ kargs.register_writes = kargs.register_writes -
+ (uintptr_t)buffer + (uintptr_t)user_buffer;
+ kargs.page_table_dump = kargs.page_table_dump -
+ (uintptr_t)buffer + (uintptr_t)user_buffer;
+
+ if (0 != copy_to_user(uargs, &kargs, sizeof(kargs)))
+ goto err_exit;
+
rc = 0;
err_exit:
- if (kargs.buffer) _mali_osk_vfree(kargs.buffer);
+ if (buffer) _mali_osk_vfree(buffer);
return rc;
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
MALI_CHECK_NON_NULL(uargs, -EINVAL);
MALI_CHECK_NON_NULL(session_data, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_pp_number_of_cores(&kargs);
if (_MALI_OSK_ERR_OK != err) {
return map_errcode(err);
}
- kargs.ctx = NULL; /* prevent kernel address to be returned to user space */
+ kargs.ctx = (uintptr_t)NULL; /* prevent kernel address to be returned to user space */
if (0 != copy_to_user(uargs, &kargs, sizeof(_mali_uk_get_pp_number_of_cores_s))) {
return -EFAULT;
}
MALI_CHECK_NON_NULL(uargs, -EINVAL);
MALI_CHECK_NON_NULL(session_data, -EINVAL);
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_get_pp_core_version(&kargs);
if (_MALI_OSK_ERR_OK != err) return map_errcode(err);
if (0 != copy_from_user(&kargs, uargs, sizeof(_mali_uk_pp_disable_wb_s))) return -EFAULT;
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
_mali_ukk_pp_job_disable_wb(&kargs);
return 0;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "mali_session.h"
#include "mali_ukk_wrappers.h"
-int profiling_start_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_start_s __user *uargs)
-{
- _mali_uk_profiling_start_s kargs;
- _mali_osk_errcode_t err;
-
- MALI_CHECK_NON_NULL(uargs, -EINVAL);
-
- if (0 != copy_from_user(&kargs, uargs, sizeof(_mali_uk_profiling_start_s))) {
- return -EFAULT;
- }
-
- kargs.ctx = session_data;
- err = _mali_ukk_profiling_start(&kargs);
- if (_MALI_OSK_ERR_OK != err) {
- return map_errcode(err);
- }
-
- if (0 != put_user(kargs.limit, &uargs->limit)) {
- return -EFAULT;
- }
-
- return 0;
-}
-
int profiling_add_event_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_add_event_s __user *uargs)
{
_mali_uk_profiling_add_event_s kargs;
return -EFAULT;
}
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_profiling_add_event(&kargs);
if (_MALI_OSK_ERR_OK != err) {
return map_errcode(err);
return 0;
}
-int profiling_stop_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_stop_s __user *uargs)
-{
- _mali_uk_profiling_stop_s kargs;
- _mali_osk_errcode_t err;
-
- MALI_CHECK_NON_NULL(uargs, -EINVAL);
-
- kargs.ctx = session_data;
- err = _mali_ukk_profiling_stop(&kargs);
- if (_MALI_OSK_ERR_OK != err) {
- return map_errcode(err);
- }
-
- if (0 != put_user(kargs.count, &uargs->count)) {
- return -EFAULT;
- }
-
- return 0;
-}
-
-int profiling_get_event_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_get_event_s __user *uargs)
+int profiling_memory_usage_get_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_memory_usage_get_s __user *uargs)
{
- _mali_uk_profiling_get_event_s kargs;
_mali_osk_errcode_t err;
+ _mali_uk_profiling_memory_usage_get_s kargs;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
+ MALI_CHECK_NON_NULL(session_data, -EINVAL);
- if (0 != get_user(kargs.index, &uargs->index)) {
- return -EFAULT;
- }
-
- kargs.ctx = session_data;
-
- err = _mali_ukk_profiling_get_event(&kargs);
+ kargs.ctx = (uintptr_t)session_data;
+ err = _mali_ukk_profiling_memory_usage_get(&kargs);
if (_MALI_OSK_ERR_OK != err) {
return map_errcode(err);
}
- kargs.ctx = NULL; /* prevent kernel address to be returned to user space */
- if (0 != copy_to_user(uargs, &kargs, sizeof(_mali_uk_profiling_get_event_s))) {
+ kargs.ctx = (uintptr_t)NULL; /* prevent kernel address to be returned to user space */
+ if (0 != copy_to_user(uargs, &kargs, sizeof(_mali_uk_profiling_memory_usage_get_s))) {
return -EFAULT;
}
return 0;
}
-int profiling_clear_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_clear_s __user *uargs)
-{
- _mali_uk_profiling_clear_s kargs;
- _mali_osk_errcode_t err;
-
- MALI_CHECK_NON_NULL(uargs, -EINVAL);
-
- kargs.ctx = session_data;
- err = _mali_ukk_profiling_clear(&kargs);
- if (_MALI_OSK_ERR_OK != err) {
- return map_errcode(err);
- }
-
- return 0;
-}
-
int profiling_report_sw_counters_wrapper(struct mali_session_data *session_data, _mali_uk_sw_counters_report_s __user *uargs)
{
_mali_uk_sw_counters_report_s kargs;
_mali_osk_errcode_t err;
u32 *counter_buffer;
+ u32 __user *counters;
MALI_CHECK_NON_NULL(uargs, -EINVAL);
return -EINVAL;
}
- counter_buffer = (u32*)kmalloc(sizeof(u32) * kargs.num_counters, GFP_KERNEL);
+ counter_buffer = (u32 *)kmalloc(sizeof(u32) * kargs.num_counters, GFP_KERNEL);
if (NULL == counter_buffer) {
return -ENOMEM;
}
- if (0 != copy_from_user(counter_buffer, kargs.counters, sizeof(u32) * kargs.num_counters)) {
+ counters = (u32 *)(uintptr_t)kargs.counters;
+
+ if (0 != copy_from_user(counter_buffer, counters, sizeof(u32) * kargs.num_counters)) {
kfree(counter_buffer);
return -EFAULT;
}
- kargs.ctx = session_data;
- kargs.counters = counter_buffer;
+ kargs.ctx = (uintptr_t)session_data;
+ kargs.counters = (uintptr_t)counter_buffer;
err = _mali_ukk_sw_counters_report(&kargs);
return 0;
}
-
-
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
int soft_job_start_wrapper(struct mali_session_data *session, _mali_uk_soft_job_start_s __user *uargs)
{
- u32 type, user_job, point;
- _mali_uk_fence_t uk_fence;
+ _mali_uk_soft_job_start_s kargs;
+ u32 type, point;
+ u64 user_job;
struct mali_timeline_fence fence;
struct mali_soft_job *job = NULL;
u32 __user *job_id_ptr = NULL;
MALI_DEBUG_ASSERT_POINTER(session->soft_job_system);
- if (0 != get_user(type, &uargs->type)) return -EFAULT;
- if (0 != get_user(user_job, &uargs->user_job)) return -EFAULT;
- if (0 != get_user(job_id_ptr, &uargs->job_id_ptr)) return -EFAULT;
+ if (0 != copy_from_user(&kargs, uargs, sizeof(kargs))) {
+ return -EFAULT;
+ }
+
+ type = kargs.type;
+ user_job = kargs.user_job;
+ job_id_ptr = (u32 __user *)(uintptr_t)kargs.job_id_ptr;
- if (0 != copy_from_user(&uk_fence, &uargs->fence, sizeof(_mali_uk_fence_t))) return -EFAULT;
- mali_timeline_fence_copy_uk_fence(&fence, &uk_fence);
+ mali_timeline_fence_copy_uk_fence(&fence, &kargs.fence);
- if (MALI_SOFT_JOB_TYPE_USER_SIGNALED < type) {
+ if ((MALI_SOFT_JOB_TYPE_USER_SIGNALED != type) && (MALI_SOFT_JOB_TYPE_SELF_SIGNALED != type)) {
MALI_DEBUG_PRINT_ERROR(("Invalid soft job type specified\n"));
return -EINVAL;
}
/*
- * Copyright (C) 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2011-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2011-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
return -EFAULT;
}
- kargs.ctx = session_data;
+ kargs.ctx = (uintptr_t)session_data;
err = _mali_ukk_vsync_event_report(&kargs);
if (_MALI_OSK_ERR_OK != err) {
return map_errcode(err);
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
int wait_for_notification_wrapper(struct mali_session_data *session_data, _mali_uk_wait_for_notification_s __user *uargs);
int get_api_version_wrapper(struct mali_session_data *session_data, _mali_uk_get_api_version_s __user *uargs);
+int get_api_version_v2_wrapper(struct mali_session_data *session_data, _mali_uk_get_api_version_v2_s __user *uargs);
int get_user_settings_wrapper(struct mali_session_data *session_data, _mali_uk_get_user_settings_s __user *uargs);
int post_notification_wrapper(struct mali_session_data *session_data, _mali_uk_post_notification_s __user *uargs);
int request_high_priority_wrapper(struct mali_session_data *session_data, _mali_uk_request_high_priority_s __user *uargs);
-int mem_write_safe_wrapper(struct mali_session_data *session_data, _mali_uk_mem_write_safe_s __user * uargs);
-int mem_map_ext_wrapper(struct mali_session_data *session_data, _mali_uk_map_external_mem_s __user * argument);
-int mem_unmap_ext_wrapper(struct mali_session_data *session_data, _mali_uk_unmap_external_mem_s __user * argument);
-int mem_query_mmu_page_table_dump_size_wrapper(struct mali_session_data *session_data, _mali_uk_query_mmu_page_table_dump_size_s __user * uargs);
-int mem_dump_mmu_page_table_wrapper(struct mali_session_data *session_data, _mali_uk_dump_mmu_page_table_s __user * uargs);
+int mem_write_safe_wrapper(struct mali_session_data *session_data, _mali_uk_mem_write_safe_s __user *uargs);
+int mem_map_ext_wrapper(struct mali_session_data *session_data, _mali_uk_map_external_mem_s __user *argument);
+int mem_unmap_ext_wrapper(struct mali_session_data *session_data, _mali_uk_unmap_external_mem_s __user *argument);
+int mem_query_mmu_page_table_dump_size_wrapper(struct mali_session_data *session_data, _mali_uk_query_mmu_page_table_dump_size_s __user *uargs);
+int mem_dump_mmu_page_table_wrapper(struct mali_session_data *session_data, _mali_uk_dump_mmu_page_table_s __user *uargs);
int timeline_get_latest_point_wrapper(struct mali_session_data *session, _mali_uk_timeline_get_latest_point_s __user *uargs);
int timeline_wait_wrapper(struct mali_session_data *session, _mali_uk_timeline_wait_s __user *uargs);
int soft_job_signal_wrapper(struct mali_session_data *session, _mali_uk_soft_job_signal_s __user *uargs);
#if defined(CONFIG_MALI400_UMP)
-int mem_attach_ump_wrapper(struct mali_session_data *session_data, _mali_uk_attach_ump_mem_s __user * argument);
-int mem_release_ump_wrapper(struct mali_session_data *session_data, _mali_uk_release_ump_mem_s __user * argument);
+int mem_attach_ump_wrapper(struct mali_session_data *session_data, _mali_uk_attach_ump_mem_s __user *argument);
+int mem_release_ump_wrapper(struct mali_session_data *session_data, _mali_uk_release_ump_mem_s __user *argument);
#endif
int pp_start_job_wrapper(struct mali_session_data *session_data, _mali_uk_pp_start_job_s __user *uargs);
int gp_get_core_version_wrapper(struct mali_session_data *session_data, _mali_uk_get_gp_core_version_s __user *uargs);
int gp_suspend_response_wrapper(struct mali_session_data *session_data, _mali_uk_gp_suspend_response_s __user *uargs);
-int profiling_start_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_start_s __user *uargs);
int profiling_add_event_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_add_event_s __user *uargs);
-int profiling_stop_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_stop_s __user *uargs);
-int profiling_get_event_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_get_event_s __user *uargs);
-int profiling_clear_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_clear_s __user *uargs);
int profiling_report_sw_counters_wrapper(struct mali_session_data *session_data, _mali_uk_sw_counters_report_s __user *uargs);
+int profiling_memory_usage_get_wrapper(struct mali_session_data *session_data, _mali_uk_profiling_memory_usage_get_s __user *uargs);
int vsync_event_report_wrapper(struct mali_session_data *session_data, _mali_uk_vsync_event_report_s __user *uargs);
-int map_errcode( _mali_osk_errcode_t err );
+int map_errcode(_mali_osk_errcode_t err);
#ifdef __cplusplus
}
#if MESON_CPU_TYPE >= MESON_CPU_TYPE_MESON6TVD
#define FCLK_MPLL2 (2 << 9)
-
static DEFINE_SPINLOCK(lock);
static mali_plat_info_t* pmali_plat = NULL;
static u32 mali_extr_backup = 0;
_mali_osk_errcode_t mali_platform_power_mode_change(mali_power_mode power_mode)
{
- unsigned long flags;
- unsigned cpu_divider, mali_divider;
- unsigned ddr_pll_setting, sys_pll_setting;
- unsigned cpu_freq, ddr_freq;
- int mali_flag;
-
MALI_DEBUG_PRINT(3, ( "mali_platform_power_mode_change power_mode=%d\n", power_mode));
switch (power_mode) {
u32 mali_dvfs_clk[1];
u32 mali_dvfs_clk_sample[1];
-static struct mali_dvfs_threshold_table mali_dvfs_threshold[1];
-
#if MESON_CPU_TYPE == MESON_CPU_TYPE_MESON6TV
#undef INT_MALI_GP
#undef INT_MALI_GP_MMU
int get_mali_freq_level(int freq)
{
- int i = 0, level = -1;
int mali_freq_num;
+ int i = 0, level = -1;
if(freq < 0)
return level;
+
mali_freq_num = mali_plat_data.dvfs_table_size - 1;
if(freq <= mali_plat_data.clk_sample[0])
level = mali_freq_num-1;
int mali_deep_suspend(struct device *device)
{
int ret = 0;
+ struct mali_pmu_core *pmu;
+
+ pmu = mali_pmu_get_global_pmu_core();
enable_clock();
flush_scaling_job();
enable_clock();
ret = mali_clock_critical(mali_cri_deep_resume, (size_t)device);
return ret;
-
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define MALI200_REG_VAL_PERF_CNT_ENABLE 1
enum mali200_mgmt_ctrl_mgmt {
- MALI200_REG_VAL_CTRL_MGMT_STOP_BUS = (1<<0),
- MALI200_REG_VAL_CTRL_MGMT_FLUSH_CACHES = (1<<3),
- MALI200_REG_VAL_CTRL_MGMT_FORCE_RESET = (1<<5),
- MALI200_REG_VAL_CTRL_MGMT_START_RENDERING = (1<<6),
- MALI400PP_REG_VAL_CTRL_MGMT_SOFT_RESET = (1<<7), /* Only valid for Mali-300 and later */
+ MALI200_REG_VAL_CTRL_MGMT_STOP_BUS = (1 << 0),
+ MALI200_REG_VAL_CTRL_MGMT_FLUSH_CACHES = (1 << 3),
+ MALI200_REG_VAL_CTRL_MGMT_FORCE_RESET = (1 << 5),
+ MALI200_REG_VAL_CTRL_MGMT_START_RENDERING = (1 << 6),
+ MALI400PP_REG_VAL_CTRL_MGMT_SOFT_RESET = (1 << 7), /* Only valid for Mali-300 and later */
};
enum mali200_mgmt_irq {
- MALI200_REG_VAL_IRQ_END_OF_FRAME = (1<<0),
- MALI200_REG_VAL_IRQ_END_OF_TILE = (1<<1),
- MALI200_REG_VAL_IRQ_HANG = (1<<2),
- MALI200_REG_VAL_IRQ_FORCE_HANG = (1<<3),
- MALI200_REG_VAL_IRQ_BUS_ERROR = (1<<4),
- MALI200_REG_VAL_IRQ_BUS_STOP = (1<<5),
- MALI200_REG_VAL_IRQ_CNT_0_LIMIT = (1<<6),
- MALI200_REG_VAL_IRQ_CNT_1_LIMIT = (1<<7),
- MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR = (1<<8),
- MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND = (1<<9),
- MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW = (1<<10),
- MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW = (1<<11),
- MALI400PP_REG_VAL_IRQ_RESET_COMPLETED = (1<<12),
+ MALI200_REG_VAL_IRQ_END_OF_FRAME = (1 << 0),
+ MALI200_REG_VAL_IRQ_END_OF_TILE = (1 << 1),
+ MALI200_REG_VAL_IRQ_HANG = (1 << 2),
+ MALI200_REG_VAL_IRQ_FORCE_HANG = (1 << 3),
+ MALI200_REG_VAL_IRQ_BUS_ERROR = (1 << 4),
+ MALI200_REG_VAL_IRQ_BUS_STOP = (1 << 5),
+ MALI200_REG_VAL_IRQ_CNT_0_LIMIT = (1 << 6),
+ MALI200_REG_VAL_IRQ_CNT_1_LIMIT = (1 << 7),
+ MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR = (1 << 8),
+ MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND = (1 << 9),
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW = (1 << 10),
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW = (1 << 11),
+ MALI400PP_REG_VAL_IRQ_RESET_COMPLETED = (1 << 12),
};
#define MALI200_REG_VAL_IRQ_MASK_ALL ((enum mali200_mgmt_irq) (\
- MALI200_REG_VAL_IRQ_END_OF_FRAME |\
- MALI200_REG_VAL_IRQ_END_OF_TILE |\
- MALI200_REG_VAL_IRQ_HANG |\
- MALI200_REG_VAL_IRQ_FORCE_HANG |\
- MALI200_REG_VAL_IRQ_BUS_ERROR |\
- MALI200_REG_VAL_IRQ_BUS_STOP |\
- MALI200_REG_VAL_IRQ_CNT_0_LIMIT |\
- MALI200_REG_VAL_IRQ_CNT_1_LIMIT |\
- MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR |\
- MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND |\
- MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW |\
- MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW |\
- MALI400PP_REG_VAL_IRQ_RESET_COMPLETED))
+ MALI200_REG_VAL_IRQ_END_OF_FRAME |\
+ MALI200_REG_VAL_IRQ_END_OF_TILE |\
+ MALI200_REG_VAL_IRQ_HANG |\
+ MALI200_REG_VAL_IRQ_FORCE_HANG |\
+ MALI200_REG_VAL_IRQ_BUS_ERROR |\
+ MALI200_REG_VAL_IRQ_BUS_STOP |\
+ MALI200_REG_VAL_IRQ_CNT_0_LIMIT |\
+ MALI200_REG_VAL_IRQ_CNT_1_LIMIT |\
+ MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR |\
+ MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND |\
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW |\
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW |\
+ MALI400PP_REG_VAL_IRQ_RESET_COMPLETED))
#define MALI200_REG_VAL_IRQ_MASK_USED ((enum mali200_mgmt_irq) (\
- MALI200_REG_VAL_IRQ_END_OF_FRAME |\
- MALI200_REG_VAL_IRQ_FORCE_HANG |\
- MALI200_REG_VAL_IRQ_BUS_ERROR |\
- MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR |\
- MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND |\
- MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW |\
- MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW))
+ MALI200_REG_VAL_IRQ_END_OF_FRAME |\
+ MALI200_REG_VAL_IRQ_FORCE_HANG |\
+ MALI200_REG_VAL_IRQ_BUS_ERROR |\
+ MALI200_REG_VAL_IRQ_WRITE_BOUNDARY_ERROR |\
+ MALI400PP_REG_VAL_IRQ_INVALID_PLIST_COMMAND |\
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_UNDERFLOW |\
+ MALI400PP_REG_VAL_IRQ_CALL_STACK_OVERFLOW))
#define MALI200_REG_VAL_IRQ_MASK_NONE ((enum mali200_mgmt_irq)(0))
enum mali200_mgmt_status {
- MALI200_REG_VAL_STATUS_RENDERING_ACTIVE = (1<<0),
- MALI200_REG_VAL_STATUS_BUS_STOPPED = (1<<4),
+ MALI200_REG_VAL_STATUS_RENDERING_ACTIVE = (1 << 0),
+ MALI200_REG_VAL_STATUS_BUS_STOPPED = (1 << 4),
};
enum mali200_render_unit {
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @see MALIGP2_CTRL_REG_CMD
*/
typedef enum {
- MALIGP2_REG_VAL_CMD_START_VS = (1<< 0),
- MALIGP2_REG_VAL_CMD_START_PLBU = (1<< 1),
- MALIGP2_REG_VAL_CMD_UPDATE_PLBU_ALLOC = (1<< 4),
- MALIGP2_REG_VAL_CMD_RESET = (1<< 5),
- MALIGP2_REG_VAL_CMD_FORCE_HANG = (1<< 6),
- MALIGP2_REG_VAL_CMD_STOP_BUS = (1<< 9),
- MALI400GP_REG_VAL_CMD_SOFT_RESET = (1<<10), /* only valid for Mali-300 and later */
+ MALIGP2_REG_VAL_CMD_START_VS = (1 << 0),
+ MALIGP2_REG_VAL_CMD_START_PLBU = (1 << 1),
+ MALIGP2_REG_VAL_CMD_UPDATE_PLBU_ALLOC = (1 << 4),
+ MALIGP2_REG_VAL_CMD_RESET = (1 << 5),
+ MALIGP2_REG_VAL_CMD_FORCE_HANG = (1 << 6),
+ MALIGP2_REG_VAL_CMD_STOP_BUS = (1 << 9),
+ MALI400GP_REG_VAL_CMD_SOFT_RESET = (1 << 10), /* only valid for Mali-300 and later */
} mgp_contr_reg_val_cmd;
/* Mask defining all IRQs in Mali GP */
#define MALIGP2_REG_VAL_IRQ_MASK_ALL \
(\
- MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | \
- MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | \
- MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM | \
- MALIGP2_REG_VAL_IRQ_VS_SEM_IRQ | \
- MALIGP2_REG_VAL_IRQ_PLBU_SEM_IRQ | \
- MALIGP2_REG_VAL_IRQ_HANG | \
- MALIGP2_REG_VAL_IRQ_FORCE_HANG | \
- MALIGP2_REG_VAL_IRQ_PERF_CNT_0_LIMIT | \
- MALIGP2_REG_VAL_IRQ_PERF_CNT_1_LIMIT | \
- MALIGP2_REG_VAL_IRQ_WRITE_BOUND_ERR | \
- MALIGP2_REG_VAL_IRQ_SYNC_ERROR | \
- MALIGP2_REG_VAL_IRQ_AXI_BUS_ERROR | \
- MALI400GP_REG_VAL_IRQ_AXI_BUS_STOPPED | \
- MALI400GP_REG_VAL_IRQ_VS_INVALID_CMD | \
- MALI400GP_REG_VAL_IRQ_PLB_INVALID_CMD | \
- MALI400GP_REG_VAL_IRQ_RESET_COMPLETED | \
- MALI400GP_REG_VAL_IRQ_SEMAPHORE_UNDERFLOW | \
- MALI400GP_REG_VAL_IRQ_SEMAPHORE_OVERFLOW | \
- MALI400GP_REG_VAL_IRQ_PTR_ARRAY_OUT_OF_BOUNDS)
+ MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | \
+ MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | \
+ MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM | \
+ MALIGP2_REG_VAL_IRQ_VS_SEM_IRQ | \
+ MALIGP2_REG_VAL_IRQ_PLBU_SEM_IRQ | \
+ MALIGP2_REG_VAL_IRQ_HANG | \
+ MALIGP2_REG_VAL_IRQ_FORCE_HANG | \
+ MALIGP2_REG_VAL_IRQ_PERF_CNT_0_LIMIT | \
+ MALIGP2_REG_VAL_IRQ_PERF_CNT_1_LIMIT | \
+ MALIGP2_REG_VAL_IRQ_WRITE_BOUND_ERR | \
+ MALIGP2_REG_VAL_IRQ_SYNC_ERROR | \
+ MALIGP2_REG_VAL_IRQ_AXI_BUS_ERROR | \
+ MALI400GP_REG_VAL_IRQ_AXI_BUS_STOPPED | \
+ MALI400GP_REG_VAL_IRQ_VS_INVALID_CMD | \
+ MALI400GP_REG_VAL_IRQ_PLB_INVALID_CMD | \
+ MALI400GP_REG_VAL_IRQ_RESET_COMPLETED | \
+ MALI400GP_REG_VAL_IRQ_SEMAPHORE_UNDERFLOW | \
+ MALI400GP_REG_VAL_IRQ_SEMAPHORE_OVERFLOW | \
+ MALI400GP_REG_VAL_IRQ_PTR_ARRAY_OUT_OF_BOUNDS)
/* Mask defining the IRQs in Mali GP which we use */
#define MALIGP2_REG_VAL_IRQ_MASK_USED \
(\
- MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | \
- MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | \
- MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM | \
- MALIGP2_REG_VAL_IRQ_FORCE_HANG | \
- MALIGP2_REG_VAL_IRQ_WRITE_BOUND_ERR | \
- MALIGP2_REG_VAL_IRQ_SYNC_ERROR | \
- MALIGP2_REG_VAL_IRQ_AXI_BUS_ERROR | \
- MALI400GP_REG_VAL_IRQ_VS_INVALID_CMD | \
- MALI400GP_REG_VAL_IRQ_PLB_INVALID_CMD | \
- MALI400GP_REG_VAL_IRQ_SEMAPHORE_UNDERFLOW | \
- MALI400GP_REG_VAL_IRQ_SEMAPHORE_OVERFLOW | \
- MALI400GP_REG_VAL_IRQ_PTR_ARRAY_OUT_OF_BOUNDS)
+ MALIGP2_REG_VAL_IRQ_VS_END_CMD_LST | \
+ MALIGP2_REG_VAL_IRQ_PLBU_END_CMD_LST | \
+ MALIGP2_REG_VAL_IRQ_PLBU_OUT_OF_MEM | \
+ MALIGP2_REG_VAL_IRQ_FORCE_HANG | \
+ MALIGP2_REG_VAL_IRQ_WRITE_BOUND_ERR | \
+ MALIGP2_REG_VAL_IRQ_SYNC_ERROR | \
+ MALIGP2_REG_VAL_IRQ_AXI_BUS_ERROR | \
+ MALI400GP_REG_VAL_IRQ_VS_INVALID_CMD | \
+ MALI400GP_REG_VAL_IRQ_PLB_INVALID_CMD | \
+ MALI400GP_REG_VAL_IRQ_SEMAPHORE_UNDERFLOW | \
+ MALI400GP_REG_VAL_IRQ_SEMAPHORE_OVERFLOW | \
+ MALI400GP_REG_VAL_IRQ_PTR_ARRAY_OUT_OF_BOUNDS)
/* Mask defining non IRQs on MaliGP2*/
#define MALIGP2_REG_VAL_IRQ_MASK_NONE 0
/** }@ defgroup MALIGP2_STATUS*/
#define MALIGP2_REG_VAL_STATUS_MASK_ACTIVE (\
- MALIGP2_REG_VAL_STATUS_VS_ACTIVE|\
- MALIGP2_REG_VAL_STATUS_PLBU_ACTIVE)
+ MALIGP2_REG_VAL_STATUS_VS_ACTIVE|\
+ MALIGP2_REG_VAL_STATUS_PLBU_ACTIVE)
#define MALIGP2_REG_VAL_STATUS_MASK_ERROR (\
- MALIGP2_REG_VAL_STATUS_BUS_ERROR |\
- MALIGP2_REG_VAL_STATUS_WRITE_BOUND_ERR )
+ MALIGP2_REG_VAL_STATUS_BUS_ERROR |\
+ MALIGP2_REG_VAL_STATUS_WRITE_BOUND_ERR )
/* This should be in the top 16 bit of the version register of gp.*/
#define MALI200_GP_PRODUCT_ID 0xA07
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
*/
u32 mask = (1 << 0) | /* enable all three counters */
- (0 << 1) | /* reset both Count Registers to 0x0 */
- (1 << 2) | /* reset the Cycle Counter Register to 0x0 */
- (0 << 3) | /* 1 = Cycle Counter Register counts every 64th processor clock cycle */
- (0 << 4) | /* Count Register 0 interrupt enable */
- (0 << 5) | /* Count Register 1 interrupt enable */
- (0 << 6) | /* Cycle Counter interrupt enable */
- (0 << 8) | /* Count Register 0 overflow flag (clear or write, flag on read) */
- (0 << 9) | /* Count Register 1 overflow flag (clear or write, flag on read) */
- (1 << 10); /* Cycle Counter Register overflow flag (clear or write, flag on read) */
-
- __asm__ __volatile__ ("MCR p15, 0, %0, c15, c12, 0" : : "r" (mask) );
+ (0 << 1) | /* reset both Count Registers to 0x0 */
+ (1 << 2) | /* reset the Cycle Counter Register to 0x0 */
+ (0 << 3) | /* 1 = Cycle Counter Register counts every 64th processor clock cycle */
+ (0 << 4) | /* Count Register 0 interrupt enable */
+ (0 << 5) | /* Count Register 1 interrupt enable */
+ (0 << 6) | /* Cycle Counter interrupt enable */
+ (0 << 8) | /* Count Register 0 overflow flag (clear or write, flag on read) */
+ (0 << 9) | /* Count Register 1 overflow flag (clear or write, flag on read) */
+ (1 << 10); /* Cycle Counter Register overflow flag (clear or write, flag on read) */
+
+ __asm__ __volatile__("MCR p15, 0, %0, c15, c12, 0" : : "r"(mask));
return _MALI_OSK_ERR_OK;
}
u32 result;
/* this is for the clock cycles */
- __asm__ __volatile__ ("MRC p15, 0, %0, c15, c12, 1" : "=r" (result));
+ __asm__ __volatile__("MRC p15, 0, %0, c15, c12, 1" : "=r"(result));
return (u64)result;
}
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
ccflags-y += -I$(TOP_KBUILD_SRC)$(src)/linux/license/proprietary
else
ccflags-y += -I$(TOP_KBUILD_SRC)$(src)/linux/license/gpl
+ccflags-y += -I$(TOP_KBUILD_SRC)$(src)/../mali/linux/license/gpl
endif
linux/ump_osk_atomics.o \
linux/ump_osk_low_level_mem.o \
linux/ump_osk_misc.o \
+ linux/ump_kernel_random_mapping.o \
__mali_osk_locks.o \
__mali_osk_memory.o \
__mali_osk_atomics.o \
#
-# Copyright (C) 2010-2012 ARM Limited. All rights reserved.
+# Copyright (C) 2010-2012, 2014 ARM Limited. All rights reserved.
#
# This program is free software and is provided to you under the terms of the GNU General Public License version 2
# as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#
-# Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+# Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
#
# This program is free software and is provided to you under the terms of the GNU General Public License version 2
# as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_uk_types.h"
#include "ump_kernel_interface.h"
#include "ump_kernel_common.h"
+#include "ump_kernel_random_mapping.h"
UMP_KERNEL_API_EXPORT ump_secure_id ump_dd_secure_id_get(ump_dd_handle memh)
{
- ump_dd_mem * mem = (ump_dd_mem *)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
DEBUG_ASSERT_POINTER(mem);
UMP_KERNEL_API_EXPORT ump_dd_handle ump_dd_handle_create_from_secure_id(ump_secure_id secure_id)
{
- ump_dd_mem * mem;
-
- _mali_osk_mutex_wait(device.secure_id_map_lock);
+ ump_dd_mem *mem;
DBG_MSG(5, ("Getting handle from secure ID. ID: %u\n", secure_id));
- if (0 != ump_descriptor_mapping_get(device.secure_id_map, (int)secure_id, (void**)&mem)) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
+ mem = ump_random_mapping_get(device.secure_id_map, (int)secure_id);
+ if (NULL == mem) {
DBG_MSG(1, ("Secure ID not found. ID: %u\n", secure_id));
return UMP_DD_HANDLE_INVALID;
}
- ump_dd_reference_add(mem);
-
- _mali_osk_mutex_signal(device.secure_id_map_lock);
+ /* Keep the reference taken in ump_random_mapping_get() */
return (ump_dd_handle)mem;
}
UMP_KERNEL_API_EXPORT unsigned long ump_dd_phys_block_count_get(ump_dd_handle memh)
{
- ump_dd_mem * mem = (ump_dd_mem*) memh;
+ ump_dd_mem *mem = (ump_dd_mem *) memh;
DEBUG_ASSERT_POINTER(mem);
-UMP_KERNEL_API_EXPORT ump_dd_status_code ump_dd_phys_blocks_get(ump_dd_handle memh, ump_dd_physical_block * blocks, unsigned long num_blocks)
+UMP_KERNEL_API_EXPORT ump_dd_status_code ump_dd_phys_blocks_get(ump_dd_handle memh, ump_dd_physical_block *blocks, unsigned long num_blocks)
{
- ump_dd_mem * mem = (ump_dd_mem *)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
DEBUG_ASSERT_POINTER(mem);
-UMP_KERNEL_API_EXPORT ump_dd_status_code ump_dd_phys_block_get(ump_dd_handle memh, unsigned long index, ump_dd_physical_block * block)
+UMP_KERNEL_API_EXPORT ump_dd_status_code ump_dd_phys_block_get(ump_dd_handle memh, unsigned long index, ump_dd_physical_block *block)
{
- ump_dd_mem * mem = (ump_dd_mem *)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
DEBUG_ASSERT_POINTER(mem);
UMP_KERNEL_API_EXPORT unsigned long ump_dd_size_get(ump_dd_handle memh)
{
- ump_dd_mem * mem = (ump_dd_mem*)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
DEBUG_ASSERT_POINTER(mem);
UMP_KERNEL_API_EXPORT void ump_dd_reference_add(ump_dd_handle memh)
{
- ump_dd_mem * mem = (ump_dd_mem*)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
int new_ref;
DEBUG_ASSERT_POINTER(mem);
UMP_KERNEL_API_EXPORT void ump_dd_reference_release(ump_dd_handle memh)
{
- int new_ref;
- ump_dd_mem * mem = (ump_dd_mem*)memh;
+ ump_dd_mem *mem = (ump_dd_mem *)memh;
DEBUG_ASSERT_POINTER(mem);
- /* We must hold this mutex while doing the atomic_dec_and_read, to protect
- that elements in the ump_descriptor_mapping table is always valid. If they
- are not, userspace may accidently map in this secure_ids right before its freed
- giving a mapped backdoor into unallocated memory.*/
- _mali_osk_mutex_wait(device.secure_id_map_lock);
-
- new_ref = _ump_osk_atomic_dec_and_read(&mem->ref_count);
-
- DBG_MSG(5, ("Memory reference decremented. ID: %u, new value: %d\n", mem->secure_id, new_ref));
-
- if (0 == new_ref) {
- DBG_MSG(3, ("Final release of memory. ID: %u\n", mem->secure_id));
-
- ump_descriptor_mapping_free(device.secure_id_map, (int)mem->secure_id);
-
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- mem->release_func(mem->ctx, mem);
- _mali_osk_free(mem);
- } else {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- }
+ ump_random_mapping_put(mem);
}
/* --------------- Handling of user space requests follows --------------- */
-_mali_osk_errcode_t _ump_uku_get_api_version( _ump_uk_api_version_s *args )
+_mali_osk_errcode_t _ump_uku_get_api_version(_ump_uk_api_version_s *args)
{
- ump_session_data * session_data;
+ ump_session_data *session_data;
- DEBUG_ASSERT_POINTER( args );
- DEBUG_ASSERT_POINTER( args->ctx );
+ DEBUG_ASSERT_POINTER(args);
+ DEBUG_ASSERT_POINTER(args->ctx);
session_data = (ump_session_data *)args->ctx;
/* check compatability */
if (args->version == UMP_IOCTL_API_VERSION) {
- DBG_MSG(3, ("API version set to newest %d (compatible)\n", GET_VERSION(args->version)));
- args->compatible = 1;
- session_data->api_version = args->version;
- } else if (args->version == MAKE_VERSION_ID(1)) {
- DBG_MSG(2, ("API version set to depricated: %d (compatible)\n", GET_VERSION(args->version)));
+ DBG_MSG(3, ("API version set to newest %d (compatible)\n",
+ GET_VERSION(args->version)));
args->compatible = 1;
session_data->api_version = args->version;
} else {
- DBG_MSG(2, ("API version set to %d (incompatible with client version %d)\n", GET_VERSION(UMP_IOCTL_API_VERSION), GET_VERSION(args->version)));
+ DBG_MSG(2, ("API version set to %d (incompatible with client version %d)\n",
+ GET_VERSION(UMP_IOCTL_API_VERSION), GET_VERSION(args->version)));
args->compatible = 0;
args->version = UMP_IOCTL_API_VERSION; /* report our version */
}
}
-_mali_osk_errcode_t _ump_ukk_release( _ump_uk_release_s *release_info )
+_mali_osk_errcode_t _ump_ukk_release(_ump_uk_release_s *release_info)
{
- ump_session_memory_list_element * session_memory_element;
- ump_session_memory_list_element * tmp;
- ump_session_data * session_data;
+ ump_session_memory_list_element *session_memory_element;
+ ump_session_memory_list_element *tmp;
+ ump_session_data *session_data;
_mali_osk_errcode_t ret = _MALI_OSK_ERR_INVALID_FUNC;
int secure_id;
- DEBUG_ASSERT_POINTER( release_info );
- DEBUG_ASSERT_POINTER( release_info->ctx );
+ DEBUG_ASSERT_POINTER(release_info);
+ DEBUG_ASSERT_POINTER(release_info->ctx);
/* Retreive the session data */
- session_data = (ump_session_data*)release_info->ctx;
+ session_data = (ump_session_data *)release_info->ctx;
/* If there are many items in the memory session list we
* could be de-referencing this pointer a lot so keep a local copy
/* Iterate through the memory list looking for the requested secure ID */
_mali_osk_mutex_wait(session_data->lock);
_MALI_OSK_LIST_FOREACHENTRY(session_memory_element, tmp, &session_data->list_head_session_memory_list, ump_session_memory_list_element, list) {
- if ( session_memory_element->mem->secure_id == secure_id) {
+ if (session_memory_element->mem->secure_id == secure_id) {
ump_dd_mem *release_mem;
release_mem = session_memory_element->mem;
return ret;
}
-_mali_osk_errcode_t _ump_ukk_size_get( _ump_uk_size_get_s *user_interaction )
+_mali_osk_errcode_t _ump_ukk_size_get(_ump_uk_size_get_s *user_interaction)
{
- ump_dd_mem * mem;
+ ump_dd_mem *mem;
_mali_osk_errcode_t ret = _MALI_OSK_ERR_FAULT;
- DEBUG_ASSERT_POINTER( user_interaction );
+ DEBUG_ASSERT_POINTER(user_interaction);
/* We lock the mappings so things don't get removed while we are looking for the memory */
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- if (0 == ump_descriptor_mapping_get(device.secure_id_map, (int)user_interaction->secure_id, (void**)&mem)) {
+ mem = ump_random_mapping_get(device.secure_id_map, user_interaction->secure_id);
+ if (NULL != mem) {
user_interaction->size = mem->size_bytes;
- DBG_MSG(4, ("Returning size. ID: %u, size: %lu ", (ump_secure_id)user_interaction->secure_id, (unsigned long)user_interaction->size));
+ DBG_MSG(4, ("Returning size. ID: %u, size: %lu ",
+ (ump_secure_id)user_interaction->secure_id,
+ (unsigned long)user_interaction->size));
+ ump_random_mapping_put(mem);
ret = _MALI_OSK_ERR_OK;
} else {
user_interaction->size = 0;
- DBG_MSG(1, ("Failed to look up mapping in ump_ioctl_size_get(). ID: %u\n", (ump_secure_id)user_interaction->secure_id));
+ DBG_MSG(1, ("Failed to look up mapping in ump_ioctl_size_get(). ID: %u\n",
+ (ump_secure_id)user_interaction->secure_id));
}
- _mali_osk_mutex_signal(device.secure_id_map_lock);
return ret;
}
-void _ump_ukk_msync( _ump_uk_msync_s *args )
+void _ump_ukk_msync(_ump_uk_msync_s *args)
{
- ump_dd_mem * mem = NULL;
+ ump_dd_mem *mem = NULL;
void *virtual = NULL;
u32 size = 0;
u32 offset = 0;
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- ump_descriptor_mapping_get(device.secure_id_map, (int)args->secure_id, (void**)&mem);
-
+ mem = ump_random_mapping_get(device.secure_id_map, (int)args->secure_id);
if (NULL == mem) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_msync(). ID: %u\n", (ump_secure_id)args->secure_id));
+ DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_msync(). ID: %u\n",
+ (ump_secure_id)args->secure_id));
return;
}
- /* Ensure the memory doesn't dissapear when we are flushing it. */
- ump_dd_reference_add(mem);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
/* Returns the cache settings back to Userspace */
- args->is_cached=mem->is_cached;
+ args->is_cached = mem->is_cached;
/* If this flag is the only one set, we should not do the actual flush, only the readout */
- if ( _UMP_UK_MSYNC_READOUT_CACHE_ENABLED==args->op ) {
+ if (_UMP_UK_MSYNC_READOUT_CACHE_ENABLED == args->op) {
DBG_MSG(3, ("_ump_ukk_msync READOUT ID: %u Enabled: %d\n", (ump_secure_id)args->secure_id, mem->is_cached));
goto msync_release_and_return;
}
/* Nothing to do if the memory is not caches */
- if ( 0==mem->is_cached ) {
+ if (0 == mem->is_cached) {
DBG_MSG(3, ("_ump_ukk_msync IGNORING ID: %u Enabled: %d OP: %d\n", (ump_secure_id)args->secure_id, mem->is_cached, args->op));
goto msync_release_and_return;
}
DBG_MSG(3, ("UMP[%02u] _ump_ukk_msync Flush OP: %d Address: 0x%08x Mapping: 0x%08x\n",
- (ump_secure_id)args->secure_id, args->op, args->address, args->mapping));
+ (ump_secure_id)args->secure_id, args->op, args->address, args->mapping));
- if ( args->address ) {
+ if (args->address) {
virtual = (void *)((u32)args->address);
offset = (u32)((args->address) - (args->mapping));
} else {
/* Flush entire mapping when no address is specified. */
virtual = args->mapping;
}
- if ( args->size ) {
+ if (args->size) {
size = args->size;
} else {
/* Flush entire mapping when no size is specified. */
size = mem->size_bytes - offset;
}
- if ( (offset + size) > mem->size_bytes ) {
+ if ((offset + size) > mem->size_bytes) {
DBG_MSG(1, ("Trying to flush more than the entire UMP allocation: offset: %u + size: %u > %u\n", offset, size, mem->size_bytes));
goto msync_release_and_return;
}
/* The actual cache flush - Implemented for each OS*/
- _ump_osk_msync( mem, virtual, offset, size, args->op, NULL);
+ _ump_osk_msync(mem, virtual, offset, size, args->op, NULL);
msync_release_and_return:
- ump_dd_reference_release(mem);
+ ump_random_mapping_put(mem);
return;
}
-void _ump_ukk_cache_operations_control(_ump_uk_cache_operations_control_s* args)
+void _ump_ukk_cache_operations_control(_ump_uk_cache_operations_control_s *args)
{
- ump_session_data * session_data;
+ ump_session_data *session_data;
ump_uk_cache_op_control op;
- DEBUG_ASSERT_POINTER( args );
- DEBUG_ASSERT_POINTER( args->ctx );
+ DEBUG_ASSERT_POINTER(args);
+ DEBUG_ASSERT_POINTER(args->ctx);
op = args->op;
session_data = (ump_session_data *)args->ctx;
_mali_osk_mutex_wait(session_data->lock);
- if ( op== _UMP_UK_CACHE_OP_START ) {
+ if (op == _UMP_UK_CACHE_OP_START) {
session_data->cache_operations_ongoing++;
- DBG_MSG(4, ("Cache ops start\n" ));
- if ( session_data->cache_operations_ongoing != 1 ) {
- DBG_MSG(2, ("UMP: Number of simultanious cache control ops: %d\n", session_data->cache_operations_ongoing) );
+ DBG_MSG(4, ("Cache ops start\n"));
+ if (session_data->cache_operations_ongoing != 1) {
+ DBG_MSG(2, ("UMP: Number of simultanious cache control ops: %d\n", session_data->cache_operations_ongoing));
}
- } else if ( op== _UMP_UK_CACHE_OP_FINISH ) {
+ } else if (op == _UMP_UK_CACHE_OP_FINISH) {
DBG_MSG(4, ("Cache ops finish\n"));
session_data->cache_operations_ongoing--;
#if 0
- if ( session_data->has_pending_level1_cache_flush) {
+ if (session_data->has_pending_level1_cache_flush) {
/* This function will set has_pending_level1_cache_flush=0 */
- _ump_osk_msync( NULL, NULL, 0, 0, _UMP_UK_MSYNC_FLUSH_L1, session_data);
+ _ump_osk_msync(NULL, NULL, 0, 0, _UMP_UK_MSYNC_FLUSH_L1, session_data);
}
#endif
/* to be on the safe side: always flush l1 cache when cache operations are done */
- _ump_osk_msync( NULL, NULL, 0, 0, _UMP_UK_MSYNC_FLUSH_L1, session_data);
- DBG_MSG(4, ("Cache ops finish end\n" ));
+ _ump_osk_msync(NULL, NULL, 0, 0, _UMP_UK_MSYNC_FLUSH_L1, session_data);
+ DBG_MSG(4, ("Cache ops finish end\n"));
} else {
DBG_MSG(1, ("Illegal call to %s at line %d\n", __FUNCTION__, __LINE__));
}
}
-void _ump_ukk_switch_hw_usage(_ump_uk_switch_hw_usage_s *args )
+void _ump_ukk_switch_hw_usage(_ump_uk_switch_hw_usage_s *args)
{
- ump_dd_mem * mem = NULL;
+ ump_dd_mem *mem = NULL;
ump_uk_user old_user;
ump_uk_msync_op cache_op = _UMP_UK_MSYNC_CLEAN_AND_INVALIDATE;
ump_session_data *session_data;
- DEBUG_ASSERT_POINTER( args );
- DEBUG_ASSERT_POINTER( args->ctx );
+ DEBUG_ASSERT_POINTER(args);
+ DEBUG_ASSERT_POINTER(args->ctx);
session_data = (ump_session_data *)args->ctx;
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- ump_descriptor_mapping_get(device.secure_id_map, (int)args->secure_id, (void**)&mem);
-
+ mem = ump_random_mapping_get(device.secure_id_map, (int)args->secure_id);
if (NULL == mem) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_switch_hw_usage(). ID: %u\n", (ump_secure_id)args->secure_id));
+ DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_switch_hw_usage(). ID: %u\n",
+ (ump_secure_id)args->secure_id));
return;
}
old_user = mem->hw_device;
mem->hw_device = args->new_user;
- DBG_MSG(3, ("UMP[%02u] Switch usage Start New: %s Prev: %s.\n", (ump_secure_id)args->secure_id, args->new_user?"MALI":"CPU",old_user?"MALI":"CPU"));
+ DBG_MSG(3, ("UMP[%02u] Switch usage Start New: %s Prev: %s.\n",
+ (ump_secure_id)args->secure_id,
+ args->new_user ? "MALI" : "CPU",
+ old_user ? "MALI" : "CPU"));
- if ( ! mem->is_cached ) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(3, ("UMP[%02u] Changing owner of uncached memory. Cache flushing not needed.\n", (ump_secure_id)args->secure_id));
- return;
+ if (!mem->is_cached) {
+ DBG_MSG(3, ("UMP[%02u] Changing owner of uncached memory. Cache flushing not needed.\n",
+ (ump_secure_id)args->secure_id));
+ goto out;
}
- if ( old_user == args->new_user) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(4, ("UMP[%02u] Setting the new_user equal to previous for. Cache flushing not needed.\n", (ump_secure_id)args->secure_id));
- return;
+ if (old_user == args->new_user) {
+ DBG_MSG(4, ("UMP[%02u] Setting the new_user equal to previous for. Cache flushing not needed.\n",
+ (ump_secure_id)args->secure_id));
+ goto out;
}
if (
- /* Previous AND new is both different from CPU */
- (old_user != _UMP_UK_USED_BY_CPU) && (args->new_user != _UMP_UK_USED_BY_CPU )
+ /* Previous AND new is both different from CPU */
+ (old_user != _UMP_UK_USED_BY_CPU) && (args->new_user != _UMP_UK_USED_BY_CPU)
) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(4, ("UMP[%02u] Previous and new user is not CPU. Cache flushing not needed.\n", (ump_secure_id)args->secure_id));
- return;
+ DBG_MSG(4, ("UMP[%02u] Previous and new user is not CPU. Cache flushing not needed.\n",
+ (ump_secure_id)args->secure_id));
+ goto out;
}
- if ( (old_user != _UMP_UK_USED_BY_CPU ) && (args->new_user==_UMP_UK_USED_BY_CPU) ) {
- cache_op =_UMP_UK_MSYNC_INVALIDATE;
+ if ((old_user != _UMP_UK_USED_BY_CPU) && (args->new_user == _UMP_UK_USED_BY_CPU)) {
+ cache_op = _UMP_UK_MSYNC_INVALIDATE;
DBG_MSG(4, ("UMP[%02u] Cache invalidation needed\n", (ump_secure_id)args->secure_id));
#ifdef UMP_SKIP_INVALIDATION
#error
- _mali_osk_mutex_signal(device.secure_id_map_lock);
DBG_MSG(4, ("UMP[%02u] Performing Cache invalidation SKIPPED\n", (ump_secure_id)args->secure_id));
- return;
+ goto out;
#endif
}
- /* Ensure the memory doesn't dissapear when we are flushing it. */
- ump_dd_reference_add(mem);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
/* Take lock to protect: session->cache_operations_ongoing and session->has_pending_level1_cache_flush */
_mali_osk_mutex_wait(session_data->lock);
/* Actual cache flush */
- _ump_osk_msync( mem, NULL, 0, mem->size_bytes, cache_op, session_data);
+ _ump_osk_msync(mem, NULL, 0, mem->size_bytes, cache_op, session_data);
_mali_osk_mutex_signal(session_data->lock);
- ump_dd_reference_release(mem);
+out:
+ ump_random_mapping_put(mem);
DBG_MSG(4, ("UMP[%02u] Switch usage Finish\n", (ump_secure_id)args->secure_id));
return;
}
-void _ump_ukk_lock(_ump_uk_lock_s *args )
+void _ump_ukk_lock(_ump_uk_lock_s *args)
{
- ump_dd_mem * mem = NULL;
-
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- ump_descriptor_mapping_get(device.secure_id_map, (int)args->secure_id, (void**)&mem);
+ ump_dd_mem *mem = NULL;
+ mem = ump_random_mapping_get(device.secure_id_map, (int)args->secure_id);
if (NULL == mem) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("UMP[%02u] Failed to look up mapping in _ump_ukk_lock(). ID: %u\n", (ump_secure_id)args->secure_id));
+ DBG_MSG(1, ("UMP[%02u] Failed to look up mapping in _ump_ukk_lock(). ID: %u\n",
+ (ump_secure_id)args->secure_id));
return;
}
- ump_dd_reference_add(mem);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("UMP[%02u] Lock. New lock flag: %d. Old Lock flag:\n", (u32)args->secure_id, (u32)args->lock_usage, (u32) mem->lock_usage ));
+ DBG_MSG(1, ("UMP[%02u] Lock. New lock flag: %d. Old Lock flag:\n", (u32)args->secure_id, (u32)args->lock_usage, (u32) mem->lock_usage));
mem->lock_usage = (ump_lock_usage) args->lock_usage;
- ump_dd_reference_release(mem);
+ ump_random_mapping_put(mem);
}
-void _ump_ukk_unlock(_ump_uk_unlock_s *args )
+void _ump_ukk_unlock(_ump_uk_unlock_s *args)
{
- ump_dd_mem * mem = NULL;
-
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- ump_descriptor_mapping_get(device.secure_id_map, (int)args->secure_id, (void**)&mem);
+ ump_dd_mem *mem = NULL;
+ mem = ump_random_mapping_get(device.secure_id_map, (int)args->secure_id);
if (NULL == mem) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_unlock(). ID: %u\n", (ump_secure_id)args->secure_id));
+ DBG_MSG(1, ("Failed to look up mapping in _ump_ukk_unlock(). ID: %u\n",
+ (ump_secure_id)args->secure_id));
return;
}
- ump_dd_reference_add(mem);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- DBG_MSG(1, ("UMP[%02u] Unlocking. Old Lock flag:\n", (u32)args->secure_id, (u32) mem->lock_usage ));
+ DBG_MSG(1, ("UMP[%02u] Unlocking. Old Lock flag:\n",
+ (u32)args->secure_id, (u32) mem->lock_usage));
mem->lock_usage = (ump_lock_usage) UMP_NOT_LOCKED;
- ump_dd_reference_release(mem);
+ ump_random_mapping_put(mem);
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/* Perform OS Specific initialization */
err = _ump_osk_init();
- if( _MALI_OSK_ERR_OK != err ) {
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("Failed to initiaze the UMP Device Driver"));
return err;
}
/* Init the global device */
- _mali_osk_memset(&device, 0, sizeof(device) );
+ _mali_osk_memset(&device, 0, sizeof(device));
/* Create the descriptor map, which will be used for mapping secure ID to ump_dd_mem structs */
- device.secure_id_map_lock = _mali_osk_mutex_init(_MALI_OSK_LOCKFLAG_UNORDERED, 0);
- if (NULL == device.secure_id_map_lock) {
- MSG_ERR(("Failed to create OSK lock for secure id lookup table\n"));
- return _MALI_OSK_ERR_NOMEM;
- }
-
- device.secure_id_map = ump_descriptor_mapping_create(UMP_SECURE_ID_TABLE_ENTRIES_INITIAL, UMP_SECURE_ID_TABLE_ENTRIES_MAXIMUM);
+ device.secure_id_map = ump_random_mapping_create();
if (NULL == device.secure_id_map) {
- _mali_osk_mutex_term(device.secure_id_map_lock);
MSG_ERR(("Failed to create secure id lookup table\n"));
return _MALI_OSK_ERR_NOMEM;
}
device.backend = ump_memory_backend_create();
if (NULL == device.backend) {
MSG_ERR(("Failed to create memory backend\n"));
- _mali_osk_mutex_term(device.secure_id_map_lock);
- ump_descriptor_mapping_destroy(device.secure_id_map);
+ ump_random_mapping_destroy(device.secure_id_map);
return _MALI_OSK_ERR_NOMEM;
}
void ump_kernel_destructor(void)
{
DEBUG_ASSERT_POINTER(device.secure_id_map);
- DEBUG_ASSERT_POINTER(device.secure_id_map_lock);
-
- _mali_osk_mutex_term(device.secure_id_map_lock);
- device.secure_id_map_lock = NULL;
- ump_descriptor_mapping_destroy(device.secure_id_map);
+ ump_random_mapping_destroy(device.secure_id_map);
device.secure_id_map = NULL;
device.backend->shutdown(device.backend);
/** Creates a new UMP session
*/
-_mali_osk_errcode_t _ump_ukk_open( void** context )
+_mali_osk_errcode_t _ump_ukk_open(void **context)
{
- struct ump_session_data * session_data;
+ struct ump_session_data *session_data;
/* allocated struct to track this session */
session_data = (struct ump_session_data *)_mali_osk_malloc(sizeof(struct ump_session_data));
}
session_data->lock = _mali_osk_mutex_init(_MALI_OSK_LOCKFLAG_UNORDERED, 0);
- if( NULL == session_data->lock ) {
+ if (NULL == session_data->lock) {
MSG_ERR(("Failed to initialize lock for ump_session_data in ump_file_open()\n"));
_mali_osk_free(session_data);
return _MALI_OSK_ERR_NOMEM;
}
- session_data->cookies_map = ump_descriptor_mapping_create( UMP_COOKIES_PER_SESSION_INITIAL, UMP_COOKIES_PER_SESSION_MAXIMUM );
+ session_data->cookies_map = ump_descriptor_mapping_create(
+ UMP_COOKIES_PER_SESSION_INITIAL,
+ UMP_COOKIES_PER_SESSION_MAXIMUM);
- if ( NULL == session_data->cookies_map ) {
+ if (NULL == session_data->cookies_map) {
MSG_ERR(("Failed to create descriptor mapping for _ump_ukk_map_mem cookies\n"));
_mali_osk_mutex_term(session_data->lock);
- _mali_osk_free( session_data );
+ _mali_osk_free(session_data);
return _MALI_OSK_ERR_NOMEM;
}
to the correct one.*/
session_data->api_version = MAKE_VERSION_ID(1);
- *context = (void*)session_data;
+ *context = (void *)session_data;
session_data->cache_operations_ongoing = 0 ;
session_data->has_pending_level1_cache_flush = 0;
return _MALI_OSK_ERR_OK;
}
-_mali_osk_errcode_t _ump_ukk_close( void** context )
+_mali_osk_errcode_t _ump_ukk_close(void **context)
{
- struct ump_session_data * session_data;
- ump_session_memory_list_element * item;
- ump_session_memory_list_element * tmp;
+ struct ump_session_data *session_data;
+ ump_session_memory_list_element *item;
+ ump_session_memory_list_element *tmp;
session_data = (struct ump_session_data *)*context;
if (NULL == session_data) {
_MALI_OSK_LIST_FOREACHENTRY(descriptor, temp, &session_data->list_head_session_memory_mappings_list, ump_memory_allocation, list) {
_ump_uk_unmap_mem_s unmap_args;
DBG_MSG(4, ("Freeing block with phys address 0x%x size 0x%x mapped in user space at 0x%x\n",
- descriptor->phys_addr, descriptor->size, descriptor->mapping));
- unmap_args.ctx = (void*)session_data;
+ descriptor->phys_addr, descriptor->size, descriptor->mapping));
+ unmap_args.ctx = (void *)session_data;
unmap_args.mapping = descriptor->mapping;
unmap_args.size = descriptor->size;
unmap_args._ukk_private = NULL; /* NOTE: unused */
unmap_args.cookie = descriptor->cookie;
/* NOTE: This modifies the list_head_session_memory_mappings_list */
- _ump_ukk_unmap_mem( &unmap_args );
+ _ump_ukk_unmap_mem(&unmap_args);
}
}
/* ASSERT that we really did free everything, because _ump_ukk_unmap_mem()
* can fail silently. */
- DEBUG_ASSERT( _mali_osk_list_empty(&session_data->list_head_session_memory_mappings_list) );
+ DEBUG_ASSERT(_mali_osk_list_empty(&session_data->list_head_session_memory_mappings_list));
_MALI_OSK_LIST_FOREACHENTRY(item, tmp, &session_data->list_head_session_memory_list, ump_session_memory_list_element, list) {
_mali_osk_list_del(&item->list);
_mali_osk_free(item);
}
- ump_descriptor_mapping_destroy( session_data->cookies_map );
+ ump_descriptor_mapping_destroy(session_data->cookies_map);
_mali_osk_mutex_term(session_data->lock);
_mali_osk_free(session_data);
return _MALI_OSK_ERR_OK;
}
-_mali_osk_errcode_t _ump_ukk_map_mem( _ump_uk_map_mem_s *args )
+_mali_osk_errcode_t _ump_ukk_map_mem(_ump_uk_map_mem_s *args)
{
- struct ump_session_data * session_data;
- ump_memory_allocation * descriptor; /* Describes current mapping of memory */
+ struct ump_session_data *session_data;
+ ump_memory_allocation *descriptor; /* Describes current mapping of memory */
_mali_osk_errcode_t err;
unsigned long offset = 0;
unsigned long left;
ump_dd_handle handle; /* The real UMP handle for this memory. Its real datatype is ump_dd_mem* */
- ump_dd_mem * mem; /* The real UMP memory. It is equal to the handle, but with exposed struct */
+ ump_dd_mem *mem; /* The real UMP memory. It is equal to the handle, but with exposed struct */
u32 block;
int map_id;
session_data = (ump_session_data *)args->ctx;
- if( NULL == session_data ) {
+ if (NULL == session_data) {
MSG_ERR(("Session data is NULL in _ump_ukk_map_mem()\n"));
return _MALI_OSK_ERR_INVALID_ARGS;
}
- descriptor = (ump_memory_allocation*) _mali_osk_calloc( 1, sizeof(ump_memory_allocation));
+ descriptor = (ump_memory_allocation *) _mali_osk_calloc(1, sizeof(ump_memory_allocation));
if (NULL == descriptor) {
MSG_ERR(("ump_ukk_map_mem: descriptor allocation failed\n"));
return _MALI_OSK_ERR_NOMEM;
}
handle = ump_dd_handle_create_from_secure_id(args->secure_id);
- if ( UMP_DD_HANDLE_INVALID == handle) {
+ if (UMP_DD_HANDLE_INVALID == handle) {
_mali_osk_free(descriptor);
DBG_MSG(1, ("Trying to map unknown secure ID %u\n", args->secure_id));
return _MALI_OSK_ERR_FAULT;
}
- mem = (ump_dd_mem*)handle;
+ mem = (ump_dd_mem *)handle;
DEBUG_ASSERT(mem);
if (mem->size_bytes != args->size) {
_mali_osk_free(descriptor);
return _MALI_OSK_ERR_FAULT;
}
- map_id = ump_descriptor_mapping_allocate_mapping( session_data->cookies_map, (void*) descriptor );
+ map_id = ump_descriptor_mapping_allocate_mapping(session_data->cookies_map, (void *) descriptor);
if (map_id < 0) {
_mali_osk_free(descriptor);
descriptor->ump_session = session_data;
descriptor->cookie = (u32)map_id;
- if ( mem->is_cached ) {
+ if (mem->is_cached) {
descriptor->is_cached = 1;
args->is_cached = 1;
DBG_MSG(3, ("Mapping UMP secure_id: %d as cached.\n", args->secure_id));
DBG_MSG(3, ("Mapping UMP secure_id: %d as Uncached.\n", args->secure_id));
}
- _mali_osk_list_init( &descriptor->list );
+ _mali_osk_list_init(&descriptor->list);
- err = _ump_osk_mem_mapregion_init( descriptor );
- if( _MALI_OSK_ERR_OK != err ) {
+ err = _ump_osk_mem_mapregion_init(descriptor);
+ if (_MALI_OSK_ERR_OK != err) {
DBG_MSG(1, ("Failed to initialize memory mapping in _ump_ukk_map_mem(). ID: %u\n", args->secure_id));
- ump_descriptor_mapping_free( session_data->cookies_map, map_id );
+ ump_descriptor_mapping_free(session_data->cookies_map, map_id);
_mali_osk_free(descriptor);
ump_dd_reference_release(mem);
return err;
}
DBG_MSG(4, ("Mapping virtual to physical memory: ID: %u, size:%lu, first physical addr: 0x%08lx, number of regions: %lu\n",
- mem->secure_id,
- mem->size_bytes,
- ((NULL != mem->block_array) ? mem->block_array->addr : 0),
- mem->nr_blocks));
+ mem->secure_id,
+ mem->size_bytes,
+ ((NULL != mem->block_array) ? mem->block_array->addr : 0),
+ mem->nr_blocks));
left = descriptor->size;
/* loop over all blocks and map them in */
size_to_map = left;
}
- if (_MALI_OSK_ERR_OK != _ump_osk_mem_mapregion_map(descriptor, offset, (u32 *)&(mem->block_array[block].addr), size_to_map ) ) {
+ if (_MALI_OSK_ERR_OK != _ump_osk_mem_mapregion_map(descriptor, offset, (u32 *) & (mem->block_array[block].addr), size_to_map)) {
DBG_MSG(1, ("WARNING: _ump_ukk_map_mem failed to map memory into userspace\n"));
- ump_descriptor_mapping_free( session_data->cookies_map, map_id );
+ ump_descriptor_mapping_free(session_data->cookies_map, map_id);
ump_dd_reference_release(mem);
- _ump_osk_mem_mapregion_term( descriptor );
+ _ump_osk_mem_mapregion_term(descriptor);
_mali_osk_free(descriptor);
return _MALI_OSK_ERR_FAULT;
}
/* Add to the ump_memory_allocation tracking list */
_mali_osk_mutex_wait(session_data->lock);
- _mali_osk_list_add( &descriptor->list, &session_data->list_head_session_memory_mappings_list );
+ _mali_osk_list_add(&descriptor->list, &session_data->list_head_session_memory_mappings_list);
_mali_osk_mutex_signal(session_data->lock);
args->mapping = descriptor->mapping;
return _MALI_OSK_ERR_OK;
}
-void _ump_ukk_unmap_mem( _ump_uk_unmap_mem_s *args )
+void _ump_ukk_unmap_mem(_ump_uk_unmap_mem_s *args)
{
- struct ump_session_data * session_data;
- ump_memory_allocation * descriptor;
+ struct ump_session_data *session_data;
+ ump_memory_allocation *descriptor;
ump_dd_handle handle;
session_data = (ump_session_data *)args->ctx;
- if( NULL == session_data ) {
+ if (NULL == session_data) {
MSG_ERR(("Session data is NULL in _ump_ukk_map_mem()\n"));
return;
}
- if (0 != ump_descriptor_mapping_get( session_data->cookies_map, (int)args->cookie, (void**)&descriptor) ) {
- MSG_ERR(("_ump_ukk_map_mem: cookie 0x%X not found for this session\n", args->cookie ));
+ if (0 != ump_descriptor_mapping_get(session_data->cookies_map, (int)args->cookie, (void **)&descriptor)) {
+ MSG_ERR(("_ump_ukk_map_mem: cookie 0x%X not found for this session\n", args->cookie));
return;
}
DEBUG_ASSERT_POINTER(descriptor);
handle = descriptor->handle;
- if ( UMP_DD_HANDLE_INVALID == handle) {
+ if (UMP_DD_HANDLE_INVALID == handle) {
DBG_MSG(1, ("WARNING: Trying to unmap unknown handle: UNKNOWN\n"));
return;
}
/* Remove the ump_memory_allocation from the list of tracked mappings */
_mali_osk_mutex_wait(session_data->lock);
- _mali_osk_list_del( &descriptor->list );
+ _mali_osk_list_del(&descriptor->list);
_mali_osk_mutex_signal(session_data->lock);
- ump_descriptor_mapping_free( session_data->cookies_map, (int)args->cookie );
+ ump_descriptor_mapping_free(session_data->cookies_map, (int)args->cookie);
ump_dd_reference_release(handle);
- _ump_osk_mem_mapregion_term( descriptor );
+ _ump_osk_mem_mapregion_term(descriptor);
_mali_osk_free(descriptor);
}
-u32 _ump_ukk_report_memory_usage( void )
+u32 _ump_ukk_report_memory_usage(void)
{
- if(device.backend->stat)
+ if (device.backend->stat)
return device.backend->stat(device.backend);
else
return 0;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_kernel_types.h"
#include "ump_kernel_interface.h"
#include "ump_kernel_descriptor_mapping.h"
+#include "ump_kernel_random_mapping.h"
#include "ump_kernel_memory_backend.h"
((level) <= ump_debug_level)?\
UMP_DEBUG_PRINT(("UMP<" #level ">: ")), \
UMP_DEBUG_PRINT(args):0; \
- } while (0)
+ } while (0)
#define DBG_MSG_IF(level,condition,args) /* args should be in brackets */ \
- if((condition)&&((level) <= ump_debug_level)) {\
+ if((condition)&&((level) <= ump_debug_level)) {\
UMP_DEBUG_PRINT(("UMP<" #level ">: ")); \
UMP_DEBUG_PRINT(args); \
- }
+ }
#define DBG_MSG_ELSE(level,args) /* args should be in brackets */ \
- else if((level) <= ump_debug_level) { \
+ else if((level) <= ump_debug_level) { \
UMP_DEBUG_PRINT(("UMP<" #level ">: ")); \
UMP_DEBUG_PRINT(args); \
- }
+ }
#define DEBUG_ASSERT_POINTER(pointer) do {if( (pointer)== NULL) MSG_ERR(("NULL pointer " #pointer)); } while(0)
#define DEBUG_ASSERT(condition) do {if(!(condition)) MSG_ERR(("ASSERT failed: " #condition)); } while(0)
#endif /* DEBUG */
#define MSG_ERR(args) do{ /* args should be in brackets */ \
- _mali_osk_dbgmsg("UMP: ERR: %s\n" ,__FILE__); \
- _mali_osk_dbgmsg( " %s()%4d\n", __FUNCTION__, __LINE__) ; \
- _mali_osk_dbgmsg args ; \
- _mali_osk_dbgmsg("\n"); \
+ _mali_osk_dbgmsg("UMP: ERR: %s\n" ,__FILE__); \
+ _mali_osk_dbgmsg( " %s()%4d\n", __FUNCTION__, __LINE__) ; \
+ _mali_osk_dbgmsg args ; \
+ _mali_osk_dbgmsg("\n"); \
} while(0)
#define MSG(args) do{ /* args should be in brackets */ \
- _mali_osk_dbgmsg("UMP: "); \
- _mali_osk_dbgmsg args; \
- } while (0)
+ _mali_osk_dbgmsg("UMP: "); \
+ _mali_osk_dbgmsg args; \
+ } while (0)
_mali_osk_list_t list_head_session_memory_mappings_list; /**< List of ump_memory_allocations mapped in */
int api_version;
_mali_osk_mutex_t *lock;
- ump_descriptor_mapping * cookies_map; /**< Secure mapping of cookies from _ump_ukk_map_mem() */
+ ump_descriptor_mapping *cookies_map; /**< Secure mapping of cookies from _ump_ukk_map_mem() */
int cache_operations_ongoing;
int has_pending_level1_cache_flush;
} ump_session_data;
* which don't do it themself (e.g. due to a crash or premature termination).
*/
typedef struct ump_session_memory_list_element {
- struct ump_dd_mem * mem;
+ struct ump_dd_mem *mem;
_mali_osk_list_t list;
} ump_session_memory_list_element;
* Device specific data, created when device driver is loaded, and then kept as the global variable device.
*/
typedef struct ump_dev {
- _mali_osk_mutex_t *secure_id_map_lock;
- ump_descriptor_mapping * secure_id_map;
- ump_memory_backend * backend;
+ ump_random_mapping *secure_id_map;
+ ump_memory_backend *backend;
} ump_dev;
_mali_osk_errcode_t ump_kernel_constructor(void);
void ump_kernel_destructor(void);
-int map_errcode( _mali_osk_errcode_t err );
+int map_errcode(_mali_osk_errcode_t err);
/**
* variables from user space cannot be dereferenced from kernel space; tagging them
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* @param count Number of mappings in the table
* @return Pointer to a new table, NULL on error
*/
-static ump_descriptor_table * descriptor_table_alloc(int count);
+static ump_descriptor_table *descriptor_table_alloc(int count);
/**
* Free a descriptor table
* @param table The table to free
*/
-static void descriptor_table_free(ump_descriptor_table * table);
+static void descriptor_table_free(ump_descriptor_table *table);
-ump_descriptor_mapping * ump_descriptor_mapping_create(int init_entries, int max_entries)
+ump_descriptor_mapping *ump_descriptor_mapping_create(int init_entries, int max_entries)
{
- ump_descriptor_mapping * map = _mali_osk_calloc(1, sizeof(ump_descriptor_mapping) );
+ ump_descriptor_mapping *map = _mali_osk_calloc(1, sizeof(ump_descriptor_mapping));
init_entries = MALI_PAD_INT(init_entries);
max_entries = MALI_PAD_INT(max_entries);
map->table = descriptor_table_alloc(init_entries);
if (NULL != map->table) {
map->lock = _mali_osk_mutex_rw_init(_MALI_OSK_LOCKFLAG_UNORDERED, 0);
- if ( NULL != map->lock ) {
+ if (NULL != map->lock) {
_mali_osk_set_nonatomic_bit(0, map->table->usage); /* reserve bit 0 to prevent NULL/zero logic to kick in */
map->max_nr_mappings_allowed = max_entries;
map->current_nr_mappings = init_entries;
return NULL;
}
-void ump_descriptor_mapping_destroy(ump_descriptor_mapping * map)
+void ump_descriptor_mapping_destroy(ump_descriptor_mapping *map)
{
descriptor_table_free(map->table);
_mali_osk_mutex_rw_term(map->lock);
_mali_osk_free(map);
}
-int ump_descriptor_mapping_allocate_mapping(ump_descriptor_mapping * map, void * target)
+int ump_descriptor_mapping_allocate_mapping(ump_descriptor_mapping *map, void *target)
{
int descriptor = -1;/*-EFAULT;*/
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RW);
if (descriptor == map->current_nr_mappings) {
int nr_mappings_new;
/* no free descriptor, try to expand the table */
- ump_descriptor_table * new_table;
- ump_descriptor_table * old_table = map->table;
- nr_mappings_new= map->current_nr_mappings *2;
+ ump_descriptor_table *new_table;
+ ump_descriptor_table *old_table = map->table;
+ nr_mappings_new = map->current_nr_mappings * 2;
if (map->current_nr_mappings >= map->max_nr_mappings_allowed) {
descriptor = -1;
}
_mali_osk_memcpy(new_table->usage, old_table->usage, (sizeof(unsigned long)*map->current_nr_mappings) / BITS_PER_LONG);
- _mali_osk_memcpy(new_table->mappings, old_table->mappings, map->current_nr_mappings * sizeof(void*));
+ _mali_osk_memcpy(new_table->mappings, old_table->mappings, map->current_nr_mappings * sizeof(void *));
map->table = new_table;
map->current_nr_mappings = nr_mappings_new;
descriptor_table_free(old_table);
return descriptor;
}
-int ump_descriptor_mapping_get(ump_descriptor_mapping * map, int descriptor, void** target)
+int ump_descriptor_mapping_get(ump_descriptor_mapping *map, int descriptor, void **target)
{
int result = -1;/*-EFAULT;*/
DEBUG_ASSERT(map);
return result;
}
-int ump_descriptor_mapping_set(ump_descriptor_mapping * map, int descriptor, void * target)
+int ump_descriptor_mapping_set(ump_descriptor_mapping *map, int descriptor, void *target)
{
int result = -1;/*-EFAULT;*/
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RO);
return result;
}
-void ump_descriptor_mapping_free(ump_descriptor_mapping * map, int descriptor)
+void ump_descriptor_mapping_free(ump_descriptor_mapping *map, int descriptor)
{
_mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RW);
if ((descriptor > 0) && (descriptor < map->current_nr_mappings) && _mali_osk_test_bit(descriptor, map->table->usage)) {
_mali_osk_mutex_rw_signal(map->lock, _MALI_OSK_LOCKMODE_RW);
}
-static ump_descriptor_table * descriptor_table_alloc(int count)
+static ump_descriptor_table *descriptor_table_alloc(int count)
{
- ump_descriptor_table * table;
+ ump_descriptor_table *table;
- table = _mali_osk_calloc(1, sizeof(ump_descriptor_table) + ((sizeof(unsigned long) * count)/BITS_PER_LONG) + (sizeof(void*) * count) );
+ table = _mali_osk_calloc(1, sizeof(ump_descriptor_table) + ((sizeof(unsigned long) * count) / BITS_PER_LONG) + (sizeof(void *) * count));
if (NULL != table) {
- table->usage = (u32*)((u8*)table + sizeof(ump_descriptor_table));
- table->mappings = (void**)((u8*)table + sizeof(ump_descriptor_table) + ((sizeof(unsigned long) * count)/BITS_PER_LONG));
+ table->usage = (u32 *)((u8 *)table + sizeof(ump_descriptor_table));
+ table->mappings = (void **)((u8 *)table + sizeof(ump_descriptor_table) + ((sizeof(unsigned long) * count) / BITS_PER_LONG));
}
return table;
}
-static void descriptor_table_free(ump_descriptor_table * table)
+static void descriptor_table_free(ump_descriptor_table *table)
{
_mali_osk_free(table);
}
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* The actual descriptor mapping table, never directly accessed by clients
*/
typedef struct ump_descriptor_table {
- u32 * usage; /**< Pointer to bitpattern indicating if a descriptor is valid/used or not */
- void** mappings; /**< Array of the pointers the descriptors map to */
+ u32 *usage; /**< Pointer to bitpattern indicating if a descriptor is valid/used or not */
+ void **mappings; /**< Array of the pointers the descriptors map to */
} ump_descriptor_table;
/**
_mali_osk_mutex_rw_t *lock; /**< Lock protecting access to the mapping object */
int max_nr_mappings_allowed; /**< Max number of mappings to support in this namespace */
int current_nr_mappings; /**< Current number of possible mappings */
- ump_descriptor_table * table; /**< Pointer to the current mapping table */
+ ump_descriptor_table *table; /**< Pointer to the current mapping table */
} ump_descriptor_mapping;
/**
* @param max_entries Number of entries to max support
* @return Pointer to a descriptor mapping object, NULL on failure
*/
-ump_descriptor_mapping * ump_descriptor_mapping_create(int init_entries, int max_entries);
+ump_descriptor_mapping *ump_descriptor_mapping_create(int init_entries, int max_entries);
/**
* Destroy a descriptor mapping object
* @param map The map to free
*/
-void ump_descriptor_mapping_destroy(ump_descriptor_mapping * map);
+void ump_descriptor_mapping_destroy(ump_descriptor_mapping *map);
/**
* Allocate a new mapping entry (descriptor ID)
* @param target The value to map to
* @return The descriptor allocated, a negative value on error
*/
-int ump_descriptor_mapping_allocate_mapping(ump_descriptor_mapping * map, void * target);
+int ump_descriptor_mapping_allocate_mapping(ump_descriptor_mapping *map, void *target);
/**
* Get the value mapped to by a descriptor ID
* @param target Pointer to a pointer which will receive the stored value
* @return 0 on successful lookup, negative on error
*/
-int ump_descriptor_mapping_get(ump_descriptor_mapping * map, int descriptor, void** target);
+int ump_descriptor_mapping_get(ump_descriptor_mapping *map, int descriptor, void **target);
/**
* Set the value mapped to by a descriptor ID
* @param target Pointer to replace the current value with
* @return 0 on successful lookup, negative on error
*/
-int ump_descriptor_mapping_set(ump_descriptor_mapping * map, int descriptor, void * target);
+int ump_descriptor_mapping_set(ump_descriptor_mapping *map, int descriptor, void *target);
/**
* Free the descriptor ID
* @param map The map to free the descriptor from
* @param descriptor The descriptor ID to free
*/
-void ump_descriptor_mapping_free(ump_descriptor_mapping * map, int descriptor);
+void ump_descriptor_mapping_free(ump_descriptor_mapping *map, int descriptor);
#endif /* __UMP_KERNEL_DESCRIPTOR_MAPPING_H__ */
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
typedef struct ump_memory_allocation {
- void * phys_addr;
- void * mapping;
+ void *phys_addr;
+ void *mapping;
unsigned long size;
ump_dd_handle handle;
- void * process_mapping_info;
+ void *process_mapping_info;
u32 cookie; /**< necessary on some U/K interface implementations */
- struct ump_session_data * ump_session; /**< Session that this allocation belongs to */
+ struct ump_session_data *ump_session; /**< Session that this allocation belongs to */
_mali_osk_list_t list; /**< List for linking together memory allocations into the session's memory head */
u32 is_cached;
} ump_memory_allocation;
typedef struct ump_memory_backend {
- int (*allocate)(void* ctx, ump_dd_mem * descriptor);
- void (*release)(void* ctx, ump_dd_mem * descriptor);
- void (*shutdown)(struct ump_memory_backend * backend);
- u32 (*stat)(struct ump_memory_backend *backend);
- int (*pre_allocate_physical_check)(void *ctx, u32 size);
- u32 (*adjust_to_mali_phys)(void *ctx, u32 cpu_phys);
- void * ctx;
+ int (*allocate)(void *ctx, ump_dd_mem *descriptor);
+ void (*release)(void *ctx, ump_dd_mem *descriptor);
+ void (*shutdown)(struct ump_memory_backend *backend);
+ u32(*stat)(struct ump_memory_backend *backend);
+ int (*pre_allocate_physical_check)(void *ctx, u32 size);
+ u32(*adjust_to_mali_phys)(void *ctx, u32 cpu_phys);
+ void *ctx;
} ump_memory_backend;
-ump_memory_backend * ump_memory_backend_create ( void );
-void ump_memory_backend_destroy( void );
+ump_memory_backend *ump_memory_backend_create(void);
+void ump_memory_backend_destroy(void);
#endif /*__UMP_KERNEL_MEMORY_BACKEND_H__ */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#define UMP_MINIMUM_SIZE_MASK (~(UMP_MINIMUM_SIZE-1))
#define UMP_SIZE_ALIGN(x) (((x)+UMP_MINIMUM_SIZE-1)&UMP_MINIMUM_SIZE_MASK)
#define UMP_ADDR_ALIGN_OFFSET(x) ((x)&(UMP_MINIMUM_SIZE-1))
-static void phys_blocks_release(void * ctx, struct ump_dd_mem * descriptor);
+static void phys_blocks_release(void *ctx, struct ump_dd_mem *descriptor);
-UMP_KERNEL_API_EXPORT ump_dd_handle ump_dd_handle_create_from_phys_blocks(ump_dd_physical_block * blocks, unsigned long num_blocks)
+UMP_KERNEL_API_EXPORT ump_dd_handle ump_dd_handle_create_from_phys_blocks(ump_dd_physical_block *blocks, unsigned long num_blocks)
{
- ump_dd_mem * mem;
+ ump_dd_mem *mem;
unsigned long size_total = 0;
- int map_id;
+ int ret;
u32 i;
/* Go through the input blocks and verify that they are sane */
- for (i=0; i < num_blocks; i++) {
+ for (i = 0; i < num_blocks; i++) {
unsigned long addr = blocks[i].addr;
unsigned long size = blocks[i].size;
return UMP_DD_HANDLE_INVALID;
}
- /* Find a secure ID for this allocation */
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- map_id = ump_descriptor_mapping_allocate_mapping(device.secure_id_map, (void*) mem);
-
- if (map_id < 0) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- _mali_osk_free(mem);
- DBG_MSG(1, ("Failed to allocate secure ID in ump_dd_handle_create_from_phys_blocks()\n"));
- return UMP_DD_HANDLE_INVALID;
- }
-
/* Now, make a copy of the block information supplied by the user */
- mem->block_array = _mali_osk_malloc(sizeof(ump_dd_physical_block)* num_blocks);
+ mem->block_array = _mali_osk_malloc(sizeof(ump_dd_physical_block) * num_blocks);
if (NULL == mem->block_array) {
- ump_descriptor_mapping_free(device.secure_id_map, map_id);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
_mali_osk_free(mem);
DBG_MSG(1, ("Could not allocate a mem handle for function ump_dd_handle_create_from_phys_blocks().\n"));
return UMP_DD_HANDLE_INVALID;
/* And setup the rest of the ump_dd_mem struct */
_mali_osk_atomic_init(&mem->ref_count, 1);
- mem->secure_id = (ump_secure_id)map_id;
mem->size_bytes = size_total;
mem->nr_blocks = num_blocks;
mem->backend_info = NULL;
mem->hw_device = _UMP_UK_USED_BY_CPU;
mem->lock_usage = UMP_NOT_LOCKED;
- _mali_osk_mutex_signal(device.secure_id_map_lock);
+ /* Find a secure ID for this allocation */
+ ret = ump_random_mapping_insert(device.secure_id_map, mem);
+ if (unlikely(ret)) {
+ _mali_osk_free(mem->block_array);
+ _mali_osk_free(mem);
+ DBG_MSG(1, ("Failed to allocate secure ID in ump_dd_handle_create_from_phys_blocks()\n"));
+ return UMP_DD_HANDLE_INVALID;
+ }
+
DBG_MSG(3, ("UMP memory created. ID: %u, size: %lu\n", mem->secure_id, mem->size_bytes));
return (ump_dd_handle)mem;
}
-static void phys_blocks_release(void * ctx, struct ump_dd_mem * descriptor)
+static void phys_blocks_release(void *ctx, struct ump_dd_mem *descriptor)
{
_mali_osk_free(descriptor->block_array);
descriptor->block_array = NULL;
}
-_mali_osk_errcode_t _ump_ukk_allocate( _ump_uk_allocate_s *user_interaction )
+_mali_osk_errcode_t _ump_ukk_allocate(_ump_uk_allocate_s *user_interaction)
{
- ump_session_data * session_data = NULL;
+ ump_session_data *session_data = NULL;
ump_dd_mem *new_allocation = NULL;
- ump_session_memory_list_element * session_memory_element = NULL;
- int map_id;
+ ump_session_memory_list_element *session_memory_element = NULL;
+ int ret;
- DEBUG_ASSERT_POINTER( user_interaction );
- DEBUG_ASSERT_POINTER( user_interaction->ctx );
+ DEBUG_ASSERT_POINTER(user_interaction);
+ DEBUG_ASSERT_POINTER(user_interaction->ctx);
session_data = (ump_session_data *) user_interaction->ctx;
- session_memory_element = _mali_osk_calloc( 1, sizeof(ump_session_memory_list_element));
+ session_memory_element = _mali_osk_calloc(1, sizeof(ump_session_memory_list_element));
if (NULL == session_memory_element) {
DBG_MSG(1, ("Failed to allocate ump_session_memory_list_element in ump_ioctl_allocate()\n"));
return _MALI_OSK_ERR_NOMEM;
}
- new_allocation = _mali_osk_calloc( 1, sizeof(ump_dd_mem));
- if (NULL==new_allocation) {
+ new_allocation = _mali_osk_calloc(1, sizeof(ump_dd_mem));
+ if (NULL == new_allocation) {
_mali_osk_free(session_memory_element);
DBG_MSG(1, ("Failed to allocate ump_dd_mem in _ump_ukk_allocate()\n"));
return _MALI_OSK_ERR_NOMEM;
}
- /* Create a secure ID for this allocation */
- _mali_osk_mutex_wait(device.secure_id_map_lock);
- map_id = ump_descriptor_mapping_allocate_mapping(device.secure_id_map, (void*)new_allocation);
-
- if (map_id < 0) {
- _mali_osk_mutex_signal(device.secure_id_map_lock);
- _mali_osk_free(session_memory_element);
- _mali_osk_free(new_allocation);
- DBG_MSG(1, ("Failed to allocate secure ID in ump_ioctl_allocate()\n"));
- return - _MALI_OSK_ERR_INVALID_FUNC;
- }
-
/* Initialize the part of the new_allocation that we know so for */
- new_allocation->secure_id = (ump_secure_id)map_id;
- _mali_osk_atomic_init(&new_allocation->ref_count,1);
- if ( 0==(UMP_REF_DRV_UK_CONSTRAINT_USE_CACHE & user_interaction->constraints) )
+ _mali_osk_atomic_init(&new_allocation->ref_count, 1);
+ if (0 == (UMP_REF_DRV_UK_CONSTRAINT_USE_CACHE & user_interaction->constraints))
new_allocation->is_cached = 0;
else new_allocation->is_cached = 1;
- /* special case a size of 0, we should try to emulate what malloc does in this case, which is to return a valid pointer that must be freed, but can't be dereferences */
+ /* Special case a size of 0, we should try to emulate what malloc does
+ * in this case, which is to return a valid pointer that must be freed,
+ * but can't be dereferenced */
if (0 == user_interaction->size) {
- user_interaction->size = 1; /* emulate by actually allocating the minimum block size */
+ /* Emulate by actually allocating the minimum block size */
+ user_interaction->size = 1;
}
- new_allocation->size_bytes = UMP_SIZE_ALIGN(user_interaction->size); /* Page align the size */
+ /* Page align the size */
+ new_allocation->size_bytes = UMP_SIZE_ALIGN(user_interaction->size);
new_allocation->lock_usage = UMP_NOT_LOCKED;
/* Now, ask the active memory backend to do the actual memory allocation */
- if (!device.backend->allocate( device.backend->ctx, new_allocation ) ) {
- DBG_MSG(3, ("OOM: No more UMP memory left. Failed to allocate memory in ump_ioctl_allocate(). Size: %lu, requested size: %lu\n", new_allocation->size_bytes, (unsigned long)user_interaction->size));
- ump_descriptor_mapping_free(device.secure_id_map, map_id);
- _mali_osk_mutex_signal(device.secure_id_map_lock);
+ if (!device.backend->allocate(device.backend->ctx, new_allocation)) {
+ DBG_MSG(3, ("OOM: No more UMP memory left. Failed to allocate memory in ump_ioctl_allocate(). Size: %lu, requested size: %lu\n",
+ new_allocation->size_bytes,
+ (unsigned long)user_interaction->size));
_mali_osk_free(new_allocation);
_mali_osk_free(session_memory_element);
return _MALI_OSK_ERR_INVALID_FUNC;
new_allocation->ctx = device.backend->ctx;
new_allocation->release_func = device.backend->release;
- _mali_osk_mutex_signal(device.secure_id_map_lock);
-
/* Initialize the session_memory_element, and add it to the session object */
session_memory_element->mem = new_allocation;
_mali_osk_mutex_wait(session_data->lock);
_mali_osk_list_add(&(session_memory_element->list), &(session_data->list_head_session_memory_list));
_mali_osk_mutex_signal(session_data->lock);
+ /* Create a secure ID for this allocation */
+ ret = ump_random_mapping_insert(device.secure_id_map, new_allocation);
+ if (unlikely(ret)) {
+ new_allocation->release_func(new_allocation->ctx, new_allocation);
+ _mali_osk_free(session_memory_element);
+ _mali_osk_free(new_allocation);
+ DBG_MSG(1, ("Failed to allocate secure ID in ump_ioctl_allocate()\n"));
+ return _MALI_OSK_ERR_INVALID_FUNC;
+ }
+
user_interaction->secure_id = new_allocation->secure_id;
user_interaction->size = new_allocation->size_bytes;
- DBG_MSG(3, ("UMP memory allocated. ID: %u, size: %lu\n", new_allocation->secure_id, new_allocation->size_bytes));
+ DBG_MSG(3, ("UMP memory allocated. ID: %u, size: %lu\n",
+ new_allocation->secure_id,
+ new_allocation->size_bytes));
return _MALI_OSK_ERR_OK;
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_kernel_interface.h"
#include "mali_osk.h"
+#include <linux/rbtree.h>
typedef enum {
UMP_USED_BY_CPU = 0,
UMP_USED_BY_MALI = 1,
- UMP_USED_BY_UNKNOWN_DEVICE= 100,
+ UMP_USED_BY_UNKNOWN_DEVICE = 100,
} ump_hw_usage;
typedef enum {
UMP_READ_WRITE = 3,
} ump_lock_usage;
-
/*
* This struct is what is "behind" a ump_dd_handle
*/
typedef struct ump_dd_mem {
+ struct rb_node node;
ump_secure_id secure_id;
_mali_osk_atomic_t ref_count;
unsigned long size_bytes;
unsigned long nr_blocks;
- ump_dd_physical_block * block_array;
- void (*release_func)(void * ctx, struct ump_dd_mem * descriptor);
- void * ctx;
- void * backend_info;
+ ump_dd_physical_block *block_array;
+ void (*release_func)(void *ctx, struct ump_dd_mem *descriptor);
+ void *ctx;
+ void *backend_info;
int is_cached;
ump_hw_usage hw_device;
ump_lock_usage lock_usage;
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
extern "C" {
#endif
-_mali_osk_errcode_t _ump_osk_init( void );
+_mali_osk_errcode_t _ump_osk_init(void);
-_mali_osk_errcode_t _ump_osk_term( void );
+_mali_osk_errcode_t _ump_osk_term(void);
-int _ump_osk_atomic_inc_and_read( _mali_osk_atomic_t *atom );
+int _ump_osk_atomic_inc_and_read(_mali_osk_atomic_t *atom);
-int _ump_osk_atomic_dec_and_read( _mali_osk_atomic_t *atom );
+int _ump_osk_atomic_dec_and_read(_mali_osk_atomic_t *atom);
-_mali_osk_errcode_t _ump_osk_mem_mapregion_init( ump_memory_allocation *descriptor );
+_mali_osk_errcode_t _ump_osk_mem_mapregion_init(ump_memory_allocation *descriptor);
-_mali_osk_errcode_t _ump_osk_mem_mapregion_map( ump_memory_allocation * descriptor, u32 offset, u32 * phys_addr, unsigned long size );
+_mali_osk_errcode_t _ump_osk_mem_mapregion_map(ump_memory_allocation *descriptor, u32 offset, u32 *phys_addr, unsigned long size);
-void _ump_osk_mem_mapregion_term( ump_memory_allocation * descriptor );
+void _ump_osk_mem_mapregion_term(ump_memory_allocation *descriptor);
-void _ump_osk_msync( ump_dd_mem * mem, void * virt, u32 offset, u32 size, ump_uk_msync_op op, ump_session_data * session_data );
+void _ump_osk_msync(ump_dd_mem *mem, void *virt, u32 offset, u32 size, ump_uk_msync_op op, ump_session_data *session_data);
#ifdef __cplusplus
}
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
* The 16bit integer is stored twice in a 32bit integer
* So for version 1 the value would be 0x00010001
*/
-#define UMP_IOCTL_API_VERSION MAKE_VERSION_ID(2)
+#define UMP_IOCTL_API_VERSION MAKE_VERSION_ID(3)
typedef enum
{
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#endif
-_mali_osk_errcode_t _ump_ukk_open( void** context );
+_mali_osk_errcode_t _ump_ukk_open(void **context);
-_mali_osk_errcode_t _ump_ukk_close( void** context );
+_mali_osk_errcode_t _ump_ukk_close(void **context);
-_mali_osk_errcode_t _ump_ukk_allocate( _ump_uk_allocate_s *user_interaction );
+_mali_osk_errcode_t _ump_ukk_allocate(_ump_uk_allocate_s *user_interaction);
-_mali_osk_errcode_t _ump_ukk_release( _ump_uk_release_s *release_info );
+_mali_osk_errcode_t _ump_ukk_release(_ump_uk_release_s *release_info);
-_mali_osk_errcode_t _ump_ukk_size_get( _ump_uk_size_get_s *user_interaction );
+_mali_osk_errcode_t _ump_ukk_size_get(_ump_uk_size_get_s *user_interaction);
-_mali_osk_errcode_t _ump_ukk_map_mem( _ump_uk_map_mem_s *args );
+_mali_osk_errcode_t _ump_ukk_map_mem(_ump_uk_map_mem_s *args);
-_mali_osk_errcode_t _ump_uku_get_api_version( _ump_uk_api_version_s *args );
+_mali_osk_errcode_t _ump_uku_get_api_version(_ump_uk_api_version_s *args);
-void _ump_ukk_unmap_mem( _ump_uk_unmap_mem_s *args );
+void _ump_ukk_unmap_mem(_ump_uk_unmap_mem_s *args);
-void _ump_ukk_msync( _ump_uk_msync_s *args );
+void _ump_ukk_msync(_ump_uk_msync_s *args);
-void _ump_ukk_cache_operations_control(_ump_uk_cache_operations_control_s* args);
+void _ump_ukk_cache_operations_control(_ump_uk_cache_operations_control_s *args);
-void _ump_ukk_switch_hw_usage(_ump_uk_switch_hw_usage_s *args );
+void _ump_ukk_switch_hw_usage(_ump_uk_switch_hw_usage_s *args);
-void _ump_ukk_lock(_ump_uk_lock_s *args );
+void _ump_ukk_lock(_ump_uk_lock_s *args);
-void _ump_ukk_unlock(_ump_uk_unlock_s *args );
+void _ump_ukk_unlock(_ump_uk_unlock_s *args);
-u32 _ump_ukk_report_memory_usage( void );
+u32 _ump_ukk_report_memory_usage(void);
#ifdef __cplusplus
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
struct ump_device {
struct cdev cdev;
#if UMP_LICENSE_IS_GPL
- struct class * ump_class;
+ struct class *ump_class;
#endif
};
#else
static int ump_file_ioctl(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg);
#endif
-static int ump_file_mmap(struct file * filp, struct vm_area_struct * vma);
+static int ump_file_mmap(struct file *filp, struct vm_area_struct *vma);
/* This variable defines the file operations this UMP device driver offer */
if (IS_ERR(ump_device.ump_class)) {
err = PTR_ERR(ump_device.ump_class);
} else {
- struct device * mdev;
+ struct device *mdev;
mdev = device_create(ump_device.ump_class, NULL, dev, NULL, ump_dev_name);
if (!IS_ERR(mdev)) {
return 0;
unregister_chrdev_region(dev, 1);
#if UMP_LICENSE_IS_GPL
- if(ump_debugfs_dir)
+ if (ump_debugfs_dir)
debugfs_remove_recursive(ump_debugfs_dir);
#endif
}
*/
static int ump_file_open(struct inode *inode, struct file *filp)
{
- struct ump_session_data * session_data;
+ struct ump_session_data *session_data;
_mali_osk_errcode_t err;
/* input validation */
}
/* Call the OS-Independent UMP Open function */
- err = _ump_ukk_open((void**) &session_data );
- if( _MALI_OSK_ERR_OK != err ) {
+ err = _ump_ukk_open((void **) &session_data);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("Ump failed to open a new session\n"));
- return map_errcode( err );
+ return map_errcode(err);
}
- filp->private_data = (void*)session_data;
+ filp->private_data = (void *)session_data;
filp->f_pos = 0;
return 0; /* success */
{
_mali_osk_errcode_t err;
- err = _ump_ukk_close((void**) &filp->private_data );
- if( _MALI_OSK_ERR_OK != err ) {
- return map_errcode( err );
+ err = _ump_ukk_close((void **) &filp->private_data);
+ if (_MALI_OSK_ERR_OK != err) {
+ return map_errcode(err);
}
return 0; /* success */
#endif
{
int err = -ENOTTY;
- void __user * argument;
- struct ump_session_data * session_data;
+ void __user *argument;
+ struct ump_session_data *session_data;
#ifndef HAVE_UNLOCKED_IOCTL
(void)inode; /* inode not used */
return err;
}
-int map_errcode( _mali_osk_errcode_t err )
+int map_errcode(_mali_osk_errcode_t err)
{
- switch(err) {
+ switch (err) {
case _MALI_OSK_ERR_OK :
return 0;
case _MALI_OSK_ERR_FAULT:
/*
* Handle from OS to map specified virtual memory to specified UMP memory.
*/
-static int ump_file_mmap(struct file * filp, struct vm_area_struct * vma)
+static int ump_file_mmap(struct file *filp, struct vm_area_struct *vma)
{
_ump_uk_map_mem_s args;
_mali_osk_errcode_t err;
- struct ump_session_data * session_data;
+ struct ump_session_data *session_data;
/* Validate the session data */
session_data = (struct ump_session_data *)filp->private_data;
/* By setting this flag, during a process fork; the child process will not have the parent UMP mappings */
vma->vm_flags |= VM_DONTCOPY;
- DBG_MSG(4, ("UMP vma->flags: %x\n", vma->vm_flags ));
+ DBG_MSG(4, ("UMP vma->flags: %x\n", vma->vm_flags));
/* Call the common mmap handler */
- err = _ump_ukk_map_mem( &args );
- if ( _MALI_OSK_ERR_OK != err) {
+ err = _ump_ukk_map_mem(&args);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("_ump_ukk_map_mem() failed in function ump_file_mmap()"));
- return map_errcode( err );
+ return map_errcode(err);
}
return 0; /* success */
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
typedef struct block_info {
- struct block_info * next;
+ struct block_info *next;
} block_info;
typedef struct block_allocator {
struct semaphore mutex;
- block_info * all_blocks;
- block_info * first_free;
+ block_info *all_blocks;
+ block_info *first_free;
u32 base;
u32 num_blocks;
u32 num_free;
} block_allocator;
-static void block_allocator_shutdown(ump_memory_backend * backend);
-static int block_allocator_allocate(void* ctx, ump_dd_mem * mem);
-static void block_allocator_release(void * ctx, ump_dd_mem * handle);
-static inline u32 get_phys(block_allocator * allocator, block_info * block);
+static void block_allocator_shutdown(ump_memory_backend *backend);
+static int block_allocator_allocate(void *ctx, ump_dd_mem *mem);
+static void block_allocator_release(void *ctx, ump_dd_mem *handle);
+static inline u32 get_phys(block_allocator *allocator, block_info *block);
static u32 block_allocator_stat(struct ump_memory_backend *backend);
/*
* Create dedicated memory backend
*/
-ump_memory_backend * ump_block_allocator_create(u32 base_address, u32 size)
+ump_memory_backend *ump_block_allocator_create(u32 base_address, u32 size)
{
- ump_memory_backend * backend;
- block_allocator * allocator;
+ ump_memory_backend *backend;
+ block_allocator *allocator;
u32 usable_size;
u32 num_blocks;
/*
* Destroy specified dedicated memory backend
*/
-static void block_allocator_shutdown(ump_memory_backend * backend)
+static void block_allocator_shutdown(ump_memory_backend *backend)
{
- block_allocator * allocator;
+ block_allocator *allocator;
BUG_ON(!backend);
BUG_ON(!backend->ctx);
- allocator = (block_allocator*)backend->ctx;
+ allocator = (block_allocator *)backend->ctx;
DBG_MSG_IF(1, allocator->num_free != allocator->num_blocks, ("%u blocks still in use during shutdown\n", allocator->num_blocks - allocator->num_free));
-static int block_allocator_allocate(void* ctx, ump_dd_mem * mem)
+static int block_allocator_allocate(void *ctx, ump_dd_mem *mem)
{
- block_allocator * allocator;
+ block_allocator *allocator;
u32 left;
- block_info * last_allocated = NULL;
+ block_info *last_allocated = NULL;
int i = 0;
BUG_ON(!ctx);
BUG_ON(!mem);
- allocator = (block_allocator*)ctx;
+ allocator = (block_allocator *)ctx;
left = mem->size_bytes;
BUG_ON(!left);
BUG_ON(!&allocator->mutex);
mem->nr_blocks = ((left + UMP_BLOCK_SIZE - 1) & ~(UMP_BLOCK_SIZE - 1)) / UMP_BLOCK_SIZE;
- mem->block_array = (ump_dd_physical_block*)vmalloc(sizeof(ump_dd_physical_block) * mem->nr_blocks);
+ mem->block_array = (ump_dd_physical_block *)vmalloc(sizeof(ump_dd_physical_block) * mem->nr_blocks);
if (NULL == mem->block_array) {
MSG_ERR(("Failed to allocate block array\n"));
return 0;
mem->size_bytes = 0;
while ((left > 0) && (allocator->first_free)) {
- block_info * block;
+ block_info *block;
block = allocator->first_free;
allocator->first_free = allocator->first_free->next;
}
if (left) {
- block_info * block;
+ block_info *block;
/* release all memory back to the pool */
while (last_allocated) {
block = last_allocated->next;
mem->backend_info = last_allocated;
up(&allocator->mutex);
- mem->is_cached=0;
+ mem->is_cached = 0;
return 1;
}
-static void block_allocator_release(void * ctx, ump_dd_mem * handle)
+static void block_allocator_release(void *ctx, ump_dd_mem *handle)
{
- block_allocator * allocator;
- block_info * block, * next;
+ block_allocator *allocator;
+ block_info *block, * next;
BUG_ON(!ctx);
BUG_ON(!handle);
- allocator = (block_allocator*)ctx;
- block = (block_info*)handle->backend_info;
+ allocator = (block_allocator *)ctx;
+ block = (block_info *)handle->backend_info;
BUG_ON(!block);
if (down_interruptible(&allocator->mutex)) {
while (block) {
next = block->next;
- BUG_ON( (block < allocator->all_blocks) || (block > (allocator->all_blocks + allocator->num_blocks)));
+ BUG_ON((block < allocator->all_blocks) || (block > (allocator->all_blocks + allocator->num_blocks)));
block->next = allocator->first_free;
allocator->first_free = block;
/*
* Helper function for calculating the physical base adderss of a memory block
*/
-static inline u32 get_phys(block_allocator * allocator, block_info * block)
+static inline u32 get_phys(block_allocator *allocator, block_info *block)
{
return allocator->base + ((block - allocator->all_blocks) * UMP_BLOCK_SIZE);
}
{
block_allocator *allocator;
BUG_ON(!backend);
- allocator = (block_allocator*)backend->ctx;
+ allocator = (block_allocator *)backend->ctx;
BUG_ON(!allocator);
- return (allocator->num_blocks - allocator->num_free)* UMP_BLOCK_SIZE;
+ return (allocator->num_blocks - allocator->num_free) * UMP_BLOCK_SIZE;
}
/*
- * Copyright (C) 2010 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_kernel_memory_backend.h"
-ump_memory_backend * ump_block_allocator_create(u32 base_address, u32 size);
+ump_memory_backend *ump_block_allocator_create(u32 base_address, u32 size);
#endif /* __UMP_KERNEL_MEMORY_BACKEND_DEDICATED_H__ */
/*
- * Copyright (C) 2010-2011, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
-static void os_free(void* ctx, ump_dd_mem * descriptor);
-static int os_allocate(void* ctx, ump_dd_mem * descriptor);
-static void os_memory_backend_destroy(ump_memory_backend * backend);
+static void os_free(void *ctx, ump_dd_mem *descriptor);
+static int os_allocate(void *ctx, ump_dd_mem *descriptor);
+static void os_memory_backend_destroy(ump_memory_backend *backend);
static u32 os_stat(struct ump_memory_backend *backend);
/*
* Create OS memory backend
*/
-ump_memory_backend * ump_os_memory_backend_create(const int max_allocation)
+ump_memory_backend *ump_os_memory_backend_create(const int max_allocation)
{
- ump_memory_backend * backend;
- os_allocator * info;
+ ump_memory_backend *backend;
+ os_allocator *info;
info = kmalloc(sizeof(os_allocator), GFP_KERNEL);
if (NULL == info) {
/*
* Destroy specified OS memory backend
*/
-static void os_memory_backend_destroy(ump_memory_backend * backend)
+static void os_memory_backend_destroy(ump_memory_backend *backend)
{
- os_allocator * info = (os_allocator*)backend->ctx;
+ os_allocator *info = (os_allocator *)backend->ctx;
DBG_MSG_IF(1, 0 != info->num_pages_allocated, ("%d pages still in use during shutdown\n", info->num_pages_allocated));
/*
* Allocate UMP memory
*/
-static int os_allocate(void* ctx, ump_dd_mem * descriptor)
+static int os_allocate(void *ctx, ump_dd_mem *descriptor)
{
u32 left;
- os_allocator * info;
+ os_allocator *info;
int pages_allocated = 0;
int is_cached;
BUG_ON(!descriptor);
BUG_ON(!ctx);
- info = (os_allocator*)ctx;
+ info = (os_allocator *)ctx;
left = descriptor->size_bytes;
is_cached = descriptor->is_cached;
}
while (left > 0 && ((info->num_pages_allocated + pages_allocated) < info->num_pages_max)) {
- struct page * new_page;
+ struct page *new_page;
if (is_cached) {
new_page = alloc_page(GFP_HIGHUSER | __GFP_ZERO | __GFP_REPEAT | __GFP_NOWARN);
}
/* Ensure page caches are flushed. */
- if ( is_cached ) {
+ if (is_cached) {
descriptor->block_array[pages_allocated].addr = page_to_phys(new_page);
descriptor->block_array[pages_allocated].size = PAGE_SIZE;
} else {
- descriptor->block_array[pages_allocated].addr = dma_map_page(NULL, new_page, 0, PAGE_SIZE, DMA_BIDIRECTIONAL );
+ descriptor->block_array[pages_allocated].addr = dma_map_page(NULL, new_page, 0, PAGE_SIZE, DMA_BIDIRECTIONAL);
descriptor->block_array[pages_allocated].size = PAGE_SIZE;
}
if (left) {
DBG_MSG(1, ("Failed to allocate needed pages\n"));
- while(pages_allocated) {
+ while (pages_allocated) {
pages_allocated--;
- if ( !is_cached ) {
+ if (!is_cached) {
dma_unmap_page(NULL, descriptor->block_array[pages_allocated].addr, PAGE_SIZE, DMA_BIDIRECTIONAL);
}
- __free_page(pfn_to_page(descriptor->block_array[pages_allocated].addr >> PAGE_SHIFT) );
+ __free_page(pfn_to_page(descriptor->block_array[pages_allocated].addr >> PAGE_SHIFT));
}
up(&info->mutex);
/*
* Free specified UMP memory
*/
-static void os_free(void* ctx, ump_dd_mem * descriptor)
+static void os_free(void *ctx, ump_dd_mem *descriptor)
{
- os_allocator * info;
+ os_allocator *info;
int i;
BUG_ON(!ctx);
BUG_ON(!descriptor);
- info = (os_allocator*)ctx;
+ info = (os_allocator *)ctx;
BUG_ON(descriptor->nr_blocks > info->num_pages_allocated);
up(&info->mutex);
- for ( i = 0; i < descriptor->nr_blocks; i++) {
+ for (i = 0; i < descriptor->nr_blocks; i++) {
DBG_MSG(6, ("Freeing physical page. Address: 0x%08lx\n", descriptor->block_array[i].addr));
- if ( ! descriptor->is_cached) {
+ if (! descriptor->is_cached) {
dma_unmap_page(NULL, descriptor->block_array[i].addr, PAGE_SIZE, DMA_BIDIRECTIONAL);
}
- __free_page(pfn_to_page(descriptor->block_array[i].addr>>PAGE_SHIFT) );
+ __free_page(pfn_to_page(descriptor->block_array[i].addr >> PAGE_SHIFT));
}
vfree(descriptor->block_array);
static u32 os_stat(struct ump_memory_backend *backend)
{
os_allocator *info;
- info = (os_allocator*)backend->ctx;
+ info = (os_allocator *)backend->ctx;
return info->num_pages_allocated * _MALI_OSK_MALI_PAGE_SIZE;
}
/*
- * Copyright (C) 2010 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_kernel_memory_backend.h"
-ump_memory_backend * ump_os_memory_backend_create(const int max_allocation);
+ump_memory_backend *ump_os_memory_backend_create(const int max_allocation);
#endif /* __UMP_KERNEL_MEMORY_BACKEND_OS_H__ */
--- /dev/null
+/*
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
+ *
+ * This program is free software and is provided to you under the terms of the GNU General Public License version 2
+ * as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
+ *
+ * A copy of the licence is included with the program, and can also be obtained from Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#include "mali_kernel_common.h"
+#include "mali_osk.h"
+#include "ump_osk.h"
+#include "ump_kernel_common.h"
+#include "ump_kernel_types.h"
+#include "ump_kernel_random_mapping.h"
+
+#include <linux/random.h>
+#include <linux/rbtree.h>
+#include <linux/sched.h>
+#include <linux/jiffies.h>
+
+
+static ump_dd_mem *search(struct rb_root *root, int id)
+{
+ struct rb_node *node = root->rb_node;
+
+ while (node) {
+ ump_dd_mem *e = container_of(node, ump_dd_mem, node);
+
+ if (id < e->secure_id) {
+ node = node->rb_left;
+ } else if (id > e->secure_id) {
+ node = node->rb_right;
+ } else {
+ return e;
+ }
+ }
+
+ return NULL;
+}
+
+static mali_bool insert(struct rb_root *root, int id, ump_dd_mem *mem)
+{
+ struct rb_node **new = &(root->rb_node);
+ struct rb_node *parent = NULL;
+
+ while (*new) {
+ ump_dd_mem *this = container_of(*new, ump_dd_mem, node);
+
+ parent = *new;
+ if (id < this->secure_id) {
+ new = &((*new)->rb_left);
+ } else if (id > this->secure_id) {
+ new = &((*new)->rb_right);
+ } else {
+ printk(KERN_ERR "UMP: ID already used %x\n", id);
+ return MALI_FALSE;
+ }
+ }
+
+ rb_link_node(&mem->node, parent, new);
+ rb_insert_color(&mem->node, root);
+
+ return MALI_TRUE;
+}
+
+
+ump_random_mapping *ump_random_mapping_create(void)
+{
+ ump_random_mapping *map = _mali_osk_calloc(1, sizeof(ump_random_mapping));
+
+ if (NULL == map)
+ return NULL;
+
+ map->lock = _mali_osk_mutex_rw_init(_MALI_OSK_LOCKFLAG_ORDERED,
+ _MALI_OSK_LOCK_ORDER_DESCRIPTOR_MAP);
+ if (NULL != map->lock) {
+ map->root = RB_ROOT;
+#if UMP_RANDOM_MAP_DELAY
+ map->failed.count = 0;
+ map->failed.timestamp = jiffies;
+#endif
+ return map;
+ }
+ return NULL;
+}
+
+void ump_random_mapping_destroy(ump_random_mapping *map)
+{
+ _mali_osk_mutex_rw_term(map->lock);
+ _mali_osk_free(map);
+}
+
+int ump_random_mapping_insert(ump_random_mapping *map, ump_dd_mem *mem)
+{
+ _mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RW);
+
+ while (1) {
+ u32 id;
+
+ get_random_bytes(&id, sizeof(id));
+
+ /* Try a new random number if id happened to be the invalid
+ * secure ID (-1). */
+ if (unlikely(id == UMP_INVALID_SECURE_ID))
+ continue;
+
+ /* Insert into the tree. If the id was already in use, get a
+ * new random id and try again. */
+ if (insert(&map->root, id, mem)) {
+ mem->secure_id = id;
+ break;
+ }
+ }
+ _mali_osk_mutex_rw_signal(map->lock, _MALI_OSK_LOCKMODE_RW);
+
+ return 0;
+}
+
+ump_dd_mem *ump_random_mapping_get(ump_random_mapping *map, int id)
+{
+ ump_dd_mem *mem = NULL;
+#if UMP_RANDOM_MAP_DELAY
+ int do_delay = 0;
+#endif
+
+ DEBUG_ASSERT(map);
+
+ _mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RO);
+ mem = search(&map->root, id);
+
+ if (unlikely(NULL == mem)) {
+#if UMP_RANDOM_MAP_DELAY
+ map->failed.count++;
+
+ if (time_is_before_jiffies(map->failed.timestamp +
+ UMP_FAILED_LOOKUP_DELAY * HZ)) {
+ /* If it is a long time since last failure, reset
+ * the counter and skip the delay this time. */
+ map->failed.count = 0;
+ } else if (map->failed.count > UMP_FAILED_LOOKUPS_ALLOWED) {
+ do_delay = 1;
+ }
+
+ map->failed.timestamp = jiffies;
+#endif /* UMP_RANDOM_MAP_DELAY */
+ } else {
+ ump_dd_reference_add(mem);
+ }
+ _mali_osk_mutex_rw_signal(map->lock, _MALI_OSK_LOCKMODE_RO);
+
+#if UMP_RANDOM_MAP_DELAY
+ if (do_delay) {
+ /* Apply delay */
+ schedule_timeout_killable(UMP_FAILED_LOOKUP_DELAY);
+ }
+#endif /* UMP_RANDOM_MAP_DELAY */
+
+ return mem;
+}
+
+static ump_dd_mem *ump_random_mapping_remove_internal(ump_random_mapping *map, int id)
+{
+ ump_dd_mem *mem = NULL;
+
+ mem = search(&map->root, id);
+
+ if (mem) {
+ rb_erase(&mem->node, &map->root);
+ }
+
+ return mem;
+}
+
+void ump_random_mapping_put(ump_dd_mem *mem)
+{
+ int new_ref;
+
+ _mali_osk_mutex_rw_wait(device.secure_id_map->lock, _MALI_OSK_LOCKMODE_RW);
+
+ new_ref = _ump_osk_atomic_dec_and_read(&mem->ref_count);
+ DBG_MSG(5, ("Memory reference decremented. ID: %u, new value: %d\n",
+ mem->secure_id, new_ref));
+
+ if (0 == new_ref) {
+ DBG_MSG(3, ("Final release of memory. ID: %u\n", mem->secure_id));
+
+ ump_random_mapping_remove_internal(device.secure_id_map, mem->secure_id);
+
+ mem->release_func(mem->ctx, mem);
+ _mali_osk_free(mem);
+ }
+
+ _mali_osk_mutex_rw_signal(device.secure_id_map->lock, _MALI_OSK_LOCKMODE_RW);
+}
+
+ump_dd_mem *ump_random_mapping_remove(ump_random_mapping *map, int descriptor)
+{
+ ump_dd_mem *mem;
+
+ _mali_osk_mutex_rw_wait(map->lock, _MALI_OSK_LOCKMODE_RW);
+ mem = ump_random_mapping_remove_internal(map, descriptor);
+ _mali_osk_mutex_rw_signal(map->lock, _MALI_OSK_LOCKMODE_RW);
+
+ return mem;
+}
--- /dev/null
+/*
+ * Copyright (C) 2010-2011, 2013-2014 ARM Limited. All rights reserved.
+ *
+ * This program is free software and is provided to you under the terms of the GNU General Public License version 2
+ * as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
+ *
+ * A copy of the licence is included with the program, and can also be obtained from Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+/**
+ * @file ump_kernel_random_mapping.h
+ */
+
+#ifndef __UMP_KERNEL_RANDOM_MAPPING_H__
+#define __UMP_KERNEL_RANDOM_MAPPING_H__
+
+#include "mali_osk.h"
+#include <linux/rbtree.h>
+
+#define UMP_RANDOM_MAP_DELAY 1
+#define UMP_FAILED_LOOKUP_DELAY 10 /* ms */
+#define UMP_FAILED_LOOKUPS_ALLOWED 10 /* number of allowed failed lookups */
+
+/**
+ * The random mapping object
+ * Provides a separate namespace where we can map an integer to a pointer
+ */
+typedef struct ump_random_mapping {
+ _mali_osk_mutex_rw_t *lock; /**< Lock protecting access to the mapping object */
+ struct rb_root root;
+#if UMP_RANDOM_MAP_DELAY
+ struct {
+ unsigned long count;
+ unsigned long timestamp;
+ } failed;
+#endif
+} ump_random_mapping;
+
+/**
+ * Create a random mapping object
+ * Create a random mapping capable of holding 2^20 entries
+ * @return Pointer to a random mapping object, NULL on failure
+ */
+ump_random_mapping *ump_random_mapping_create(void);
+
+/**
+ * Destroy a random mapping object
+ * @param map The map to free
+ */
+void ump_random_mapping_destroy(ump_random_mapping *map);
+
+/**
+ * Allocate a new mapping entry (random ID)
+ * Allocates a new entry in the map.
+ * @param map The map to allocate a new entry in
+ * @param target The value to map to
+ * @return The random allocated, a negative value on error
+ */
+int ump_random_mapping_insert(ump_random_mapping *map, ump_dd_mem *mem);
+
+/**
+ * Get the value mapped to by a random ID
+ *
+ * If the lookup fails, punish the calling thread by applying a delay.
+ *
+ * @param map The map to lookup the random id in
+ * @param id The ID to lookup
+ * @param target Pointer to a pointer which will receive the stored value
+ * @return ump_dd_mem pointer on successful lookup, NULL on error
+ */
+ump_dd_mem *ump_random_mapping_get(ump_random_mapping *map, int id);
+
+void ump_random_mapping_put(ump_dd_mem *mem);
+
+/**
+ * Free the random ID
+ * For the random to be reused it has to be freed
+ * @param map The map to free the random from
+ * @param id The ID to free
+ */
+ump_dd_mem *ump_random_mapping_remove(ump_random_mapping *map, int id);
+
+#endif /* __UMP_KERNEL_RANDOM_MAPPING_H__ */
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
module_param(ump_memory_size, uint, S_IRUGO); /* r--r--r-- */
MODULE_PARM_DESC(ump_memory_size, "The size of fixed memory to map in the dedicated memory backend");
-ump_memory_backend* ump_memory_backend_create ( void )
+ump_memory_backend *ump_memory_backend_create(void)
{
- ump_memory_backend * backend = NULL;
+ ump_memory_backend *backend = NULL;
/* Create the dynamic memory allocator backend */
if (0 == ump_backend) {
return backend;
}
-void ump_memory_backend_destroy( void )
+void ump_memory_backend_destroy(void)
{
if (0 == ump_backend) {
DBG_MSG(2, ("Releasing dedicated memory: 0x%08x\n", ump_memory_address));
/*
- * Copyright (C) 2010 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_osk.h"
#include <asm/atomic.h>
-int _ump_osk_atomic_dec_and_read( _mali_osk_atomic_t *atom )
+int _ump_osk_atomic_dec_and_read(_mali_osk_atomic_t *atom)
{
return atomic_dec_return((atomic_t *)&atom->u.val);
}
-int _ump_osk_atomic_inc_and_read( _mali_osk_atomic_t *atom )
+int _ump_osk_atomic_inc_and_read(_mali_osk_atomic_t *atom)
{
return atomic_inc_return((atomic_t *)&atom->u.val);
}
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include <linux/slab.h>
#include <asm/memory.h>
-#include <asm/uaccess.h> /* to verify pointers from user space */
+#include <asm/uaccess.h> /* to verify pointers from user space */
#include <asm/cacheflush.h>
#include <linux/dma-mapping.h>
ump_memory_allocation *descriptor;
} ump_vma_usage_tracker;
-static void ump_vma_open(struct vm_area_struct * vma);
-static void ump_vma_close(struct vm_area_struct * vma);
+static void ump_vma_open(struct vm_area_struct *vma);
+static void ump_vma_close(struct vm_area_struct *vma);
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26)
static int ump_cpu_page_fault_handler(struct vm_area_struct *vma, struct vm_fault *vmf);
#else
-static unsigned long ump_cpu_page_fault_handler(struct vm_area_struct * vma, unsigned long address);
+static unsigned long ump_cpu_page_fault_handler(struct vm_area_struct *vma, unsigned long address);
#endif
static struct vm_operations_struct ump_vm_ops = {
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26)
static int ump_cpu_page_fault_handler(struct vm_area_struct *vma, struct vm_fault *vmf)
#else
-static unsigned long ump_cpu_page_fault_handler(struct vm_area_struct * vma, unsigned long address)
+static unsigned long ump_cpu_page_fault_handler(struct vm_area_struct *vma, unsigned long address)
#endif
{
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26)
- void __user * address;
+ void __user *address;
address = vmf->virtual_address;
#endif
MSG_ERR(("Page-fault in UMP memory region caused by the CPU\n"));
#endif
}
-static void ump_vma_open(struct vm_area_struct * vma)
+static void ump_vma_open(struct vm_area_struct *vma)
{
- ump_vma_usage_tracker * vma_usage_tracker;
+ ump_vma_usage_tracker *vma_usage_tracker;
int new_val;
- vma_usage_tracker = (ump_vma_usage_tracker*)vma->vm_private_data;
+ vma_usage_tracker = (ump_vma_usage_tracker *)vma->vm_private_data;
BUG_ON(NULL == vma_usage_tracker);
new_val = atomic_inc_return(&vma_usage_tracker->references);
DBG_MSG(4, ("VMA open, VMA reference count incremented. VMA: 0x%08lx, reference count: %d\n", (unsigned long)vma, new_val));
}
-static void ump_vma_close(struct vm_area_struct * vma)
+static void ump_vma_close(struct vm_area_struct *vma)
{
- ump_vma_usage_tracker * vma_usage_tracker;
+ ump_vma_usage_tracker *vma_usage_tracker;
_ump_uk_unmap_mem_s args;
int new_val;
- vma_usage_tracker = (ump_vma_usage_tracker*)vma->vm_private_data;
+ vma_usage_tracker = (ump_vma_usage_tracker *)vma->vm_private_data;
BUG_ON(NULL == vma_usage_tracker);
new_val = atomic_dec_return(&vma_usage_tracker->references);
DBG_MSG(4, ("VMA close, VMA reference count decremented. VMA: 0x%08lx, reference count: %d\n", (unsigned long)vma, new_val));
if (0 == new_val) {
- ump_memory_allocation * descriptor;
+ ump_memory_allocation *descriptor;
descriptor = vma_usage_tracker->descriptor;
args._ukk_private = NULL; /** @note unused */
DBG_MSG(4, ("No more VMA references left, releasing UMP memory\n"));
- _ump_ukk_unmap_mem( & args );
+ _ump_ukk_unmap_mem(& args);
/* vma_usage_tracker is free()d by _ump_osk_mem_mapregion_term() */
}
}
-_mali_osk_errcode_t _ump_osk_mem_mapregion_init( ump_memory_allocation * descriptor )
+_mali_osk_errcode_t _ump_osk_mem_mapregion_init(ump_memory_allocation *descriptor)
{
- ump_vma_usage_tracker * vma_usage_tracker;
+ ump_vma_usage_tracker *vma_usage_tracker;
struct vm_area_struct *vma;
if (NULL == descriptor) return _MALI_OSK_ERR_FAULT;
return -_MALI_OSK_ERR_FAULT;
}
- vma = (struct vm_area_struct*)descriptor->process_mapping_info;
- if (NULL == vma ) {
+ vma = (struct vm_area_struct *)descriptor->process_mapping_info;
+ if (NULL == vma) {
kfree(vma_usage_tracker);
return _MALI_OSK_ERR_FAULT;
}
#endif
- if (0==descriptor->is_cached) {
+ if (0 == descriptor->is_cached) {
vma->vm_page_prot = pgprot_writecombine(vma->vm_page_prot);
}
- DBG_MSG(3, ("Mapping with page_prot: 0x%x\n", vma->vm_page_prot ));
+ DBG_MSG(3, ("Mapping with page_prot: 0x%x\n", vma->vm_page_prot));
/* Setup the functions which handle further VMA handling */
vma->vm_ops = &ump_vm_ops;
/* Do the va range allocation - in this case, it was done earlier, so we copy in that information */
- descriptor->mapping = (void __user*)vma->vm_start;
+ descriptor->mapping = (void __user *)vma->vm_start;
atomic_set(&vma_usage_tracker->references, 1); /*this can later be increased if process is forked, see ump_vma_open() */
vma_usage_tracker->descriptor = descriptor;
return _MALI_OSK_ERR_OK;
}
-void _ump_osk_mem_mapregion_term( ump_memory_allocation * descriptor )
+void _ump_osk_mem_mapregion_term(ump_memory_allocation *descriptor)
{
- struct vm_area_struct* vma;
- ump_vma_usage_tracker * vma_usage_tracker;
+ struct vm_area_struct *vma;
+ ump_vma_usage_tracker *vma_usage_tracker;
if (NULL == descriptor) return;
/* Linux does the right thing as part of munmap to remove the mapping
* All that remains is that we remove the vma_usage_tracker setup in init() */
- vma = (struct vm_area_struct*)descriptor->process_mapping_info;
+ vma = (struct vm_area_struct *)descriptor->process_mapping_info;
vma_usage_tracker = vma->vm_private_data;
return;
}
-_mali_osk_errcode_t _ump_osk_mem_mapregion_map( ump_memory_allocation * descriptor, u32 offset, u32 * phys_addr, unsigned long size )
+_mali_osk_errcode_t _ump_osk_mem_mapregion_map(ump_memory_allocation *descriptor, u32 offset, u32 *phys_addr, unsigned long size)
{
struct vm_area_struct *vma;
_mali_osk_errcode_t retval;
if (NULL == descriptor) return _MALI_OSK_ERR_FAULT;
- vma = (struct vm_area_struct*)descriptor->process_mapping_info;
+ vma = (struct vm_area_struct *)descriptor->process_mapping_info;
- if (NULL == vma ) return _MALI_OSK_ERR_FAULT;
+ if (NULL == vma) return _MALI_OSK_ERR_FAULT;
- retval = remap_pfn_range( vma, ((u32)descriptor->mapping) + offset, (*phys_addr) >> PAGE_SHIFT, size, vma->vm_page_prot) ? _MALI_OSK_ERR_FAULT : _MALI_OSK_ERR_OK;;
+ retval = remap_pfn_range(vma, ((u32)descriptor->mapping) + offset, (*phys_addr) >> PAGE_SHIFT, size, vma->vm_page_prot) ? _MALI_OSK_ERR_FAULT : _MALI_OSK_ERR_OK;;
DBG_MSG(4, ("Mapping virtual to physical memory. ID: %u, vma: 0x%08lx, virtual addr:0x%08lx, physical addr: 0x%08lx, size:%lu, prot:0x%x, vm_flags:0x%x RETVAL: 0x%x\n",
- ump_dd_secure_id_get(descriptor->handle),
- (unsigned long)vma,
- (unsigned long)(vma->vm_start + offset),
- (unsigned long)*phys_addr,
- size,
- (unsigned int)vma->vm_page_prot, vma->vm_flags, retval));
+ ump_dd_secure_id_get(descriptor->handle),
+ (unsigned long)vma,
+ (unsigned long)(vma->vm_start + offset),
+ (unsigned long)*phys_addr,
+ size,
+ (unsigned int)vma->vm_page_prot, vma->vm_flags, retval));
return retval;
}
__cpuc_flush_kern_all();
}
-void _ump_osk_msync( ump_dd_mem * mem, void * virt, u32 offset, u32 size, ump_uk_msync_op op, ump_session_data * session_data )
+void _ump_osk_msync(ump_dd_mem *mem, void *virt, u32 offset, u32 size, ump_uk_msync_op op, ump_session_data *session_data)
{
int i;
/* Flush L1 using virtual address, the entire range in one go.
* Only flush if user space process has a valid write mapping on given address. */
- if( (mem) && (virt!=NULL) && (access_ok(VERIFY_WRITE, virt, size)) ) {
+ if ((mem) && (virt != NULL) && (access_ok(VERIFY_WRITE, virt, size))) {
__cpuc_flush_dcache_area(virt, size);
DBG_MSG(3, ("UMP[%02u] Flushing CPU L1 Cache. CPU address: %x, size: %x\n", mem->secure_id, virt, size));
} else {
if (session_data) {
- if (op == _UMP_UK_MSYNC_FLUSH_L1 ) {
+ if (op == _UMP_UK_MSYNC_FLUSH_L1) {
DBG_MSG(4, ("UMP Pending L1 cache flushes: %d\n", session_data->has_pending_level1_cache_flush));
session_data->has_pending_level1_cache_flush = 0;
level1_cache_flush_all();
} else {
if (session_data->cache_operations_ongoing) {
session_data->has_pending_level1_cache_flush++;
- DBG_MSG(4, ("UMP[%02u] Defering the L1 flush. Nr pending:%d\n", mem->secure_id, session_data->has_pending_level1_cache_flush) );
+ DBG_MSG(4, ("UMP[%02u] Defering the L1 flush. Nr pending:%d\n", mem->secure_id, session_data->has_pending_level1_cache_flush));
} else {
/* Flushing the L1 cache for each switch_user() if ump_cache_operations_control(START) is not called */
level1_cache_flush_all();
}
}
- if ( NULL == mem ) return;
+ if (NULL == mem) return;
- if ( mem->size_bytes==size) {
- DBG_MSG(3, ("UMP[%02u] Flushing CPU L2 Cache\n",mem->secure_id));
+ if (mem->size_bytes == size) {
+ DBG_MSG(3, ("UMP[%02u] Flushing CPU L2 Cache\n", mem->secure_id));
} else {
DBG_MSG(3, ("UMP[%02u] Flushing CPU L2 Cache. Blocks:%u, TotalSize:%u. FlushSize:%u Offset:0x%x FirstPaddr:0x%08x\n",
- mem->secure_id, mem->nr_blocks, mem->size_bytes, size, offset, mem->block_array[0].addr));
+ mem->secure_id, mem->nr_blocks, mem->size_bytes, size, offset, mem->block_array[0].addr));
}
/* Flush L2 using physical addresses, block for block. */
- for (i=0 ; i < mem->nr_blocks; i++) {
+ for (i = 0 ; i < mem->nr_blocks; i++) {
u32 start_p, end_p;
ump_dd_physical_block *block;
block = &mem->block_array[i];
- if(offset >= block->size) {
+ if (offset >= block->size) {
offset -= block->size;
continue;
}
- if(offset) {
+ if (offset) {
start_p = (u32)block->addr + offset;
/* We'll zero the offset later, after using it to calculate end_p. */
} else {
start_p = (u32)block->addr;
}
- if(size < block->size - offset) {
+ if (size < block->size - offset) {
end_p = start_p + size - 1;
size = 0;
} else {
- if(offset) {
+ if (offset) {
end_p = start_p + (block->size - offset - 1);
size -= block->size - offset;
offset = 0;
}
}
- switch(op) {
+ switch (op) {
case _UMP_UK_MSYNC_CLEAN:
outer_clean_range(start_p, end_p);
break;
break;
}
- if(0 == size) {
+ if (0 == size) {
/* Nothing left to flush. */
break;
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#include "ump_kernel_linux.h"
/* is called from ump_kernel_constructor in common code */
-_mali_osk_errcode_t _ump_osk_init( void )
+_mali_osk_errcode_t _ump_osk_init(void)
{
if (0 != ump_kernel_device_initialize()) {
return _MALI_OSK_ERR_FAULT;
return _MALI_OSK_ERR_OK;
}
-_mali_osk_errcode_t _ump_osk_term( void )
+_mali_osk_errcode_t _ump_osk_term(void)
{
ump_kernel_device_terminate();
return _MALI_OSK_ERR_OK;
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
* IOCTL operation; Allocate UMP memory
*/
-int ump_allocate_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_allocate_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_allocate_s user_interaction;
_mali_osk_errcode_t err;
user_interaction.ctx = (void *) session_data;
- err = _ump_ukk_allocate( &user_interaction );
- if( _MALI_OSK_ERR_OK != err ) {
+ err = _ump_ukk_allocate(&user_interaction);
+ if (_MALI_OSK_ERR_OK != err) {
DBG_MSG(1, ("_ump_ukk_allocate() failed in ump_ioctl_allocate()\n"));
return map_errcode(err);
}
release_args.ctx = (void *) session_data;
release_args.secure_id = user_interaction.secure_id;
- err = _ump_ukk_release( &release_args );
- if(_MALI_OSK_ERR_OK != err) {
+ err = _ump_ukk_release(&release_args);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("_ump_ukk_release() also failed when trying to release newly allocated memory in ump_ioctl_allocate()\n"));
}
/*
- * Copyright (C) 2010, 2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2013-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
#endif
-int ump_allocate_wrapper(u32 __user * argument, struct ump_session_data * session_data);
+int ump_allocate_wrapper(u32 __user *argument, struct ump_session_data *session_data);
#ifdef __cplusplus
/*
- * Copyright (C) 2010-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
* IOCTL operation; Negotiate version of IOCTL API
*/
-int ump_get_api_version_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_get_api_version_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_api_version_s version_info;
_mali_osk_errcode_t err;
return -EFAULT;
}
- version_info.ctx = (void*) session_data;
- err = _ump_uku_get_api_version( &version_info );
- if( _MALI_OSK_ERR_OK != err ) {
+ version_info.ctx = (void *) session_data;
+ err = _ump_uku_get_api_version(&version_info);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("_ump_uku_get_api_version() failed in ump_ioctl_get_api_version()\n"));
return map_errcode(err);
}
/*
* IOCTL operation; Release reference to specified UMP memory.
*/
-int ump_release_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_release_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_release_s release_args;
_mali_osk_errcode_t err;
return -EFAULT;
}
- release_args.ctx = (void*) session_data;
- err = _ump_ukk_release( &release_args );
- if( _MALI_OSK_ERR_OK != err ) {
+ release_args.ctx = (void *) session_data;
+ err = _ump_ukk_release(&release_args);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("_ump_ukk_release() failed in ump_ioctl_release()\n"));
return map_errcode(err);
}
/*
* IOCTL operation; Return size for specified UMP memory.
*/
-int ump_size_get_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_size_get_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_size_get_s user_interaction;
_mali_osk_errcode_t err;
}
user_interaction.ctx = (void *) session_data;
- err = _ump_ukk_size_get( &user_interaction );
- if( _MALI_OSK_ERR_OK != err ) {
+ err = _ump_ukk_size_get(&user_interaction);
+ if (_MALI_OSK_ERR_OK != err) {
MSG_ERR(("_ump_ukk_size_get() failed in ump_ioctl_size_get()\n"));
return map_errcode(err);
}
/*
* IOCTL operation; Do cache maintenance on specified UMP memory.
*/
-int ump_msync_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_msync_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_msync_s user_interaction;
user_interaction.ctx = (void *) session_data;
- _ump_ukk_msync( &user_interaction );
+ _ump_ukk_msync(&user_interaction);
user_interaction.ctx = NULL;
return 0; /* success */
}
-int ump_cache_operations_control_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_cache_operations_control_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_cache_operations_control_s user_interaction;
user_interaction.ctx = (void *) session_data;
- _ump_ukk_cache_operations_control((_ump_uk_cache_operations_control_s*) &user_interaction );
+ _ump_ukk_cache_operations_control((_ump_uk_cache_operations_control_s *) &user_interaction);
user_interaction.ctx = NULL;
return 0; /* success */
}
-int ump_switch_hw_usage_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_switch_hw_usage_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_switch_hw_usage_s user_interaction;
user_interaction.ctx = (void *) session_data;
- _ump_ukk_switch_hw_usage( &user_interaction );
+ _ump_ukk_switch_hw_usage(&user_interaction);
user_interaction.ctx = NULL;
return 0; /* success */
}
-int ump_lock_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_lock_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_lock_s user_interaction;
user_interaction.ctx = (void *) session_data;
- _ump_ukk_lock( &user_interaction );
+ _ump_ukk_lock(&user_interaction);
user_interaction.ctx = NULL;
return 0; /* success */
}
-int ump_unlock_wrapper(u32 __user * argument, struct ump_session_data * session_data)
+int ump_unlock_wrapper(u32 __user *argument, struct ump_session_data *session_data)
{
_ump_uk_unlock_s user_interaction;
user_interaction.ctx = (void *) session_data;
- _ump_ukk_unlock( &user_interaction );
+ _ump_ukk_unlock(&user_interaction);
user_interaction.ctx = NULL;
/*
- * Copyright (C) 2010, 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2010, 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
-int ump_get_api_version_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_release_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_size_get_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_msync_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_cache_operations_control_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_switch_hw_usage_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_lock_wrapper(u32 __user * argument, struct ump_session_data * session_data);
-int ump_unlock_wrapper(u32 __user * argument, struct ump_session_data * session_data);
+int ump_get_api_version_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_release_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_size_get_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_msync_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_cache_operations_control_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_switch_hw_usage_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_lock_wrapper(u32 __user *argument, struct ump_session_data *session_data);
+int ump_unlock_wrapper(u32 __user *argument, struct ump_session_data *session_data);
#
-# Copyright (C) 2012 ARM Limited. All rights reserved.
+# Copyright (C) 2012, 2014 ARM Limited. All rights reserved.
#
# This program is free software and is provided to you under the terms of the GNU General Public License version 2
# as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.
typedef struct lock_cmd_priv {
uint32_t msg[128]; /*ioctl args*/
- u32 pid; /*process id*/
+ u32 pid; /*process id*/
} _lock_cmd_priv;
typedef struct lock_ref {
typedef struct umplock_item {
u32 secure_id;
- /*u32 references;*/
+ u32 id_ref_count;
+ u32 owner;
_lock_access_usage usage;
_lock_ref references[MAX_PIDS];
struct semaphore item_lock;
struct class *umplock_class;
};
-static char umplock_dev_name[] = "umplock";
-
-int umplock_major = 0;
-module_param(umplock_major, int, S_IRUGO); /* r--r--r-- */
-MODULE_PARM_DESC(umplock_major, "Device major number");
-
-static int umplock_driver_open( struct inode *inode, struct file *filp );
-static int umplock_driver_release( struct inode *inode, struct file *filp );
-static long umplock_driver_ioctl( struct file *f, unsigned int cmd, unsigned long arg );
-
-static struct file_operations umplock_fops = {
- .owner = THIS_MODULE,
- .open = umplock_driver_open,
- .release = umplock_driver_release,
- .unlocked_ioctl = umplock_driver_ioctl,
-};
-
static struct umplock_device umplock_device;
static umplock_device_private device;
+static dev_t umplock_dev;
+static char umplock_dev_name[] = "umplock";
-void umplock_init_locklist( void )
-{
- memset(&device.items, 0, sizeof(umplock_item)*MAX_ITEMS);
- atomic_set(&device.sessions, 0);
-}
-
-void umplock_deinit_locklist( void )
-{
- memset(&device.items, 0, sizeof(umplock_item)*MAX_ITEMS);
-}
-
-int umplock_device_initialize( void )
-{
- int err;
- dev_t dev = 0;
-
- if ( 0 == umplock_major ) {
- err = alloc_chrdev_region(&dev, 0, 1, umplock_dev_name);
- umplock_major = MAJOR(dev);
- } else {
- dev = MKDEV(umplock_major, 0);
- err = register_chrdev_region(dev, 1, umplock_dev_name);
- }
-
- if ( 0 == err ) {
- memset(&umplock_device, 0, sizeof(umplock_device));
- cdev_init(&umplock_device.cdev, &umplock_fops);
- umplock_device.cdev.owner = THIS_MODULE;
- umplock_device.cdev.ops = &umplock_fops;
-
- err = cdev_add(&umplock_device.cdev, dev, 1);
- if ( 0 == err ) {
- umplock_device.umplock_class = class_create(THIS_MODULE, umplock_dev_name);
- if ( IS_ERR(umplock_device.umplock_class ) ) {
- err = PTR_ERR(umplock_device.umplock_class);
- } else {
- struct device *mdev;
- mdev = device_create(umplock_device.umplock_class, NULL, dev, NULL, umplock_dev_name);
- if ( !IS_ERR(mdev) ) {
- return 0; /* all ok */
- }
-
- err = PTR_ERR(mdev);
- class_destroy(umplock_device.umplock_class);
- }
- cdev_del(&umplock_device.cdev);
- }
-
- unregister_chrdev_region(dev, 1);
- }
-
- return 1;
-}
-
-void umplock_device_terminate(void)
-{
- dev_t dev = MKDEV(umplock_major, 0);
-
- device_destroy(umplock_device.umplock_class, dev);
- class_destroy(umplock_device.umplock_class);
-
- cdev_del(&umplock_device.cdev);
- unregister_chrdev_region(dev, 1);
-}
-
-int umplock_constructor(void)
-{
- mutex_init(&device.item_list_lock);
- if ( !umplock_device_initialize() ) return 1;
- umplock_init_locklist();
-
- return 0;
-}
-
-void umplock_destructor(void)
-{
- umplock_deinit_locklist();
- umplock_device_terminate();
- mutex_destroy(&device.item_list_lock);
-}
-
-int umplock_find_item( u32 secure_id )
-{
- int i;
- for ( i=0; i<MAX_ITEMS; i++ ) {
- if ( device.items[i].secure_id == secure_id ) return i;
- }
+int umplock_debug_level = 0;
+module_param(umplock_debug_level, int, S_IRUSR | S_IWUSR | S_IWGRP | S_IRGRP | S_IROTH); /* rw-rw-r-- */
+MODULE_PARM_DESC(umplock_debug_level, "set umplock_debug_level to print debug messages");
- return -1;
-}
+#define PDEBUG(level, fmt, args...) do { if ((level) <= umplock_debug_level) printk(KERN_DEBUG "umplock: " fmt, ##args); } while (0)
+#define PERROR(fmt, args...) do { printk(KERN_ERR "umplock: " fmt, ##args); } while (0)
-int umplock_find_slot( void )
+int umplock_find_item(u32 secure_id)
{
int i;
- for ( i=0; i<MAX_ITEMS; i++ ) {
- if ( device.items[i].secure_id == 0 ) return i;
+ for (i = 0; i < MAX_ITEMS; i++) {
+ if (device.items[i].secure_id == secure_id) {
+ return i;
+ }
}
return -1;
}
-static int umplock_find_item_by_pid( _lock_cmd_priv *lock_cmd, int *item_slot, int *ref_slot)
+static int umplock_find_item_by_pid(_lock_cmd_priv *lock_cmd, int *item_slot, int *ref_slot)
{
_lock_item_s *lock_item;
- int i,j;
+ int i, j;
lock_item = (_lock_item_s *)&lock_cmd->msg;
i = umplock_find_item(lock_item->secure_id);
- if ( i < 0)
+ if (i < 0) {
return -1;
+ }
- for(j=0; j<MAX_PIDS; j++) {
- if(device.items[i].references[j].pid == lock_cmd->pid) {
+ for (j = 0; j < MAX_PIDS; j++) {
+ if (device.items[i].references[j].pid == lock_cmd->pid) {
*item_slot = i;
*ref_slot = j;
return 0;
{
int i;
- if(pid == 0)
+ if (pid == 0) {
return -1;
+ }
- for(i=0; i<MAX_PIDS; i++) {
- if(device.pids[i] == pid) return i;
+ for (i = 0; i < MAX_PIDS; i++) {
+ if (device.pids[i] == pid) {
+ return i;
+ }
}
return -1;
}
-static int do_umplock_create_locked( _lock_cmd_priv *lock_cmd)
+static int do_umplock_create_locked(_lock_cmd_priv *lock_cmd)
{
- int i_index,ref_index;
+ int i_index, ref_index;
int ret;
_lock_item_s *lock_item = (_lock_item_s *)&lock_cmd->msg;
i_index = ref_index = -1;
-#if 0
- if ( lock_item->usage == 1 ) printk( KERN_DEBUG "UMPLOCK: C 0x%x GPU SURFACE\n", lock_item->secure_id );
- else if ( lock_item->usage == 2 ) printk( KERN_DEBUG "UMPLOCK: C 0x%x GPU TEXTURE\n", lock_item->secure_id );
- else printk( KERN_DEBUG "UMPLOCK: C 0x%x CPU\n", lock_item->secure_id );
-#endif
-
- ret = umplock_find_client_valid( lock_cmd->pid );
- if( ret < 0 ) {
+ ret = umplock_find_client_valid(lock_cmd->pid);
+ if (ret < 0) {
/*lock request from an invalid client pid, do nothing*/
- return 0;
+ return -EINVAL;
}
- ret = umplock_find_item_by_pid( lock_cmd, &i_index, &ref_index );
- if ( ret >= 0 ) {
- if (device.items[i_index].references[ref_index].ref_count == 0)
- device.items[i_index].references[ref_index].ref_count = 1;
- } else if ( (i_index = umplock_find_item( lock_item->secure_id)) >= 0 ) {
- for ( ref_index = 0; ref_index < MAX_PIDS; ref_index++) {
- if (device.items[i_index].references[ref_index].pid == 0) break;
+ ret = umplock_find_item_by_pid(lock_cmd, &i_index, &ref_index);
+ if (ret >= 0) {
+ } else if ((i_index = umplock_find_item(lock_item->secure_id)) >= 0) {
+ for (ref_index = 0; ref_index < MAX_PIDS; ref_index++) {
+ if (device.items[i_index].references[ref_index].pid == 0) {
+ break;
+ }
}
- if ( ref_index < MAX_PIDS ) {
+ if (ref_index < MAX_PIDS) {
device.items[i_index].references[ref_index].pid = lock_cmd->pid;
- device.items[i_index].references[ref_index].ref_count = 1;
+ device.items[i_index].references[ref_index].ref_count = 0;
} else {
- printk( KERN_ERR "UMPLOCK: whoops, item ran out of available reference slot\n" );
+ PERROR("whoops, item ran out of available reference slots\n");
+ return -EINVAL;
+
}
} else {
- i_index = umplock_find_slot();
+ i_index = umplock_find_item(0);
- if ( i_index >= 0 ) {
+ if (i_index >= 0) {
device.items[i_index].secure_id = lock_item->secure_id;
+ device.items[i_index].id_ref_count = 0;
device.items[i_index].usage = lock_item->usage;
device.items[i_index].references[0].pid = lock_cmd->pid;
- device.items[i_index].references[0].ref_count = 1;
+ device.items[i_index].references[0].ref_count = 0;
sema_init(&device.items[i_index].item_lock, 1);
} else {
- printk( KERN_ERR "UMPLOCK: whoops, ran out of available slots\n" );
+ PERROR("whoops, ran out of available slots\n");
+ return -EINVAL;
}
}
static int do_umplock_create(_lock_cmd_priv *lock_cmd)
{
- int ret = 0;
- mutex_lock(&device.item_list_lock);
- ret = do_umplock_create_locked(lock_cmd);
- mutex_unlock(&device.item_list_lock);
- return ret;
+ return 0;
}
-static int do_umplock_process( _lock_cmd_priv *lock_cmd )
+static int do_umplock_process(_lock_cmd_priv *lock_cmd)
{
- int ret, i_index, ref_index, ref_count;
+ int ret, i_index, ref_index;
_lock_item_s *lock_item = (_lock_item_s *)&lock_cmd->msg;
mutex_lock(&device.item_list_lock);
- do_umplock_create_locked(lock_cmd);
+ if (0 == lock_item->secure_id) {
+ PERROR("IOCTL_UMPLOCK_PROCESS called with secure_id is 0, pid: %d\n", lock_cmd->pid);
+ mutex_unlock(&device.item_list_lock);
+ return -EINVAL;
+ }
- ret = umplock_find_client_valid( lock_cmd->pid );
- if( ret < 0 ) {
- /*lock request from an invalid client pid, do nothing*/
+ ret = do_umplock_create_locked(lock_cmd);
+ if (ret < 0) {
+ mutex_unlock(&device.item_list_lock);
+ return -EINVAL;
+ }
+
+ ret = umplock_find_item_by_pid(lock_cmd, &i_index, &ref_index);
+ if (ret < 0) {
+ /*fail to find a item*/
+ PERROR("IOCTL_UMPLOCK_PROCESS called with invalid parameter, pid: %d\n", lock_cmd->pid);
+ mutex_unlock(&device.item_list_lock);
+ return -EINVAL;
+ }
+ device.items[i_index].references[ref_index].ref_count++;
+ device.items[i_index].id_ref_count++;
+ PDEBUG(1, "try to lock, pid: %d, secure_id: 0x%x, ref_count: %d\n", lock_cmd->pid, lock_item->secure_id, device.items[i_index].references[ref_index].ref_count);
+
+ if (lock_cmd->pid == device.items[i_index].owner) {
+ PDEBUG(1, "already own the lock, pid: %d, secure_id: 0x%x, ref_count: %d\n", lock_cmd->pid, lock_item->secure_id, device.items[i_index].references[ref_index].ref_count);
mutex_unlock(&device.item_list_lock);
return 0;
}
- ret = umplock_find_item_by_pid( lock_cmd, &i_index, &ref_index );
- ref_count = device.items[i_index].references[ref_index].ref_count;
- if ( ret >= 0 ) {
- if (ref_count == 1) {
- /*add ref before down to wait for the umplock*/
- device.items[i_index].references[ref_index].ref_count++;
- mutex_unlock(&device.item_list_lock);
- if ( down_interruptible(&device.items[i_index].item_lock) ) {
- /*wait up without hold the umplock. restore previous state and return*/
- mutex_lock(&device.item_list_lock);
- device.items[i_index].references[ref_index].ref_count--;
- mutex_unlock(&device.item_list_lock);
- return -ERESTARTSYS;
+ mutex_unlock(&device.item_list_lock);
+ if (down_interruptible(&device.items[i_index].item_lock)) {
+ /*wait up without hold the umplock. restore previous state and return*/
+ mutex_lock(&device.item_list_lock);
+ device.items[i_index].references[ref_index].ref_count--;
+ device.items[i_index].id_ref_count--;
+ if (0 == device.items[i_index].references[ref_index].ref_count) {
+ device.items[i_index].references[ref_index].pid = 0;
+ if (0 == device.items[i_index].id_ref_count) {
+ PDEBUG(1, "release item, pid: %d, secure_id: 0x%x\n", lock_cmd->pid, lock_item->secure_id);
+ device.items[i_index].secure_id = 0;
}
- mutex_lock(&device.item_list_lock);
- } else {
- /*already got the umplock, add ref*/
- device.items[i_index].references[ref_index].ref_count++;
}
-#if 0
- if ( lock_item->usage == 1 ) printk( KERN_DEBUG "UMPLOCK: P 0x%x GPU SURFACE\n", lock_item->secure_id );
- else if ( lock_item->usage == 2 ) printk( KERN_DEBUG "UMPLOCK: P 0x%x GPU TEXTURE\n", lock_item->secure_id );
- else printk( KERN_DEBUG "UMPLOCK: P 0x%x CPU\n", lock_item->secure_id );
-#endif
- } else {
- /*fail to find a item*/
- printk(KERN_ERR "UMPLOCK: IOCTL_UMPLOCK_PROCESS called with invalid parameter\n");
+
+ PERROR("failed lock, pid: %d, secure_id: 0x%x, ref_count: %d\n", lock_cmd->pid, lock_item->secure_id, device.items[i_index].references[ref_index].ref_count);
+
mutex_unlock(&device.item_list_lock);
- return -EINVAL;
+ return -ERESTARTSYS;
}
+
+ mutex_lock(&device.item_list_lock);
+ PDEBUG(1, "got lock, pid: %d, secure_id: 0x%x, ref_count: %d\n", lock_cmd->pid, lock_item->secure_id, device.items[i_index].references[ref_index].ref_count);
+ device.items[i_index].owner = lock_cmd->pid;
mutex_unlock(&device.item_list_lock);
+
return 0;
}
-static int do_umplock_release( _lock_cmd_priv *lock_cmd )
+static int do_umplock_release(_lock_cmd_priv *lock_cmd)
{
- int i_index,ref_index, ref_count;
- int ret;
+ int ret, i_index, ref_index;
_lock_item_s *lock_item = (_lock_item_s *)&lock_cmd->msg;
mutex_lock(&device.item_list_lock);
- ret = umplock_find_client_valid( lock_cmd->pid );
- if( ret < 0 ) {
+
+ if (0 == lock_item->secure_id) {
+ PERROR("IOCTL_UMPLOCK_RELEASE called with secure_id is 0, pid: %d\n", lock_cmd->pid);
+ mutex_unlock(&device.item_list_lock);
+ return -EINVAL;
+ }
+
+ ret = umplock_find_client_valid(lock_cmd->pid);
+ if (ret < 0) {
/*lock request from an invalid client pid, do nothing*/
mutex_unlock(&device.item_list_lock);
- return 0;
+ return -EPERM;
}
i_index = ref_index = -1;
- ret = umplock_find_item_by_pid( lock_cmd, &i_index, &ref_index );
-
- if ( ret >= 0 ) {
- device.items[i_index].references[ref_index].ref_count--;
- ref_count = device.items[i_index].references[ref_index].ref_count;
-
-#if 0
- if ( lock_item->usage == 1 ) printk( KERN_DEBUG "UMPLOCK: R 0x%x GPU SURFACE\n", lock_item->secure_id );
- else if ( lock_item->usage == 2 ) printk( KERN_DEBUG "UMPLOCK: R 0x%x GPU TEXTURE\n", lock_item->secure_id );
- else printk( KERN_DEBUG "UMPLOCK: R 0x%x CPU\n", lock_item->secure_id );
-#endif
- /*reached the last reference to the umplock*/
- if ( ref_count == 1 ) {
- /*release the umplock*/
- up( &device.items[i_index].item_lock );
-
- device.items[i_index].references[ref_index].ref_count = 0;
- device.items[i_index].references[ref_index].pid = 0;
- }
- } else {
+ ret = umplock_find_item_by_pid(lock_cmd, &i_index, &ref_index);
+ if (ret < 0) {
/*fail to find item*/
- printk(KERN_ERR "UMPLOCK: IOCTL_UMPLOCK_RELEASE called with invalid parameter\n");
+ PERROR("IOCTL_UMPLOCK_RELEASE called with invalid parameter pid: %d, secid: 0x%x\n", lock_cmd->pid, lock_item->secure_id);
mutex_unlock(&device.item_list_lock);
return -EINVAL;
}
+
+ /* if the lock is not owned by this process */
+ if (lock_cmd->pid != device.items[i_index].owner) {
+ mutex_unlock(&device.item_list_lock);
+ return -EPERM;
+ }
+
+ /* if the ref_count is 0, that means nothing to unlock, just return */
+ if (0 == device.items[i_index].references[ref_index].ref_count) {
+ mutex_unlock(&device.item_list_lock);
+ return 0;
+ }
+
+ device.items[i_index].references[ref_index].ref_count--;
+ device.items[i_index].id_ref_count--;
+ PDEBUG(1, "unlock, pid: %d, secure_id: 0x%x, ref_count: %d\n", lock_cmd->pid, lock_item->secure_id, device.items[i_index].references[ref_index].ref_count);
+
+ if (0 == device.items[i_index].references[ref_index].ref_count) {
+ device.items[i_index].references[ref_index].pid = 0;
+ if (0 == device.items[i_index].id_ref_count) {
+ PDEBUG(1, "release item, pid: %d, secure_id: 0x%x\n", lock_cmd->pid, lock_item->secure_id);
+ device.items[i_index].secure_id = 0;
+ }
+ device.items[i_index].owner = 0;
+ up(&device.items[i_index].item_lock);
+ }
mutex_unlock(&device.item_list_lock);
+
return 0;
}
-static int do_umplock_zap( void )
+static int do_umplock_zap(void)
{
int i;
- printk( KERN_DEBUG "UMPLOCK: ZAP ALL ENTRIES!\n" );
+ PDEBUG(1, "ZAP ALL ENTRIES!\n");
mutex_lock(&device.item_list_lock);
- for ( i=0; i<MAX_ITEMS; i++ ) {
+ for (i = 0; i < MAX_ITEMS; i++) {
device.items[i].secure_id = 0;
- memset(&device.items[i].references, 0, sizeof(_lock_ref)*MAX_PIDS);
+ memset(&device.items[i].references, 0, sizeof(_lock_ref) * MAX_PIDS);
sema_init(&device.items[i].item_lock, 1);
}
- mutex_unlock(&device.item_list_lock);
- for ( i=0; i<MAX_PIDS; i++) {
+ for (i = 0; i < MAX_PIDS; i++) {
device.pids[i] = 0;
}
+ mutex_unlock(&device.item_list_lock);
+
return 0;
}
-static int do_umplock_dump( void )
+static int do_umplock_dump(void)
{
int i, j;
- printk("dump all the items\n");
-
mutex_lock(&device.item_list_lock);
+ PERROR("dump all the items begin\n");
for (i = 0; i < MAX_ITEMS; i++) {
for (j = 0; j < MAX_PIDS; j++) {
if (device.items[i].secure_id != 0 && device.items[i].references[j].pid != 0) {
- printk("item[%d]->secure_id=%d\t reference[%d].ref_count=%d.pid=%d\n",
+ PERROR("item[%d]->secure_id=0x%x, owner=%d\t reference[%d].ref_count=%d.pid=%d\n",
i,
device.items[i].secure_id,
+ device.items[i].owner,
j,
device.items[i].references[j].ref_count,
device.items[i].references[j].pid);
}
}
}
+ PERROR("dump all the items end\n");
mutex_unlock(&device.item_list_lock);
return 0;
}
-int do_umplock_client_add (_lock_cmd_priv *lock_cmd )
+int do_umplock_client_add(_lock_cmd_priv *lock_cmd)
{
int i;
mutex_lock(&device.item_list_lock);
- for ( i= 0; i<MAX_PIDS; i++) {
- if(device.pids[i] == lock_cmd->pid) {
+ for (i = 0; i < MAX_PIDS; i++) {
+ if (device.pids[i] == lock_cmd->pid) {
+ mutex_unlock(&device.item_list_lock);
return 0;
}
}
- for ( i=0; i<MAX_PIDS; i++) {
- if(device.pids[i]==0) {
+ for (i = 0; i < MAX_PIDS; i++) {
+ if (device.pids[i] == 0) {
device.pids[i] = lock_cmd->pid;
break;
}
}
mutex_unlock(&device.item_list_lock);
- if( i==MAX_PIDS) {
- printk(KERN_ERR "Oops, Run out of cient slots\n ");
+ if (i == MAX_PIDS) {
+ PERROR("Oops, Run out of client slots\n ");
+ return -EINVAL;
}
return 0;
}
-int do_umplock_client_delete (_lock_cmd_priv *lock_cmd )
+int do_umplock_client_delete(_lock_cmd_priv *lock_cmd)
{
- int p_index=-1, i_index=-1,ref_index=-1;
+ int p_index = -1, i_index = -1, ref_index = -1;
int ret;
_lock_item_s *lock_item;
lock_item = (_lock_item_s *)&lock_cmd->msg;
mutex_lock(&device.item_list_lock);
- p_index = umplock_find_client_valid( lock_cmd->pid );
+ p_index = umplock_find_client_valid(lock_cmd->pid);
/*lock item pid is not valid.*/
- if ( p_index<0 ) {
+ if (p_index < 0) {
mutex_unlock(&device.item_list_lock);
return 0;
}
/*walk through umplock item list and release reference attached to this client*/
- for(i_index = 0; i_index< MAX_ITEMS; i_index++ ) {
+ for (i_index = 0; i_index < MAX_ITEMS; i_index++) {
lock_item->secure_id = device.items[i_index].secure_id;
+
/*find the item index and reference slot for the lock_item*/
ret = umplock_find_item_by_pid(lock_cmd, &i_index, &ref_index);
- if(ret < 0) {
+ if (ret < 0) {
/*client has no reference on this umplock item, skip*/
continue;
}
- while(device.items[i_index].references[ref_index].ref_count) {
+ while (device.items[i_index].references[ref_index].ref_count) {
/*release references on this client*/
+
+ PDEBUG(1, "delete client, pid: %d, ref_count: %d\n", lock_cmd->pid, device.items[i_index].references[ref_index].ref_count);
+
mutex_unlock(&device.item_list_lock);
do_umplock_release(lock_cmd);
mutex_lock(&device.item_list_lock);
return 0;
}
-static long umplock_driver_ioctl( struct file *f, unsigned int cmd, unsigned long arg )
+static long umplock_driver_ioctl(struct file *f, unsigned int cmd, unsigned long arg)
{
int ret;
uint32_t size = _IOC_SIZE(cmd);
_lock_cmd_priv lock_cmd ;
- if (_IOC_TYPE(cmd) != LOCK_IOCTL_GROUP ) {
+ if (_IOC_TYPE(cmd) != LOCK_IOCTL_GROUP) {
return -ENOTTY;
}
- if (_IOC_NR(cmd) >= LOCK_IOCTL_MAX_CMDS ) {
+ if (_IOC_NR(cmd) >= LOCK_IOCTL_MAX_CMDS) {
return -ENOTTY;
}
- switch ( cmd ) {
+ switch (cmd) {
case LOCK_IOCTL_CREATE:
if (size != sizeof(_lock_item_s)) {
return -ENOTTY;
return -EFAULT;
}
lock_cmd.pid = (u32)current->tgid;
- ret = do_umplock_release( &lock_cmd );
+ ret = do_umplock_release(&lock_cmd);
if (ret) {
return ret;
}
return -ENOIOCTLCMD;
}
-static int umplock_driver_open( struct inode *inode, struct file *filp )
+static int umplock_driver_open(struct inode *inode, struct file *filp)
{
_lock_cmd_priv lock_cmd;
atomic_inc(&device.sessions);
- printk( KERN_DEBUG "UMPLOCK: OPEN SESSION (%i references)\n", atomic_read(&device.sessions) );
+ PDEBUG(1, "OPEN SESSION (%i references)\n", atomic_read(&device.sessions));
lock_cmd.pid = (u32)current->tgid;
do_umplock_client_add(&lock_cmd);
return 0;
}
-static int umplock_driver_release( struct inode *inode, struct file *filp )
+static int umplock_driver_release(struct inode *inode, struct file *filp)
{
+ int sessions = 0;
_lock_cmd_priv lock_cmd;
lock_cmd.pid = (u32)current->tgid;
do_umplock_client_delete(&lock_cmd);
+ mutex_lock(&device.item_list_lock);
atomic_dec(&device.sessions);
- printk( KERN_DEBUG "UMPLOCK: CLOSE SESSION (%i references)\n", atomic_read(&device.sessions) );
- if ( atomic_read(&device.sessions) == 0 ) {
+ sessions = atomic_read(&device.sessions);
+ PDEBUG(1, "CLOSE SESSION (%i references)\n", sessions);
+ mutex_unlock(&device.item_list_lock);
+ if (sessions == 0) {
do_umplock_zap();
}
return 0;
}
-static int __init umplock_initialize_module( void )
+static struct file_operations umplock_fops = {
+ .owner = THIS_MODULE,
+ .open = umplock_driver_open,
+ .release = umplock_driver_release,
+ .unlocked_ioctl = umplock_driver_ioctl,
+};
+
+int umplock_device_initialize(void)
+{
+ int err;
+
+ err = alloc_chrdev_region(&umplock_dev, 0, 1, umplock_dev_name);
+
+ if (0 == err) {
+ memset(&umplock_device, 0, sizeof(umplock_device));
+ cdev_init(&umplock_device.cdev, &umplock_fops);
+ umplock_device.cdev.owner = THIS_MODULE;
+ umplock_device.cdev.ops = &umplock_fops;
+
+ err = cdev_add(&umplock_device.cdev, umplock_dev, 1);
+ if (0 == err) {
+ umplock_device.umplock_class = class_create(THIS_MODULE, umplock_dev_name);
+ if (IS_ERR(umplock_device.umplock_class)) {
+ err = PTR_ERR(umplock_device.umplock_class);
+ } else {
+ struct device *mdev;
+ mdev = device_create(umplock_device.umplock_class, NULL, umplock_dev, NULL, umplock_dev_name);
+ if (!IS_ERR(mdev)) {
+ return 0; /* all ok */
+ }
+
+ err = PTR_ERR(mdev);
+ class_destroy(umplock_device.umplock_class);
+ }
+ cdev_del(&umplock_device.cdev);
+ }
+
+ unregister_chrdev_region(umplock_dev, 1);
+ } else {
+ PERROR("alloc chardev region failed\n");
+ }
+
+ return err;
+}
+
+void umplock_device_terminate(void)
{
- printk( KERN_DEBUG "Inserting UMP lock device driver. Compiled: %s, time: %s\n", __DATE__, __TIME__ );
+ device_destroy(umplock_device.umplock_class, umplock_dev);
+ class_destroy(umplock_device.umplock_class);
+
+ cdev_del(&umplock_device.cdev);
+ unregister_chrdev_region(umplock_dev, 1);
+}
+
+static int __init umplock_initialize_module(void)
+{
+ PDEBUG(1, "Inserting UMP lock device driver. Compiled: %s, time: %s\n", __DATE__, __TIME__);
- if ( !umplock_constructor() ) {
- printk( KERN_ERR "UMP lock device driver init failed\n");
+ mutex_init(&device.item_list_lock);
+ if (umplock_device_initialize() != 0) {
+ PERROR("UMP lock device driver init failed\n");
return -ENOTTY;
}
+ memset(&device.items, 0, sizeof(umplock_item) * MAX_ITEMS);
+ memset(&device.pids, 0, sizeof(u32) * MAX_PIDS);
+ atomic_set(&device.sessions, 0);
- printk( KERN_DEBUG "UMP lock device driver loaded\n" );
+ PDEBUG(1, "UMP lock device driver loaded\n");
return 0;
}
-static void __exit umplock_cleanup_module( void )
+static void __exit umplock_cleanup_module(void)
{
- printk( KERN_DEBUG "unloading UMP lock module\n" );
- umplock_destructor();
- printk( KERN_DEBUG "UMP lock module unloaded\n" );
+ PDEBUG(1, "unloading UMP lock module\n");
+
+ memset(&device.items, 0, sizeof(umplock_item) * MAX_ITEMS);
+ memset(&device.pids, 0, sizeof(u32) * MAX_PIDS);
+ umplock_device_terminate();
+ mutex_destroy(&device.item_list_lock);
+
+ PDEBUG(1, "UMP lock module unloaded\n");
}
module_init(umplock_initialize_module);
/*
- * Copyright (C) 2012-2013 ARM Limited. All rights reserved.
+ * Copyright (C) 2012-2014 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation, and any use by you of this program is subject to the terms of such GNU licence.