/****************************************************************************
*
*    The MIT License (MIT)
*
*    Copyright (c) 2014 - 2020 Vivante Corporation
*
*    Permission is hereby granted, free of charge, to any person obtaining a
*    copy of this software and associated documentation files (the "Software"),
*    to deal in the Software without restriction, including without limitation
*    the rights to use, copy, modify, merge, publish, distribute, sublicense,
*    and/or sell copies of the Software, and to permit persons to whom the
*    Software is furnished to do so, subject to the following conditions:
*
*    The above copyright notice and this permission notice shall be included in
*    all copies or substantial portions of the Software.
*
*    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
*    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
*    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
*    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
*    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
*    FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
*    DEALINGS IN THE SOFTWARE.
*
*****************************************************************************
*
*    The GPL License (GPL)
*
*    Copyright (C) 2014 - 2020 Vivante Corporation
*
*    This program is free software; you can redistribute it and/or
*    modify it under the terms of the GNU General Public License
*    as published by the Free Software Foundation; either version 2
*    of the License, or (at your option) any later version.
*
*    This program is distributed in the hope that 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.
*
*    You should have received a copy of the GNU General Public License
*    along with this program; if not, write to the Free Software Foundation,
*    Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
*****************************************************************************
*
*    Note: This software is released under dual MIT and GPL licenses. A
*    recipient may use this file under the terms of either the MIT license or
*    GPL License. If you wish to use only one license not the other, you can
*    indicate your decision by deleting one of the above license notices in your
*    version of this file.
*
*****************************************************************************/


#include "gc_hal_kernel_precomp.h"

#define _GC_OBJ_ZONE    gcvZONE_DATABASE

/*******************************************************************************
***** Private fuctions ********************************************************/

#define _GetSlot(database, x) \
    (gctUINT32)(gcmPTR_TO_UINT64(x) % gcmCOUNTOF(database->list))

/*******************************************************************************
**  gckKERNEL_FindDatabase
**
**  Find a database identified by a process ID and move it to the head of the
**  hash list.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          ProcessID that identifies the database.
**
**      gctBOOL LastProcessID
**          gcvTRUE if searching for the last known process ID.  gcvFALSE if
**          we need to search for the process ID specified by the ProcessID
**          argument.
**
**  OUTPUT:
**
**      gcsDATABASE_PTR * Database
**          Pointer to a variable receiving the database structure pointer on
**          success.
*/
gceSTATUS
gckKERNEL_FindDatabase(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    IN gctBOOL LastProcessID,
    OUT gcsDATABASE_PTR * Database
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database, previous;
    gctSIZE_T slot;
    gctBOOL acquired = gcvFALSE;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d LastProcessID=%d",
                   Kernel, ProcessID, LastProcessID);

    /* Compute the hash for the database. */
    slot = ProcessID % gcmCOUNTOF(Kernel->db->db);

    /* Acquire the database mutex. */
    gcmkONERROR(
        gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Check whether we are getting the last known database. */
    if (LastProcessID)
    {
        /* Use last database. */
        database = Kernel->db->lastDatabase;

        if (database == gcvNULL)
        {
            /* Database not found. */
            gcmkONERROR(gcvSTATUS_INVALID_DATA);
        }
    }
    else
    {
        /* Walk the hash list. */
        for (previous = gcvNULL, database = Kernel->db->db[slot];
             database != gcvNULL;
             database = database->next)
        {
            if (database->processID == ProcessID)
            {
                /* Found it! */
                break;
            }

            previous = database;
        }

        if (database == gcvNULL)
        {
            /* Database not found. */
            gcmkONERROR(gcvSTATUS_INVALID_DATA);
        }

        if (previous != gcvNULL)
        {
            /* Move database to the head of the hash list. */
            previous->next   = database->next;
            database->next   = Kernel->db->db[slot];
            Kernel->db->db[slot] = database;
        }
    }

    /* Release the database mutex. */
    gcmkONERROR(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));

    /* Return the database. */
    *Database = database;

    /* Success. */
    gcmkFOOTER_ARG("*Database=0x%x", *Database);
    return gcvSTATUS_OK;

OnError:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }

    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_DeinitDatabase
**
**  De-init a database structure.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gcsDATABASE_PTR Database
**          Pointer to the database structure to deinit.
**
**  OUTPUT:
**
**      Nothing.
*/
static gceSTATUS
gckKERNEL_DeinitDatabase(
    IN gckKERNEL Kernel,
    IN gcsDATABASE_PTR Database
    )
{
    gcmkHEADER_ARG("Kernel=%p Database=%p", Kernel, Database);

    if (Database)
    {
        Database->deleted = gcvFALSE;

        /* Destory handle db. */
        if (Database->refs)
        {
            gcmkVERIFY_OK(gckOS_AtomDestroy(Kernel->os, Database->refs));
            Database->refs = gcvNULL;
        }

        if (Database->handleDatabase)
        {
            gcmkVERIFY_OK(gckKERNEL_DestroyIntegerDatabase(Kernel, Database->handleDatabase));
            Database->handleDatabase = gcvNULL;
        }

        if (Database->handleDatabaseMutex)
        {
            gcmkVERIFY_OK(gckOS_DeleteMutex(Kernel->os, Database->handleDatabaseMutex));
            Database->handleDatabaseMutex = gcvNULL;
        }
    }

    gcmkFOOTER_NO();
    return gcvSTATUS_OK;
}

/*******************************************************************************
**  gckKERNEL_NewRecord
**
**  Create a new database record structure and insert it to the head of the
**  database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gcsDATABASE_PTR Database
**          Pointer to a database structure.
**
**  OUTPUT:
**
**      gcsDATABASE_RECORD_PTR * Record
**          Pointer to a variable receiving the database record structure
**          pointer on success.
*/
static gceSTATUS
gckKERNEL_NewRecord(
    IN gckKERNEL Kernel,
    IN gcsDATABASE_PTR Database,
    IN gctUINT32 Slot,
    OUT gcsDATABASE_RECORD_PTR * Record
    )
{
    gceSTATUS status;
    gctBOOL acquired = gcvFALSE;
    gcsDATABASE_RECORD_PTR record = gcvNULL;

    gcmkHEADER_ARG("Kernel=%p Database=%p", Kernel, Database);

    /* Acquire the database mutex. */
    gcmkONERROR(
        gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    if (Kernel->db->freeRecord != gcvNULL)
    {
        /* Allocate the record from the free list. */
        record             = Kernel->db->freeRecord;
        Kernel->db->freeRecord = record->next;
    }
    else
    {
        gctPOINTER pointer = gcvNULL;

        /* Allocate the record from the heap. */
        gcmkONERROR(gckOS_Allocate(Kernel->os,
                                   gcmSIZEOF(gcsDATABASE_RECORD),
                                   &pointer));

        record = pointer;
    }

    /* Insert the record in the database. */
    record->next         = Database->list[Slot];
    Database->list[Slot] = record;

    /* Release the database mutex. */
    gcmkONERROR(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));

    /* Return the record. */
    *Record = record;

    /* Success. */
    gcmkFOOTER_ARG("*Record=0x%x", *Record);
    return gcvSTATUS_OK;

OnError:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }
    if (record != gcvNULL)
    {
        gcmkVERIFY_OK(gcmkOS_SAFE_FREE(Kernel->os, record));
    }

    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_DeleteRecord
**
**  Remove a database record from the database and delete its structure.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gcsDATABASE_PTR Database
**          Pointer to a database structure.
**
**      gceDATABASE_TYPE Type
**          Type of the record to remove.
**
**      gctPOINTER Data
**          Data of the record to remove.
**
**  OUTPUT:
**
**      gctSIZE_T_PTR Bytes
**          Pointer to a variable that receives the size of the record deleted.
**          Can be gcvNULL if the size is not required.
*/
static gceSTATUS
gckKERNEL_DeleteRecord(
    IN gckKERNEL Kernel,
    IN gcsDATABASE_PTR Database,
    IN gceDATABASE_TYPE Type,
    IN gctPOINTER Data,
    OUT gctSIZE_T_PTR Bytes OPTIONAL
    )
{
    gceSTATUS status;
    gctBOOL acquired = gcvFALSE;
    gcsDATABASE_RECORD_PTR record, previous;
    gctUINT32 slot = _GetSlot(Database, Data);

    gcmkHEADER_ARG("Kernel=%p Database=%p Type=%d Data=%p",
                   Kernel, Database, Type, Data);

    /* Acquire the database mutex. */
    gcmkONERROR(
        gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Scan the database for this record. */
    for (record = Database->list[slot], previous = gcvNULL;
         record != gcvNULL;
         record = record->next
    )
    {
        if ((record->type == Type)
        &&  (record->data == Data)
        )
        {
            /* Found it! */
            break;
        }

        previous = record;
    }

    if (record == gcvNULL)
    {
        /* Ouch!  This record is not found? */
        gcmkONERROR(gcvSTATUS_INVALID_DATA);
    }

    if (Bytes != gcvNULL)
    {
        /* Return size of record. */
        *Bytes = record->bytes;
    }

    /* Remove record from database. */
    if (previous == gcvNULL)
    {
        Database->list[slot] = record->next;
    }
    else
    {
        previous->next = record->next;
    }

    /* Insert record in free list. */
    record->next       = Kernel->db->freeRecord;
    Kernel->db->freeRecord = record;

    /* Release the database mutex. */
    gcmkONERROR(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));

    /* Success. */
    gcmkFOOTER_ARG("*Bytes=%lu", gcmOPT_VALUE(Bytes));
    return gcvSTATUS_OK;

OnError:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }

    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_FindRecord
**
**  Find a database record from the database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gcsDATABASE_PTR Database
**          Pointer to a database structure.
**
**      gceDATABASE_TYPE Type
**          Type of the record to remove.
**
**      gctPOINTER Data
**          Data of the record to remove.
**
**  OUTPUT:
**
**      gctSIZE_T_PTR Bytes
**          Pointer to a variable that receives the size of the record deleted.
**          Can be gcvNULL if the size is not required.
*/
static gceSTATUS
gckKERNEL_FindRecord(
    IN gckKERNEL Kernel,
    IN gcsDATABASE_PTR Database,
    IN gceDATABASE_TYPE Type,
    IN gctPOINTER Data,
    OUT gcsDATABASE_RECORD_PTR Record
    )
{
    gceSTATUS status;
    gctBOOL acquired = gcvFALSE;
    gcsDATABASE_RECORD_PTR record;
    gctUINT32 slot = _GetSlot(Database, Data);

    gcmkHEADER_ARG("Kernel=%p Database=%p Type=%d Data=%p",
                   Kernel, Database, Type, Data);

    /* Acquire the database mutex. */
    gcmkONERROR(
        gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Scan the database for this record. */
    for (record = Database->list[slot];
         record != gcvNULL;
         record = record->next
    )
    {
        if ((record->type == Type)
        &&  (record->data == Data)
        )
        {
            /* Found it! */
            break;
        }
    }

    if (record == gcvNULL)
    {
        /* Ouch!  This record is not found? */
        gcmkONERROR(gcvSTATUS_INVALID_DATA);
    }

    if (Record != gcvNULL)
    {
        /* Return information of record. */
        gcmkONERROR(
            gckOS_MemCopy(Record, record, sizeof(gcsDATABASE_RECORD)));
    }

    /* Release the database mutex. */
    gcmkONERROR(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));

    /* Success. */
    gcmkFOOTER_ARG("Record=0x%x", Record);
    return gcvSTATUS_OK;

OnError:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }

    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
***** Public API **************************************************************/

/*******************************************************************************
**  gckKERNEL_CreateProcessDB
**
**  Create a new process database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**  OUTPUT:
**
**      Nothing.
*/
gceSTATUS
gckKERNEL_CreateProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID
    )
{
    gceSTATUS status = gcvSTATUS_OK;
    gcsDATABASE_PTR database = gcvNULL;
    gctPOINTER pointer = gcvNULL;
    gctBOOL acquired = gcvFALSE;
    gctSIZE_T slot;
    gctUINT32 i;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d", Kernel, ProcessID);

    /* Compute the hash for the database. */
    slot = ProcessID % gcmCOUNTOF(Kernel->db->db);

    /* Acquire the database mutex. */
    gcmkONERROR(gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Walk the hash list. */
    for (database = Kernel->db->db[slot];
         database != gcvNULL;
         database = database->next)
    {
        if (database->processID == ProcessID)
        {
            gctINT32 oldVal = 0;

            if (database->deleted)
            {
                gcmkFATAL("%s(%d): DB of Process=0x%x cannot be reentered since it was in deletion\n",
                          __FUNCTION__, __LINE__, ProcessID);
                gcmkONERROR(gcvSTATUS_INVALID_REQUEST);
            }

            gcmkVERIFY_OK(gckOS_AtomIncrement(Kernel->os, database->refs, &oldVal));
            goto OnExit;
        }
    }

    if (Kernel->db->freeDatabase)
    {
        /* Allocate a database from the free list. */
        database = Kernel->db->freeDatabase;
        Kernel->db->freeDatabase = database->next;
    }
    else
    {
        /* Allocate a new database from the heap. */
        gcmkONERROR(gckOS_Allocate(Kernel->os,
                                   gcmSIZEOF(gcsDATABASE),
                                   &pointer));

        gckOS_ZeroMemory(pointer, gcmSIZEOF(gcsDATABASE));

        database = pointer;

        gcmkONERROR(gckOS_CreateMutex(Kernel->os, &database->counterMutex));
    }

    /* Initialize the database. */
    /* Save the hash slot. */
    database->slot                      = slot;
    database->processID                 = ProcessID;
    database->vidMem.bytes              = 0;
    database->vidMem.maxBytes           = 0;
    database->vidMem.totalBytes         = 0;
    database->nonPaged.bytes            = 0;
    database->nonPaged.maxBytes         = 0;
    database->nonPaged.totalBytes       = 0;
    database->mapMemory.bytes           = 0;
    database->mapMemory.maxBytes        = 0;
    database->mapMemory.totalBytes      = 0;

    for (i = 0; i < gcmCOUNTOF(database->list); i++)
    {
        database->list[i] = gcvNULL;
    }

    for (i = 0; i < gcvVIDMEM_TYPE_COUNT; i++)
    {
        database->vidMemType[i].bytes = 0;
        database->vidMemType[i].maxBytes = 0;
        database->vidMemType[i].totalBytes = 0;
    }

    for (i = 0; i < gcvPOOL_NUMBER_OF_POOLS; i++)
    {
        database->vidMemPool[i].bytes = 0;
        database->vidMemPool[i].maxBytes = 0;
        database->vidMemPool[i].totalBytes = 0;
    }

    gcmkASSERT(database->refs == gcvNULL);
    gcmkONERROR(gckOS_AtomConstruct(Kernel->os, &database->refs));
    gcmkONERROR(gckOS_AtomSet(Kernel->os, database->refs, 1));

    gcmkASSERT(database->handleDatabase == gcvNULL);
    gcmkONERROR(gckKERNEL_CreateIntegerDatabase(Kernel, 64, &database->handleDatabase));

    gcmkASSERT(database->handleDatabaseMutex == gcvNULL);
    gcmkONERROR(gckOS_CreateMutex(Kernel->os, &database->handleDatabaseMutex));

    /* Insert the database into the hash. */
    database->next = Kernel->db->db[slot];
    Kernel->db->db[slot] = database;

    /* Reset idle timer. */
    Kernel->db->lastIdle = 0;

OnError:
    if (gcmIS_ERROR(status))
    {
        gcmkVERIFY_OK(gckKERNEL_DeinitDatabase(Kernel, database));

        if (pointer)
        {
            gcmkOS_SAFE_FREE(Kernel->os, pointer);
        }
    }

OnExit:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }

    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_AddProcessDB
**
**  Add a record to a process database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**      gceDATABASE_TYPE TYPE
**          Type of the record to add.
**
**      gctPOINTER Pointer
**          Data of the record to add.
**
**      gctPHYS_ADDR Physical
**          Physical address of the record to add.
**
**      gctSIZE_T Size
**          Size of the record to add.
**
**  OUTPUT:
**
**      Nothing.
*/
gceSTATUS
gckKERNEL_AddProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    IN gceDATABASE_TYPE Type,
    IN gctPOINTER Pointer,
    IN gctPHYS_ADDR Physical,
    IN gctSIZE_T Size
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;
    gcsDATABASE_RECORD_PTR record = gcvNULL;
    gcsDATABASE_COUNTERS * count;
    gctUINT32 vidMemType;
    gcePOOL vidMemPool;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d Type=%d Pointer=%p "
                   "Physical=%p Size=%lu",
                   Kernel, ProcessID, Type, Pointer, Physical, Size);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);

    /* Decode type. */
    vidMemType = (Type & gcdDB_VIDEO_MEMORY_TYPE_MASK) >> gcdDB_VIDEO_MEMORY_TYPE_SHIFT;
    vidMemPool = (Type & gcdDB_VIDEO_MEMORY_POOL_MASK) >> gcdDB_VIDEO_MEMORY_POOL_SHIFT;

    Type &= gcdDATABASE_TYPE_MASK;

    /* Special case the idle record. */
    if (Type == gcvDB_IDLE)
    {
        gctUINT64 time;

        /* Get the current profile time. */
        gcmkONERROR(gckOS_GetProfileTick(&time));

        if ((ProcessID == 0) && (Kernel->db->lastIdle != 0))
        {
            /* Out of idle, adjust time it was idle. */
            Kernel->db->idleTime += time - Kernel->db->lastIdle;
            Kernel->db->lastIdle  = 0;
        }
        else if (ProcessID == 1)
        {
            /* Save current idle time. */
            Kernel->db->lastIdle = time;
        }

#if gcdDYNAMIC_SPEED
        {
            /* Test for first call. */
            if (Kernel->db->lastSlowdown == 0)
            {
                /* Save milliseconds. */
                Kernel->db->lastSlowdown     = time;
                Kernel->db->lastSlowdownIdle = Kernel->db->idleTime;
            }
            else
            {
                /* Compute ellapsed time in milliseconds. */
                gctUINT delta = gckOS_ProfileToMS(time - Kernel->db->lastSlowdown);

                /* Test for end of period. */
                if (delta >= gcdDYNAMIC_SPEED)
                {
                    /* Compute number of idle milliseconds. */
                    gctUINT idle = gckOS_ProfileToMS(
                        Kernel->db->idleTime  - Kernel->db->lastSlowdownIdle);

                    /* Broadcast to slow down the GPU. */
                    gcmkONERROR(gckOS_BroadcastCalibrateSpeed(Kernel->os,
                                                              Kernel->hardware,
                                                              idle,
                                                              delta));

                    /* Save current time. */
                    Kernel->db->lastSlowdown     = time;
                    Kernel->db->lastSlowdownIdle = Kernel->db->idleTime;
                }
            }
        }
#endif

        /* Success. */
        gcmkFOOTER_NO();
        return gcvSTATUS_OK;
    }

    /* Verify the arguments. */
    gcmkVERIFY_ARGUMENT(Pointer != gcvNULL);

    /* Find the database. */
    gcmkONERROR(gckKERNEL_FindDatabase(Kernel, ProcessID, gcvFALSE, &database));

    /* Create a new record in the database. */
    gcmkONERROR(gckKERNEL_NewRecord(Kernel, database, _GetSlot(database, Pointer), &record));

    /* Initialize the record. */
    record->kernel   = Kernel;
    record->type     = Type;
    record->data     = Pointer;
    record->physical = Physical;
    record->bytes    = Size;

    /* Get pointer to counters. */
    switch (Type)
    {
    case gcvDB_VIDEO_MEMORY:
        count = &database->vidMem;
        break;

    case gcvDB_NON_PAGED:
        count = &database->nonPaged;
        break;

    case gcvDB_CONTIGUOUS:
        count = &database->contiguous;
        break;

    case gcvDB_MAP_MEMORY:
        count = &database->mapMemory;
        break;

    case gcvDB_MAP_USER_MEMORY:
        count = &database->mapUserMemory;
        break;

    default:
        count = gcvNULL;
        break;
    }

    gcmkVERIFY_OK(gckOS_AcquireMutex(Kernel->os, database->counterMutex, gcvINFINITE));

    if (count != gcvNULL)
    {
        /* Adjust counters. */
        count->totalBytes += Size;
        count->bytes      += Size;
        count->allocCount++;

        if (count->bytes > count->maxBytes)
        {
            count->maxBytes = count->bytes;
        }
    }

    if (Type == gcvDB_VIDEO_MEMORY)
    {
        count = &database->vidMemType[vidMemType];

        /* Adjust counters. */
        count->totalBytes += Size;
        count->bytes      += Size;
        count->allocCount++;

        if (count->bytes > count->maxBytes)
        {
            count->maxBytes = count->bytes;
        }

        count = &database->vidMemPool[vidMemPool];

        /* Adjust counters. */
        count->totalBytes += Size;
        count->bytes      += Size;
        count->allocCount++;

        if (count->bytes > count->maxBytes)
        {
            count->maxBytes = count->bytes;
        }
    }

    gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, database->counterMutex));

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_RemoveProcessDB
**
**  Remove a record from a process database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**      gceDATABASE_TYPE TYPE
**          Type of the record to remove.
**
**      gctPOINTER Pointer
**          Data of the record to remove.
**
**  OUTPUT:
**
**      Nothing.
*/
gceSTATUS
gckKERNEL_RemoveProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    IN gceDATABASE_TYPE Type,
    IN gctPOINTER Pointer
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;
    gctSIZE_T bytes = 0;
    gctUINT32 vidMemType;
    gcePOOL vidMemPool;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d Type=%d Pointer=%p",
                   Kernel, ProcessID, Type, Pointer);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);
    gcmkVERIFY_ARGUMENT(Pointer != gcvNULL);

    /* Decode type. */
    vidMemType = (Type & gcdDB_VIDEO_MEMORY_TYPE_MASK) >> gcdDB_VIDEO_MEMORY_TYPE_SHIFT;
    vidMemPool = (Type & gcdDB_VIDEO_MEMORY_POOL_MASK) >> gcdDB_VIDEO_MEMORY_POOL_SHIFT;

    Type &= gcdDATABASE_TYPE_MASK;

    /* Find the database. */
    gcmkONERROR(gckKERNEL_FindDatabase(Kernel, ProcessID, gcvFALSE, &database));

    /* Delete the record. */
    gcmkONERROR(
        gckKERNEL_DeleteRecord(Kernel, database, Type, Pointer, &bytes));

    gcmkVERIFY_OK(gckOS_AcquireMutex(Kernel->os, database->counterMutex, gcvINFINITE));

    /* Update counters. */
    switch (Type)
    {
    case gcvDB_VIDEO_MEMORY:
        database->vidMem.bytes -= bytes;
        database->vidMem.freeCount++;
        database->vidMemType[vidMemType].bytes -= bytes;
        database->vidMemType[vidMemType].freeCount++;
        database->vidMemPool[vidMemPool].bytes -= bytes;
        database->vidMemPool[vidMemPool].freeCount++;
        break;

    case gcvDB_NON_PAGED:
        database->nonPaged.bytes -= bytes;
        database->nonPaged.freeCount++;
        break;

    case gcvDB_CONTIGUOUS:
        database->contiguous.bytes -= bytes;
        database->contiguous.freeCount++;
        break;

    case gcvDB_MAP_MEMORY:
        database->mapMemory.bytes -= bytes;
        database->mapMemory.freeCount++;
        break;

    case gcvDB_MAP_USER_MEMORY:
        database->mapUserMemory.bytes -= bytes;
        database->mapUserMemory.freeCount++;
        break;

    default:
        break;
    }

    gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, database->counterMutex));

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_FindProcessDB
**
**  Find a record from a process database.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**      gceDATABASE_TYPE TYPE
**          Type of the record to remove.
**
**      gctPOINTER Pointer
**          Data of the record to remove.
**
**  OUTPUT:
**
**      gcsDATABASE_RECORD_PTR Record
**          Copy of record.
*/
gceSTATUS
gckKERNEL_FindProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    IN gctUINT32 ThreadID,
    IN gceDATABASE_TYPE Type,
    IN gctPOINTER Pointer,
    OUT gcsDATABASE_RECORD_PTR Record
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d Type=%d Pointer=%p",
                   Kernel, ProcessID, ThreadID, Type, Pointer);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);
    gcmkVERIFY_ARGUMENT(Pointer != gcvNULL);

    /* Find the database. */
    gcmkONERROR(gckKERNEL_FindDatabase(Kernel, ProcessID, gcvFALSE, &database));

    /* Find the record. */
    gcmkONERROR(
        gckKERNEL_FindRecord(Kernel, database, Type, Pointer, Record));

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_DestroyProcessDB
**
**  Destroy a process database.  If the database contains any records, the data
**  inside those records will be deleted as well.  This aids in the cleanup if
**  a process has died unexpectedly or has memory leaks.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**  OUTPUT:
**
**      Nothing.
*/
gceSTATUS
gckKERNEL_DestroyProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID
    )
{
    gceSTATUS status = gcvSTATUS_OK;
    gckKERNEL kernel = Kernel;
    gcsDATABASE_PTR previous = gcvNULL;
    gcsDATABASE_PTR database = gcvNULL;
    gcsDATABASE_PTR db = gcvNULL;
    gctBOOL acquired = gcvFALSE;
    gctSIZE_T slot;
    gctUINT32 i;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d", Kernel, ProcessID);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);

    /* Compute the hash for the database. */
    slot = ProcessID % gcmCOUNTOF(Kernel->db->db);

    /* Acquire the database mutex. */
    gcmkONERROR(gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Walk the hash list. */
    for (database = Kernel->db->db[slot];
         database != gcvNULL;
         database = database->next)
    {
        if (database->processID == ProcessID)
        {
            break;
        }
    }

    if (database)
    {
        gctINT32 oldVal = 0;
        gcmkONERROR(gckOS_AtomDecrement(Kernel->os, database->refs, &oldVal));
        if (oldVal != 1)
        {
            goto OnExit;
        }

        /* Mark it for delete so disallow reenter until really delete it */
        gcmkASSERT(!database->deleted);
        database->deleted = gcvTRUE;
    }
    else
    {
        gcmkFATAL("%s(%d): DB destroy of Process=0x%x cannot match with creation\n",
                  __FUNCTION__, __LINE__, ProcessID);
        gcmkONERROR(gcvSTATUS_NOT_FOUND);
    }

#if gcdCAPTURE_ONLY_MODE
    gcmkPRINT("Capture only mode: The max allocation from System Pool is %llu bytes", database->vidMemPool[gcvPOOL_SYSTEM].maxBytes);
#endif

    /* Cannot remove the database from the hash list
    ** since later records deinit need to access from the hash
    */

    gcmkONERROR(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    acquired = gcvFALSE;

    gcmkTRACE_ZONE(gcvLEVEL_INFO, gcvZONE_DATABASE,
                   "DB(%d): VidMem: total=%lu max=%lu",
                   ProcessID, database->vidMem.totalBytes,
                   database->vidMem.maxBytes);
    gcmkTRACE_ZONE(gcvLEVEL_INFO, gcvZONE_DATABASE,
                   "DB(%d): NonPaged: total=%lu max=%lu",
                   ProcessID, database->nonPaged.totalBytes,
                   database->nonPaged.maxBytes);
    gcmkTRACE_ZONE(gcvLEVEL_INFO, gcvZONE_DATABASE,
                   "DB(%d): Idle time=%llu",
                   ProcessID, Kernel->db->idleTime);
    gcmkTRACE_ZONE(gcvLEVEL_INFO, gcvZONE_DATABASE,
                   "DB(%d): Map: total=%lu max=%lu",
                   ProcessID, database->mapMemory.totalBytes,
                   database->mapMemory.maxBytes);

    {
        gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                       "Process %d has entries in its database:",
                       ProcessID);
    }

    for (i = 0; i < gcmCOUNTOF(database->list); i++)
    {
        gcsDATABASE_RECORD_PTR record, next;

        /* Walk all records. */
        for (record = database->list[i]; record != gcvNULL; record = next)
        {
            gctBOOL asynchronous = gcvTRUE;
            gckVIDMEM_NODE nodeObject;
            gctPHYS_ADDR physical;
            gctUINT32 handle;

            /* Next next record. */
            next = record->next;

            /* Dispatch on record type. */
            switch (record->type)
            {
            case gcvDB_VIDEO_MEMORY:
                gcmkERR_BREAK(gckVIDMEM_HANDLE_Lookup(record->kernel,
                                                      ProcessID,
                                                      gcmPTR2INT32(record->data),
                                                      &nodeObject));

                /* Free the video memory. */
                gcmkVERIFY_OK(gckVIDMEM_HANDLE_Dereference(record->kernel,
                                                           ProcessID,
                                                           gcmPTR2INT32(record->data)));

                gcmkVERIFY_OK(gckVIDMEM_NODE_Dereference(record->kernel,
                                                         nodeObject));

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: VIDEO_MEMORY 0x%x (status=%d)",
                               record->data, status);
                break;

            case gcvDB_NON_PAGED:
                physical = gcmNAME_TO_PTR(record->physical);

                /* Free the non paged memory. */
                status = gckOS_FreeNonPagedMemory(Kernel->os,
                                                  physical,
                                                  record->data,
                                                  record->bytes);

                gcmRELEASE_NAME(record->physical);

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: NON_PAGED 0x%x, bytes=%lu (status=%d)",
                               record->data, record->bytes, status);
                break;

            case gcvDB_SIGNAL:
#if USE_NEW_LINUX_SIGNAL
                status = gcvSTATUS_NOT_SUPPORTED;
#else
                /* Free the user signal. */
                status = gckOS_DestroyUserSignal(Kernel->os,
                                                 gcmPTR2INT32(record->data));
#endif /* USE_NEW_LINUX_SIGNAL */

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: SIGNAL %d (status=%d)",
                               (gctINT)(gctUINTPTR_T)record->data, status);
                break;

            case gcvDB_VIDEO_MEMORY_LOCKED:
                handle = gcmPTR2INT32(record->data);

                gcmkERR_BREAK(gckVIDMEM_HANDLE_Lookup(record->kernel,
                                                      ProcessID,
                                                      handle,
                                                      &nodeObject));

                /* Unlock CPU. */
                gcmkVERIFY_OK(gckVIDMEM_NODE_UnlockCPU(
                    record->kernel, nodeObject, ProcessID, gcvTRUE, gcvFALSE));

                /* Unlock what we still locked */
                status = gckVIDMEM_NODE_Unlock(record->kernel,
                                               nodeObject,
                                               ProcessID,
                                               &asynchronous);

                {
                    /* Deref handle. */
                    gcmkVERIFY_OK(gckVIDMEM_HANDLE_Dereference(record->kernel,
                                                               ProcessID,
                                                               handle));

                    if (gcmIS_SUCCESS(status) && (gcvTRUE == asynchronous))
                    {
                        /* Schedule unlock: will unlock and deref node later. */
                        status = gckEVENT_Unlock(record->kernel->eventObj,
                                                 gcvKERNEL_PIXEL,
                                                 nodeObject);
                    }
                    else
                    {
                        /* Deref node */
                        gcmkVERIFY_OK(gckVIDMEM_NODE_Dereference(record->kernel,
                                                                 nodeObject));
                    }
                }

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: VIDEO_MEMORY_LOCKED 0x%x (status=%d)",
                               record->data, status);
                break;

            case gcvDB_CONTEXT:
                status = gckCOMMAND_Detach(record->kernel->command, gcmNAME_TO_PTR(record->data));
                gcmRELEASE_NAME(record->data);

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: CONTEXT 0x%x (status=%d)",
                               record->data, status);
                break;

            case gcvDB_MAP_MEMORY:
                /* Unmap memory. */
                status = gckKERNEL_UnmapMemory(record->kernel,
                                               record->physical,
                                               record->bytes,
                                               record->data,
                                               ProcessID);

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: MAP MEMORY %d (status=%d)",
                               gcmPTR2INT32(record->data), status);
                break;

            case gcvDB_SHBUF:
                /* Free shared buffer. */
                status = gckKERNEL_DestroyShBuffer(record->kernel,
                                                   (gctSHBUF) record->data);

                gcmkTRACE_ZONE(gcvLEVEL_WARNING, gcvZONE_DATABASE,
                               "DB: SHBUF %u (status=%d)",
                               (gctUINT32)(gctUINTPTR_T) record->data, status);
                break;

            default:
                gcmkTRACE_ZONE(gcvLEVEL_ERROR, gcvZONE_DATABASE,
                               "DB: Correcupted record=0x%08x type=%d",
                               record, record->type);
                break;
            }

            /* Delete the record. */
            gcmkONERROR(gckKERNEL_DeleteRecord(Kernel,
                                               database,
                                               record->type,
                                               record->data,
                                               gcvNULL));
        }
    }

    gcmkONERROR(gckKERNEL_DestroyProcessReservedUserMap(Kernel, ProcessID));

    /* Acquire the database mutex. */
    gcmkONERROR(gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));
    acquired = gcvTRUE;

    /* Walk the hash list. */
    for (db = Kernel->db->db[slot];
         db != gcvNULL;
         db = db->next)
    {
        if (db->processID == ProcessID)
        {
            break;
        }
        previous = db;
    }

    if (db != database || !db->deleted)
    {
        gcmkFATAL("%s(%d): DB of Process=0x%x corrupted after found in deletion\n",
                  __FUNCTION__, __LINE__, ProcessID);
        gcmkONERROR(gcvSTATUS_NOT_FOUND);
    }

    /* Remove the database from the hash list. */
    if (previous)
    {
        previous->next = database->next;
    }
    else
    {
        Kernel->db->db[slot] = database->next;
    }

    /* Deinit current database. */
    gcmkVERIFY_OK(gckKERNEL_DeinitDatabase(Kernel, database));

    if (Kernel->db->lastDatabase)
    {
        /* Insert last database to the free list. */
        Kernel->db->lastDatabase->next = Kernel->db->freeDatabase;
        Kernel->db->freeDatabase       = Kernel->db->lastDatabase;
    }

    /* Update last database to current one. */
    Kernel->db->lastDatabase = database;

OnError:
OnExit:
    if (acquired)
    {
        /* Release the database mutex. */
        gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));
    }
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

/*******************************************************************************
**  gckKERNEL_QueryProcessDB
**
**  Query a process database for the current usage of a particular record type.
**
**  INPUT:
**
**      gckKERNEL Kernel
**          Pointer to a gckKERNEL object.
**
**      gctUINT32 ProcessID
**          Process ID used to identify the database.
**
**      gctBOOL LastProcessID
**          gcvTRUE if searching for the last known process ID.  gcvFALSE if
**          we need to search for the process ID specified by the ProcessID
**          argument.
**
**      gceDATABASE_TYPE Type
**          Type of the record to query.
**
**  OUTPUT:
**
**      gcuDATABASE_INFO * Info
**          Pointer to a variable that receives the requested information.
*/
gceSTATUS
gckKERNEL_QueryProcessDB(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    IN gctBOOL LastProcessID,
    IN gceDATABASE_TYPE Type,
    OUT gcuDATABASE_INFO * Info
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;
    gcePOOL vidMemPool;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d Type=%d Info=%p",
                   Kernel, ProcessID, Type, Info);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);
    gcmkVERIFY_ARGUMENT(Info != gcvNULL);

    /* Deocde pool. */
    vidMemPool = (Type & gcdDB_VIDEO_MEMORY_POOL_MASK) >> gcdDB_VIDEO_MEMORY_POOL_SHIFT;

    Type &= gcdDATABASE_TYPE_MASK;

    /* Find the database. */
    gcmkONERROR(gckKERNEL_FindDatabase(Kernel, ProcessID, LastProcessID, &database));

    gcmkVERIFY_OK(gckOS_AcquireMutex(Kernel->os, database->counterMutex, gcvINFINITE));

    /* Get pointer to counters. */
    switch (Type)
    {
    case gcvDB_VIDEO_MEMORY:
        if (vidMemPool != gcvPOOL_UNKNOWN)
        {
            gckOS_MemCopy(&Info->counters,
                          &database->vidMemPool[vidMemPool],
                          gcmSIZEOF(database->vidMemPool[vidMemPool]));
        }
        else
        {
            gckOS_MemCopy(&Info->counters,
                          &database->vidMem,
                          gcmSIZEOF(database->vidMem));
        }
        break;

    case gcvDB_NON_PAGED:
        gckOS_MemCopy(&Info->counters,
                                  &database->nonPaged,
                                  gcmSIZEOF(database->vidMem));
        break;

    case gcvDB_CONTIGUOUS:
        gckOS_MemCopy(&Info->counters,
                                  &database->contiguous,
                                  gcmSIZEOF(database->vidMem));
        break;

    case gcvDB_IDLE:
        Info->time           = Kernel->db->idleTime;
        Kernel->db->idleTime = 0;
        break;

    case gcvDB_MAP_MEMORY:
        gckOS_MemCopy(&Info->counters,
                                  &database->mapMemory,
                                  gcmSIZEOF(database->mapMemory));
        break;

    default:
        break;
    }

    gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, database->counterMutex));

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

gceSTATUS
gckKERNEL_FindHandleDatbase(
    IN gckKERNEL Kernel,
    IN gctUINT32 ProcessID,
    OUT gctPOINTER * HandleDatabase,
    OUT gctPOINTER * HandleDatabaseMutex
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d",
                   Kernel, ProcessID);

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);

    /* Find the database. */
    gcmkONERROR(gckKERNEL_FindDatabase(Kernel, ProcessID, gcvFALSE, &database));

    *HandleDatabase = database->handleDatabase;
    *HandleDatabaseMutex = database->handleDatabaseMutex;

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}

gceSTATUS
gckKERNEL_DumpProcessDB(
    IN gckKERNEL Kernel
    )
{
    gcsDATABASE_PTR database;
    gctINT i, pid;
    gctUINT8 name[24];

    gcmkHEADER_ARG("Kernel=%p", Kernel);

    /* Acquire the database mutex. */
    gcmkVERIFY_OK(
        gckOS_AcquireMutex(Kernel->os, Kernel->db->dbMutex, gcvINFINITE));

    gcmkPRINT("**************************\n");
    gcmkPRINT("***  PROCESS DB DUMP   ***\n");
    gcmkPRINT("**************************\n");

    gcmkPRINT_N(8, "%-8s%s\n", "PID", "NAME");
    /* Walk the databases. */
    for (i = 0; i < gcmCOUNTOF(Kernel->db->db); ++i)
    {
        for (database = Kernel->db->db[i];
             database != gcvNULL;
             database = database->next)
        {
            pid = database->processID;

            gcmkVERIFY_OK(gckOS_ZeroMemory(name, gcmSIZEOF(name)));

            gcmkVERIFY_OK(gckOS_GetProcessNameByPid(pid, gcmSIZEOF(name), name));

            gcmkPRINT_N(8, "%-8d%s\n", pid, name);
        }
    }

    /* Release the database mutex. */
    gcmkVERIFY_OK(gckOS_ReleaseMutex(Kernel->os, Kernel->db->dbMutex));

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;
}

void
_DumpCounter(
    IN gcsDATABASE_COUNTERS * Counter,
    IN gctCONST_STRING Name
    )
{
    gcmkPRINT("%s:", Name);
    gcmkPRINT("  Currently allocated : %10lld", Counter->bytes);
    gcmkPRINT("  Maximum allocated   : %10lld", Counter->maxBytes);
    gcmkPRINT("  Total allocated     : %10lld", Counter->totalBytes);
}

gceSTATUS
gckKERNEL_DumpVidMemUsage(
    IN gckKERNEL Kernel,
    IN gctINT32 ProcessID
    )
{
    gceSTATUS status;
    gcsDATABASE_PTR database;
    gcsDATABASE_COUNTERS * counter;
    gctUINT32 i = 0;

    static gctCONST_STRING vidmemTypes[] = {
        "GENERIC",
        "INDEX",
        "VERTEX",
        "TEXTURE",
        "RENDER_TARGET",
        "DEPTH",
        "BITMAP",
        "TILE_STATUS",
        "IMAGE",
        "MASK",
        "SCISSOR",
        "HIERARCHICAL_DEPTH",
        "ICACHE",
        "TXDESC",
        "FENCE",
        "TFBHEADER",
        "COMMAND",
    };

    gcmkHEADER_ARG("Kernel=%p ProcessID=%d",
                   Kernel, ProcessID);

    gcmSTATIC_ASSERT(gcmCOUNTOF(vidmemTypes) == gcvVIDMEM_TYPE_COUNT,
                     "Video memory type mismatch");

    /* Verify the arguments. */
    gcmkVERIFY_OBJECT(Kernel, gcvOBJ_KERNEL);

    /* Find the database. */
    gcmkONERROR(
        gckKERNEL_FindDatabase(Kernel, ProcessID, gcvFALSE, &database));

    gcmkPRINT("VidMem Usage (Process %d):", ProcessID);

    /* Get pointer to counters. */
    counter = &database->vidMem;

    _DumpCounter(counter, "Total Video Memory");

    for (i = 0; i < gcvVIDMEM_TYPE_COUNT; i++)
    {
        counter = &database->vidMemType[i];

        _DumpCounter(counter, vidmemTypes[i]);
    }

    /* Success. */
    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:
    /* Return the status. */
    gcmkFOOTER();
    return status;
}
