示例#1
0
//------------------------------------------------------------------------------
static void SYSRAM_FreeUser(SYSRAM_USER_ENUM const User)
{
    SYSRAM_MEM_BANK_ENUM const MemBankNo = SYSRAM_GetMemBankNo(User);
    //
    switch(MemBankNo)
    {
    case SYSRAM_MEM_BANK_BAD:
    case SYSRAM_MEM_BANK_AMOUNT:
    {
        //  Do nothing.
        break;
    }
    default:
    {
        if(SYSRAM_FreeUserPhy(User, MemBankNo))
        {
            SYSRAM_UnlockUser(User);
        }
        else
        {
            LOG_ERR("Cannot free User(%d)",User);
            SYSRAM_DumpLayout();
        }
        break;
    }
    }
}
/* ------------------------------------------------------------------------------ */
static MBOOL SYSRAM_IsLegalSizeToAlloc(SYSRAM_MEM_BANK_ENUM const MemBankNo,
				       SYSRAM_USER_ENUM const User, MUINT32 const Size)
{
	MUINT32 MaxSize = 0;
	/* (1) Check the memory pool. */
	switch (MemBankNo) {
	case SYSRAM_MEM_BANK_BAD:
	case SYSRAM_MEM_BANK_AMOUNT:
		{
			/* Illegal Memory Pool: return "illegal" */
			/* Shouldn't happen. */
			goto EXIT;
		}
	default:
		{
			break;
		}
	}
	/* (2) */
	/* Here we use the dynamic memory pools. */
	MaxSize = SysramUserSize[User];
	/*  */
EXIT:
	if (MaxSize < Size) {
		LOG_ERR("[User:%s]requested size(0x%lX) > max size(0x%lX)",
			SysramUserName[User], Size, MaxSize);
		SYSRAM_DumpLayout();
		return MFALSE;
	}
	return MTRUE;
}
/* ------------------------------------------------------------------------------ */
static int SYSRAM_Release(struct inode *pInode, struct file *pFile)
{
	MUINT32 Index = 0;
	MUINT32 Sec = 0, USec = 0;
	MUINT64 Time64 = 0;
	SYSRAM_PROC_STRUCT *pProc;
	/*  */
	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) {
		pProc = (SYSRAM_PROC_STRUCT *) (pFile->private_data);
		/*  */
		if (pProc->Pid != 0 || pProc->Tgid != 0 || pProc->Table != 0) {
			/*  */
			LOG_WRN("Proc:Name(%s),pid(%d),tgid(%d),Table(0x%08lX),Time(%ld.%06ld)",
				pProc->ProcName,
				pProc->Pid, pProc->Tgid, pProc->Table, pProc->TimeS, pProc->TimeUS);
			/*  */
			if (pProc->Table) {
				LOG_WRN("Force to release");
				/*
				   LOG_WRN("Proc:Name(%s),pid(%d),tgid(%d),Table(0x%08lX),Time(%ld.%06ld)",
				   pProc->ProcName,
				   pProc->Pid,
				   pProc->Tgid,
				   pProc->Table,
				   pProc->TimeS,
				   pProc->TimeUS);
				 */
				SYSRAM_DumpLayout();
				/*  */
				for (Index = 0; Index < SYSRAM_USER_AMOUNT; Index++) {
					if (pProc->Table & (1 << Index)) {
						SYSRAM_IOC_Free((SYSRAM_USER_ENUM) Index);
					}
				}
			}
		}
		/*  */
		kfree(pFile->private_data);
		pFile->private_data = NULL;
	} else {
		LOG_WRN("private_data is NULL");
		/*
		   LOG_WRN("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
		   current->comm,
		   current->pid,
		   current->tgid,
		   Sec,
		   USec);
		 */
	}
	/*  */
	return 0;
}
/* ------------------------------------------------------------------------------ */
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;
}
示例#5
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;
}
示例#6
0
//------------------------------------------------------------------------------
static int SYSRAM_Flush(
    struct file*    pFile,
    fl_owner_t      Id)
{
    MUINT32 Index = 0;
    MUINT32 Sec = 0,USec = 0;
    MUINT64 Time64 = 0;
    SYSRAM_PROC_STRUCT* pProc;
    //
    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)
    {
        pProc = (SYSRAM_PROC_STRUCT *)pFile->private_data;
        //
        if( pProc->Pid != 0 ||
                pProc->Tgid != 0 ||
                pProc->Table != 0)
        {
            //
            LOG_WRN("Proc:Name(%s),pid(%d),tgid(%d),Table(0x%08lX),Time(%ld.%06ld)",
                    pProc->ProcName,
                    pProc->Pid,
                    pProc->Tgid,
                    pProc->Table,
                    pProc->TimeS,
                    pProc->TimeUS);
            //
            if( pProc->Tgid == 0 &&
                    pProc->Table != 0)
            {
                LOG_ERR("No Tgid info");
                /*
                LOG_ERR("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
                        current->comm,
                        current->pid,
                        current->tgid,
                        Sec,
                        USec);
                LOG_ERR("Proc:Name(%s),pid(%d),tgid(%d),Table(0x%08lX),Time(%ld.%06ld)",
                        pProc->ProcName,
                        pProc->Pid,
                        pProc->Tgid,
                        pProc->Table,
                        pProc->TimeS,
                        pProc->TimeUS);
                */
            }
            else if( (pProc->Tgid == current->tgid) ||
                     ((pProc->Tgid != current->tgid) && (strcmp(current->comm, "binder") == 0)))
            {
                if(pProc->Table)
                {
                    LOG_WRN("Force to release");
                    /*
                    LOG_WRN("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
                            current->comm,
                            current->pid,
                            current->tgid,
                            Sec,
                            USec);
                    */
                    SYSRAM_DumpLayout();
                    //
                    for(Index = 0 ; Index < SYSRAM_USER_AMOUNT; Index++)
                    {
                        if(pProc->Table & (1 << Index))
                        {
                            SYSRAM_IOC_Free((SYSRAM_USER_ENUM)Index);
                        }
                    }
                    //
                    pProc->Table= 0;
                }
            }

        }
    }
    else
    {
        LOG_WRN("private_data is NULL");
        /*
        LOG_WRN("Cur:Name(%s),pid(%d),tgid(%d),Time(%ld.%06ld)",
                current->comm,
                current->pid,
                current->tgid,
                Sec,
                USec);
        */
    }
    //
    return 0;
}