/* ------------------------------------------------------------------------------ */
static MUINT32 SYSRAM_AllocUser(SYSRAM_USER_ENUM const User, MUINT32 Size, MUINT32 const Alignment)
{
	MUINT32 Addr = 0;

	SYSRAM_MEM_BANK_ENUM const MemBankNo = SYSRAM_GetMemBankNo(User);
	/*  */
	if (SYSRAM_IsBadOwner(User)) {
		LOG_ERR("User(%d) out of range(%d)", User, SYSRAM_USER_AMOUNT);
		return 0;
	}
	/*  */
	if (!SYSRAM_IsLegalSizeToAlloc(MemBankNo, User, Size)) {
		return 0;
	}
	/*  */
	switch (MemBankNo) {
	case SYSRAM_MEM_BANK_BAD:
	case SYSRAM_MEM_BANK_AMOUNT:
		{
			/* Do nothing. */
			break;
		}
	default:
		{
			Addr = SYSRAM_AllocUserPhy(User, Size, Alignment, MemBankNo);
			break;
		}
	}
	/*  */
	if (0 < Addr) {
		SYSRAM_LockUser(User, Size);
	}
	/*  */
	return Addr;
}
/* ------------------------------------------------------------------------------ */
static void SYSRAM_ResetUserTaskInfo(SYSRAM_USER_ENUM const User)
{
	if (!SYSRAM_IsBadOwner(User)) {
		SYSRAM_USER_STRUCT * const pUserInfo = &Sysram.UserInfo[User];
		memset(pUserInfo, 0, sizeof(*pUserInfo));
	}
}
Пример #3
0
//------------------------------------------------------------------------------
static void SYSRAM_DumpLayout(void)
{
    MUINT32 Index = 0;
    SYSRAM_MEM_NODE_STRUCT* pCurrNode = NULL;
    //
    LOG_DMP("[SYSRAM_DumpLayout]\n");
    LOG_DMP("AllocatedTbl = 0x%08lX\n",Sysram.AllocatedTbl);
    LOG_DMP("=========================================\n");
    for (Index = 0; Index < SYSRAM_MEM_BANK_AMOUNT; Index++)
    {
        LOG_DMP("\n [Mem Pool %ld] (IndexTbl, UserCount)=(%lX, %ld)\n",
                Index,
                SysramMemPoolInfo[Index].IndexTbl,
                SysramMemPoolInfo[Index].UserCount);
        LOG_DMP("[Locked Time] [Owner   Offset   Size  Index pCurrent pPrevious pNext]  [pid tgid] [Proc Name / Owner Name]\n");
        pCurrNode = &SysramMemPoolInfo[Index].pMemNode[0];
        while(NULL != pCurrNode)
        {
            SYSRAM_USER_ENUM const User = pCurrNode->User;
            if(SYSRAM_IsBadOwner(User))
            {
                LOG_DMP(
                    "------------ --------"
                    " %2d\t0x%05lX 0x%05lX  %ld    %p %p\t%p\n",
                    pCurrNode->User,
                    pCurrNode->Offset,
                    pCurrNode->Length,
                    pCurrNode->Index,
                    pCurrNode,
                    pCurrNode->pPrev,
                    pCurrNode->pNext);
            }
            else
            {
                SYSRAM_USER_STRUCT*const pUserInfo = &Sysram.UserInfo[User];
                LOG_DMP("%5lu.%06lu"
                        " %2d\t0x%05lX 0x%05lX  %ld    %p %p\t%p"
                        "  %-4d %-4d \"%s\" / \"%s\"\n",
                        pUserInfo->TimeS,
                        pUserInfo->TimeUS,
                        User,
                        pCurrNode->Offset,
                        pCurrNode->Length,
                        pCurrNode->Index,
                        pCurrNode,
                        pCurrNode->pPrev,
                        pCurrNode->pNext,
                        pUserInfo->pid,
                        pUserInfo->tgid,
                        pUserInfo->ProcName,
                        SysramUserName[User]);
            }
            pCurrNode = pCurrNode->pNext;
        };
    }
    LOG_DMP("\n");
    SYSRAM_DumpResMgr();
}
/* ------------------------------------------------------------------------------ */
static void SYSRAM_SetUserTaskInfo(SYSRAM_USER_ENUM const User)
{
	if (!SYSRAM_IsBadOwner(User)) {
		SYSRAM_USER_STRUCT * const pUserInfo = &Sysram.UserInfo[User];
		/*  */
		pUserInfo->pid = current->pid;
		pUserInfo->tgid = current->tgid;
		memcpy(pUserInfo->ProcName, current->comm, sizeof(pUserInfo->ProcName));
		/*  */
		SYSRAM_GetTime(&(pUserInfo->Time64), &(pUserInfo->TimeS), &(pUserInfo->TimeUS));
	}
}
/* ------------------------------------------------------------------------------ */
static void SYSRAM_IOC_Free(SYSRAM_USER_ENUM User)
{
	if (SYSRAM_IsBadOwner(User)) {
		LOG_ERR("User(%d) out of range(%d)", User, SYSRAM_USER_AMOUNT);
		return;
	}
	/*  */
	SYSRAM_SpinLock();
	SYSRAM_FreeUser(User);
	wake_up_interruptible(&Sysram.WaitQueueHead);
	SYSRAM_CheckClock();
	SYSRAM_SpinUnlock();
	/*  */
	if ((1 << User) & SysramLogUserMask) {
		LOG_MSG("[User:%s]Done", SysramUserName[User]);
	}
}
/* ------------------------------------------------------------------------------ */
static MUINT32 SYSRAM_IOC_Alloc(SYSRAM_USER_ENUM const User,
				MUINT32 const Size, MUINT32 Alignment, MUINT32 const TimeoutMS)
{
	MUINT32 Addr = 0;
	MINT32 TimeOut = 0;
	/*  */
	if (SYSRAM_IsBadOwner(User)) {
		LOG_ERR("User(%d) out of range(%d)", User, SYSRAM_USER_AMOUNT);
		return 0;
	}
	/*  */
	if (0 == Size) {
		LOG_ERR("[User:%s]allocates 0 size!", SysramUserName[User]);
		return 0;
	}
	/*  */
	Addr = SYSRAM_TryAllocUser(User, Size, Alignment);
	if (0 != Addr		/* success */
	    || 0 == TimeoutMS	/* failure without a timeout specified */
	    ) {
		goto EXIT;
	}
	/*  */
	TimeOut = wait_event_interruptible_timeout(Sysram.WaitQueueHead,
						   0 != (Addr =
							 SYSRAM_TryAllocUser(User, Size,
									     Alignment)),
						   SYSRAM_MsToJiffies(TimeoutMS));
	/*  */
	if (0 == TimeOut && 0 == Addr) {
		LOG_ERR("[User:%s]allocate timeout", SysramUserName[User]);
	}
	/*  */
EXIT:
	if (0 == Addr) {	/* Failure */
		LOG_ERR("[User:%s]fails to allocate.Size(%lu),Alignment(%lu),TimeoutMS(%lu)",
			SysramUserName[User], Size, Alignment, TimeoutMS);
		SYSRAM_DumpLayout();
	} else {		/* Success */
		if ((1 << User) & SysramLogUserMask) {
			LOG_MSG("[User:%s]%lu bytes OK", SysramUserName[User], Size);
		}
	}
	/*  */
	return Addr;
}
Пример #7
0
//------------------------------------------------------------------------------
static long SYSRAM_Ioctl(
    struct file*    pFile,
    unsigned int    Cmd,
    unsigned long   Param)
{
    MINT32 Ret = 0;
    MUINT32 Sec = 0,USec = 0;
    MUINT64 Time64 = 0;
    SYSRAM_PROC_STRUCT* pProc = (SYSRAM_PROC_STRUCT*)pFile->private_data;
    SYSRAM_ALLOC_STRUCT Alloc;
    SYSRAM_USER_ENUM User;
    //
    SYSRAM_GetTime(&Time64, &Sec, &USec);
    /*
    LOG_MSG("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
            current->comm,
            current->pid,
            current->tgid,
            Sec,
            USec);
    */
    if(pFile->private_data == NULL)
    {
        LOG_WRN("private_data is NULL.");
        Ret = -EFAULT;
        goto EXIT;
    }
    //
    switch(Cmd)
    {
    case SYSRAM_ALLOC:
    {
        if(copy_from_user(&Alloc, (void*)Param, sizeof(SYSRAM_ALLOC_STRUCT)) == 0)
        {
            if(SYSRAM_IsBadOwner(Alloc.User))
            {
                LOG_ERR("User(%d) out of range(%d)",Alloc.User,SYSRAM_USER_AMOUNT);
                Ret = -EFAULT;
                goto EXIT;
            }
            //
            Alloc.Addr = SYSRAM_IOC_Alloc(
                             Alloc.User,
                             Alloc.Size,
                             Alloc.Alignment,
                             Alloc.TimeoutMS);
            if(Alloc.Addr != 0)
            {
                SYSRAM_SpinLock();
                pProc->Table |= (1 << Alloc.User);
                if(pProc->Tgid == 0)
                {
                    pProc->Pid = current->pid;
                    pProc->Tgid = current->tgid;
                    strcpy(pProc->ProcName,current->comm);
                    SYSRAM_SpinUnlock();
                }
                else
                {
                    SYSRAM_SpinUnlock();
                    if(pProc->Tgid != current->tgid)
                    {
                        LOG_ERR("Tgid is inconsistent");
                        Ret = -EFAULT;
                    }
                }
            }
            else
            {
                Ret = -EFAULT;
            }
            //
            if(copy_to_user((void*)Param, &Alloc, sizeof(SYSRAM_ALLOC_STRUCT)) )
            {
                LOG_ERR("copy to user failed");
                Ret = -EFAULT;
            }
        }
        else
        {
            LOG_ERR("copy_from_user fail");
            Ret = -EFAULT;
        }
        break;
    }
    //
    case SYSRAM_FREE:
    {
        if(copy_from_user(&User, (void*)Param, sizeof(SYSRAM_USER_ENUM)) == 0)
        {
            if(SYSRAM_IsBadOwner(User))
            {
                LOG_ERR("User(%d) out of range(%d)",User,SYSRAM_USER_AMOUNT);
                Ret = -EFAULT;
                goto EXIT;
            }
            //
            SYSRAM_SpinLock();
            if((pProc->Table) & (1 << User))
            {
                SYSRAM_SpinUnlock();
                SYSRAM_IOC_Free(User);
                SYSRAM_SpinLock();
                //
                pProc->Table &= (~(1 << User));
                if(pProc->Table == 0)
                {
                    pProc->Pid = 0;
                    pProc->Tgid = 0;
                    strcpy(pProc->ProcName,SYSRAM_PROC_NAME);
                }
                SYSRAM_SpinUnlock();
            }
            else
            {
                SYSRAM_SpinUnlock();
                LOG_WRN("Freeing unallocated buffer user(%d)",User);
                Ret = -EFAULT;
            }
        }
        else
        {
            LOG_ERR("copy_from_user fail");
            Ret = -EFAULT;
        }
        break;
    }
    case SYSRAM_DUMP:
    {
        SYSRAM_DumpLayout();
        break;
    }
    default:
    {
        LOG_WRN("No such command");
        Ret = -EINVAL;
        break;
    }
    }
    //
EXIT:
    if(Ret != 0)
    {
        LOG_ERR("Fail");
        LOG_ERR("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
                current->comm,
                current->pid,
                current->tgid,
                Sec,
                USec);
        if(pFile->private_data != NULL)
        {
            LOG_ERR("Proc:Name(%s),pid(%d),tgid(%d),Table(0x%08lX),Time(%ld.%06ld)",
                    pProc->ProcName,
                    pProc->Pid,
                    pProc->Tgid,
                    pProc->Table,
                    Sec,
                    USec);
        }
    }
    //
    return Ret;
}
Пример #8
0
//------------------------------------------------------------------------------
static int SYSRAM_DumpLayoutToProc(
    char*   pPage,
    char**  ppStart,
    off_t   Off,
    int     Count,
    int*    pEof,
    void*   pData)
{
    char *p = pPage;
    MUINT32 len = 0;
    MUINT32 Index = 0;
    SYSRAM_MEM_NODE_STRUCT* pCurrNode = NULL;
    //
    p += sprintf(p, "\n[SYSRAM_DumpLayoutToProc]\n");
    p += sprintf(p, "AllocatedTbl = 0x%08lX\n",Sysram.AllocatedTbl);
    p += sprintf(p, "=========================================\n" );
    for (Index = 0; Index < SYSRAM_MEM_BANK_AMOUNT; Index++)
    {
        p += sprintf(p, "\n [Mem Pool %ld] (IndexTbl, UserCount)=(%lX, %ld)\n",
                     Index,
                     SysramMemPoolInfo[Index].IndexTbl,
                     SysramMemPoolInfo[Index].UserCount);
        p += sprintf(p, "[Locked Time] [Owner   Offset   Size  Index pCurrent pPrevious pNext]  [pid tgid] [Proc Name / Owner Name]\n");
        pCurrNode = &SysramMemPoolInfo[Index].pMemNode[0];
        while ( NULL != pCurrNode )
        {
            SYSRAM_USER_ENUM const User = pCurrNode->User;
            if  ( SYSRAM_IsBadOwner(User) )
            {
                p += sprintf(p,
                             "------------ --------"
                             " %2d\t0x%05lX 0x%05lX  %ld    %p %p\t%p\n",
                             pCurrNode->User,
                             pCurrNode->Offset,
                             pCurrNode->Length,
                             pCurrNode->Index,
                             pCurrNode,
                             pCurrNode->pPrev,
                             pCurrNode->pNext
                            );
            }
            else
            {
                SYSRAM_USER_STRUCT*const pUserInfo = &Sysram.UserInfo[User];
                p += sprintf(p,
                             "%5lu.%06lu"
                             " %2d\t0x%05lX 0x%05lX  %ld    %p %p\t%p"
                             "  %-4d %-4d \"%s\" / \"%s\"\n",
                             pUserInfo->TimeS,
                             pUserInfo->TimeUS,
                             User,
                             pCurrNode->Offset,
                             pCurrNode->Length,
                             pCurrNode->Index,
                             pCurrNode,
                             pCurrNode->pPrev,
                             pCurrNode->pNext,
                             pUserInfo->pid,
                             pUserInfo->tgid,
                             pUserInfo->ProcName,
                             SysramUserName[User]);
            }
            pCurrNode = pCurrNode->pNext;
        };
    }
    //
    *ppStart = pPage + Off;
    len = p - pPage;
    if(len > Off)
    {
        len -= Off;
    }
    else
    {
        len = 0;
    }
    //
    return len < Count ? len : Count;
}