// SPDX-License-Identifier: GPL-2.0
|
/*
|
* Support for Intel Camera Imaging ISP subsystem.
|
* Copyright (c) 2015, Intel Corporation.
|
*
|
* This program is free software; you can redistribute it and/or modify it
|
* under the terms and conditions of the GNU General Public License,
|
* version 2, as published by the Free Software Foundation.
|
*
|
* This program is distributed in the hope it will be useful, but WITHOUT
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
* more details.
|
*/
|
|
#include "system_global.h"
|
|
#include "assert_support.h"
|
#include "platform_support.h"
|
#include "ia_css_isys.h"
|
#include "ibuf_ctrl_rmgr.h"
|
|
static ibuf_rsrc_t ibuf_rsrc;
|
|
static ibuf_handle_t *getHandle(uint16_t index)
|
{
|
ibuf_handle_t *handle = NULL;
|
|
if (index < MAX_IBUF_HANDLES)
|
handle = &ibuf_rsrc.handles[index];
|
return handle;
|
}
|
|
void ia_css_isys_ibuf_rmgr_init(void)
|
{
|
memset(&ibuf_rsrc, 0, sizeof(ibuf_rsrc));
|
ibuf_rsrc.free_size = MAX_INPUT_BUFFER_SIZE;
|
}
|
|
void ia_css_isys_ibuf_rmgr_uninit(void)
|
{
|
memset(&ibuf_rsrc, 0, sizeof(ibuf_rsrc));
|
ibuf_rsrc.free_size = MAX_INPUT_BUFFER_SIZE;
|
}
|
|
bool ia_css_isys_ibuf_rmgr_acquire(
|
u32 size,
|
uint32_t *start_addr)
|
{
|
bool retval = false;
|
bool input_buffer_found = false;
|
u32 aligned_size;
|
ibuf_handle_t *handle = NULL;
|
u16 i;
|
|
assert(start_addr);
|
assert(size > 0);
|
|
aligned_size = (size + (IBUF_ALIGN - 1)) & ~(IBUF_ALIGN - 1);
|
|
/* Check if there is an available un-used handle with the size
|
* that will fulfill the request.
|
*/
|
if (ibuf_rsrc.num_active < ibuf_rsrc.num_allocated) {
|
for (i = 0; i < ibuf_rsrc.num_allocated; i++) {
|
handle = getHandle(i);
|
if (!handle->active) {
|
if (handle->size >= aligned_size) {
|
handle->active = true;
|
input_buffer_found = true;
|
ibuf_rsrc.num_active++;
|
break;
|
}
|
}
|
}
|
}
|
|
if (!input_buffer_found) {
|
/* There were no available handles that fulfilled the
|
* request. Allocate a new handle with the requested size.
|
*/
|
if ((ibuf_rsrc.num_allocated < MAX_IBUF_HANDLES) &&
|
(ibuf_rsrc.free_size >= aligned_size)) {
|
handle = getHandle(ibuf_rsrc.num_allocated);
|
handle->start_addr = ibuf_rsrc.free_start_addr;
|
handle->size = aligned_size;
|
handle->active = true;
|
|
ibuf_rsrc.free_start_addr += aligned_size;
|
ibuf_rsrc.free_size -= aligned_size;
|
ibuf_rsrc.num_active++;
|
ibuf_rsrc.num_allocated++;
|
|
input_buffer_found = true;
|
}
|
}
|
|
if (input_buffer_found && handle) {
|
*start_addr = handle->start_addr;
|
retval = true;
|
}
|
|
return retval;
|
}
|
|
void ia_css_isys_ibuf_rmgr_release(
|
uint32_t *start_addr)
|
{
|
u16 i;
|
ibuf_handle_t *handle = NULL;
|
|
assert(start_addr);
|
|
for (i = 0; i < ibuf_rsrc.num_allocated; i++) {
|
handle = getHandle(i);
|
if (handle->active && handle->start_addr == *start_addr) {
|
handle->active = false;
|
ibuf_rsrc.num_active--;
|
break;
|
}
|
}
|
}
|