#include <linux/spinlock.h>
#include <linux/list.h>
#include <linux/slab.h>

#include "vmregion.h"

/*
 * VM region handling support.
 *
 * This should become something generic, handling VM region allocations for
 * vmalloc and similar (ioremap, module space, etc).
 *
 * I envisage vmalloc()'s supporting vm_struct becoming:
 *
 *  struct vm_struct {
 *    struct vmregion	region;
 *    unsigned long	flags;
 *    struct page	**pages;
 *    unsigned int	nr_pages;
 *    unsigned long	phys_addr;
 *  };
 *
 * get_vm_area() would then call vmregion_alloc with an appropriate
 * struct vmregion head (eg):
 *
 *  struct vmregion vmalloc_head = {
 *	.vm_list	= LIST_HEAD_INIT(vmalloc_head.vm_list),
 *	.vm_start	= VMALLOC_START,
 *	.vm_end		= VMALLOC_END,
 *  };
 *
 * However, vmalloc_head.vm_start is variable (typically, it is dependent on
 * the amount of RAM found at boot time.)  I would imagine that get_vm_area()
 * would have to initialise this each time prior to calling vmregion_alloc().
 */

struct arm_vmregion *
arm_vmregion_alloc(struct arm_vmregion_head *head, size_t align,
		   size_t size, gfp_t gfp)
{
	unsigned long addr = head->vm_start, end = head->vm_end - size;
	unsigned long flags;
	struct arm_vmregion *c, *new;

	if (head->vm_end - head->vm_start < size) {
		printk(KERN_WARNING "%s: allocation too big (requested %#x)\n",
			__func__, size);
		goto out;
	}

	new = kmalloc(sizeof(struct arm_vmregion), gfp);
	if (!new)
		goto out;

	spin_lock_irqsave(&head->vm_lock, flags);

	list_for_each_entry(c, &head->vm_list, vm_list) {
		if ((addr + size) < addr)
			goto nospc;
		if ((addr + size) <= c->vm_start)
			goto found;
		addr = ALIGN(c->vm_end, align);
		if (addr > end)
			goto nospc;
	}

 found:
	/*
	 * Insert this entry _before_ the one we found.
	 */
	list_add_tail(&new->vm_list, &c->vm_list);
	new->vm_start = addr;
	new->vm_end = addr + size;
	new->vm_active = 1;

	spin_unlock_irqrestore(&head->vm_lock, flags);
	return new;

 nospc:
	spin_unlock_irqrestore(&head->vm_lock, flags);
	kfree(new);
 out:
	return NULL;
}

static struct arm_vmregion *__arm_vmregion_find(struct arm_vmregion_head *head, unsigned long addr)
{
	struct arm_vmregion *c;

	list_for_each_entry(c, &head->vm_list, vm_list) {
		if (c->vm_active && c->vm_start == addr)
			goto out;
	}
	c = NULL;
 out:
	return c;
}

struct arm_vmregion *arm_vmregion_find(struct arm_vmregion_head *head, unsigned long addr)
{
	struct arm_vmregion *c;
	unsigned long flags;

	spin_lock_irqsave(&head->vm_lock, flags);
	c = __arm_vmregion_find(head, addr);
	spin_unlock_irqrestore(&head->vm_lock, flags);
	return c;
}

struct arm_vmregion *arm_vmregion_find_remove(struct arm_vmregion_head *head, unsigned long addr)
{
	struct arm_vmregion *c;
	unsigned long flags;

	spin_lock_irqsave(&head->vm_lock, flags);
	c = __arm_vmregion_find(head, addr);
	if (c)
		c->vm_active = 0;
	spin_unlock_irqrestore(&head->vm_lock, flags);
	return c;
}

void arm_vmregion_free(struct arm_vmregion_head *head, struct arm_vmregion *c)
{
	unsigned long flags;

	spin_lock_irqsave(&head->vm_lock, flags);
	list_del(&c->vm_list);
	spin_unlock_irqrestore(&head->vm_lock, flags);

	kfree(c);
}
