// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * Copyright 2009-2010 Freescale Semiconductor, Inc.
 *
 * Simple memory allocator abstraction for QorIQ (P1/P2) based Cache-SRAM
 *
 * Author: Vivek Mahajan <vivek.mahajan@freescale.com>
 *
 * This file is derived from the original work done
 * by Sylvain Munaut for the Bestcomm SRAM allocator.
 */

#include <linux/kernel.h>
#include <linux/export.h>
#include <linux/slab.h>
#include <linux/err.h>
#include <linux/of_platform.h>
#include <linux/pgtable.h>
#include <asm/fsl_85xx_cache_sram.h>

#include "fsl_85xx_cache_ctlr.h"

struct mpc85xx_cache_sram *cache_sram;

void *mpc85xx_cache_sram_alloc(unsigned int size,
				phys_addr_t *phys, unsigned int align)
{
	unsigned long offset;
	unsigned long flags;

	if (unlikely(cache_sram == NULL))
		return NULL;

	if (!size || (size > cache_sram->size) || (align > cache_sram->size)) {
		pr_err("%s(): size(=%x) or align(=%x) zero or too big\n",
			__func__, size, align);
		return NULL;
	}

	if ((align & (align - 1)) || align <= 1) {
		pr_err("%s(): align(=%x) must be power of two and >1\n",
			__func__, align);
		return NULL;
	}

	spin_lock_irqsave(&cache_sram->lock, flags);
	offset = rh_alloc_align(cache_sram->rh, size, align, NULL);
	spin_unlock_irqrestore(&cache_sram->lock, flags);

	if (IS_ERR_VALUE(offset))
		return NULL;

	*phys = cache_sram->base_phys + offset;

	return (unsigned char *)cache_sram->base_virt + offset;
}
EXPORT_SYMBOL(mpc85xx_cache_sram_alloc);

void mpc85xx_cache_sram_free(void *ptr)
{
	unsigned long flags;
	BUG_ON(!ptr);

	spin_lock_irqsave(&cache_sram->lock, flags);
	rh_free(cache_sram->rh, ptr - cache_sram->base_virt);
	spin_unlock_irqrestore(&cache_sram->lock, flags);
}
EXPORT_SYMBOL(mpc85xx_cache_sram_free);

int __init instantiate_cache_sram(struct platform_device *dev,
		struct sram_parameters sram_params)
{
	int ret = 0;

	if (cache_sram) {
		dev_err(&dev->dev, "Already initialized cache-sram\n");
		return -EBUSY;
	}

	cache_sram = kzalloc(sizeof(struct mpc85xx_cache_sram), GFP_KERNEL);
	if (!cache_sram) {
		dev_err(&dev->dev, "Out of memory for cache_sram structure\n");
		return -ENOMEM;
	}

	cache_sram->base_phys = sram_params.sram_offset;
	cache_sram->size = sram_params.sram_size;

	if (!request_mem_region(cache_sram->base_phys, cache_sram->size,
						"fsl_85xx_cache_sram")) {
		dev_err(&dev->dev, "%pOF: request memory failed\n",
				dev->dev.of_node);
		ret = -ENXIO;
		goto out_free;
	}

	cache_sram->base_virt = ioremap_coherent(cache_sram->base_phys,
						 cache_sram->size);
	if (!cache_sram->base_virt) {
		dev_err(&dev->dev, "%pOF: ioremap_coherent failed\n",
			dev->dev.of_node);
		ret = -ENOMEM;
		goto out_release;
	}

	cache_sram->rh = rh_create(sizeof(unsigned int));
	if (IS_ERR(cache_sram->rh)) {
		dev_err(&dev->dev, "%pOF: Unable to create remote heap\n",
				dev->dev.of_node);
		ret = PTR_ERR(cache_sram->rh);
		goto out_unmap;
	}

	rh_attach_region(cache_sram->rh, 0, cache_sram->size);
	spin_lock_init(&cache_sram->lock);

	dev_info(&dev->dev, "[base:0x%llx, size:0x%x] configured and loaded\n",
		(unsigned long long)cache_sram->base_phys, cache_sram->size);

	return 0;

out_unmap:
	iounmap(cache_sram->base_virt);

out_release:
	release_mem_region(cache_sram->base_phys, cache_sram->size);

out_free:
	kfree(cache_sram);
	return ret;
}

void remove_cache_sram(struct platform_device *dev)
{
	BUG_ON(!cache_sram);

	rh_detach_region(cache_sram->rh, 0, cache_sram->size);
	rh_destroy(cache_sram->rh);

	iounmap(cache_sram->base_virt);
	release_mem_region(cache_sram->base_phys, cache_sram->size);

	kfree(cache_sram);
	cache_sram = NULL;

	dev_info(&dev->dev, "MPC85xx Cache-SRAM driver unloaded\n");
}
