/*
 **    Name: rmamalloc.c
 **
 **    Date: Sun Jan  5 16:30:54 2003
 **
 */

#include "rmamem.h"
#include "osheap.h"
#include "kernel.h"
#include "osmodule.h"
#include <stdlib.h>

#include <stdio.h>

char *rmamalloc(size_t size)
{
    char *ptr;

    _kernel_oserror *error;

    int grow_count;

    _kernel_swi_regs regs;

    if (rmamem_status == RMAMEM_UNITIALISED)
    {
        rmamem_init(RMAMEM_UNITIALISED);
    }

    switch (rmamem_status)
    {
        case RMAMEM_DYNAMICAREA:

            grow_count = 0;
            ptr = NULL;

            while (grow_count < 100 && ptr == NULL)
            {
                if (rmamem_grow(size + rmamem_details.add) == 1)
                {
                    return NULL;
                }

                regs.r[0] = OSHeap_Alloc;
                regs.r[1] = rmamem_details.base;
                regs.r[3] = size;
                if ((error = _kernel_swi(XOS_Heap,&regs,&regs)) == NULL)
                {
                    ptr = (char *)regs.r[2];
                }
                else
                {
                    ptr = NULL;
                }

                grow_count++;
            }

            break;

        case RMAMEM_MALLOC:
            ptr = malloc(size);
            break;

        case RMAMEM_RMA:
            regs.r[0] = OSModule_Alloc;
            regs.r[3] = size + 4;
            if (_kernel_swi(XOS_Module,&regs,&regs) == NULL)
            {
                ptr = (char *)regs.r[2];

                if (ptr != NULL)
                {
                    *(int *)ptr = size;
                    rmamem_details.count++;
                    return ptr + 4;
                }
            }
            else
            {
                ptr = NULL;
            }
            break;
    }

    return ptr;
}
