Beispiel #1
0
HLOCAL 
OALLocalAlloc(
    UINT flags, 
    UINT size
    )
{
    DWORD i;
    DWORD startBlock = (DWORD) -1;
    DWORD contiguous = 0;
    T_BLOCK_COUNT_TYPE nbRequestBlock = (T_BLOCK_COUNT_TYPE) (((size+BLOCK_COUNT_SIZE) + BLOCK_SIZE- 1)/ BLOCK_SIZE);

    UNREFERENCED_PARAMETER(flags);

    DEBUGMSG(0,(TEXT("OALLocalAlloc request for %d bytes => %d block\r\n"),size,nbRequestBlock));

    for (i=0; i<nbBlock; i++)
    {
        if (IS_BLOCK_USED(i))
        {
            DEBUGMSG(0,(TEXT("block %d is used\r\n"),i));
            contiguous = 0;
            startBlock = (DWORD) -1;
        }
        else
        {
            if (contiguous == 0)
            {
                DEBUGMSG(0,(TEXT("block %d is unused\r\n"),i));
                startBlock = i;
            }
            contiguous++;      
            if (nbRequestBlock == contiguous)
            {
                DEBUGMSG(0,(TEXT("found %d free blocks (%d,%d)\r\n"),nbRequestBlock,startBlock,i));
                break;
            }
        }
    }
    if ((startBlock == (DWORD) -1) || (nbRequestBlock != contiguous))
    {
        RETAILMSG(1, (TEXT("OALLocalAlloc returned NULL !\r\n")));
        return NULL;
    }
    else
    {        
        T_BLOCK_COUNT_TYPE* p = (T_BLOCK_COUNT_TYPE*) (pool + (startBlock * BLOCK_SIZE));
        *p = nbRequestBlock;
        for (i=0;i<nbRequestBlock;i++)
        {
            DEBUGMSG(0,(TEXT("marking block %d used\r\n"),i+startBlock));
            MARK_BLOCK_USED(i+startBlock);
        }
        DEBUGMSG(0,(TEXT("returned value is 0x%x\r\n"),(HLOCAL) (pool + (startBlock * BLOCK_SIZE) + BLOCK_COUNT_SIZE)));
        return (HLOCAL) (pool + (startBlock * BLOCK_SIZE) + BLOCK_COUNT_SIZE);
    }
}
Address _allocateBlock(const size_t blockSize) {
	TRACE_FLOW("(%lu)", blockSize);
	int createOkay = _createBlock(blockSize);
	if (createOkay != 0) {
		return 0;
	}
	// we will get the first one
	Address firstBlockAddress = GET_FIRST_BLOCK_ADDRESS(blockSize);
	Address nextBlockAddress = GET_ADDRESS_OF_FOLLOWING_SIBLING(firstBlockAddress);
	// remove it from the list
	_removeBlockFromList(firstBlockAddress, blockSize);
	// set new first block
	WRITE_FIRST_BLOCK_ADDRESS(nextBlockAddress, blockSize);
	// mark it as used
	MARK_BLOCK_USED(firstBlockAddress);
	// and return it
	return firstBlockAddress;
}