Пример #1
0
void *malloc(uint64_t size)
{
	int index;
	void *ptr;
	struct boundary_tag *tag = NULL;

	liballoc_lock();

		if ( l_initialized == 0 )
		{
			for ( index = 0; index < MAXEXP; index++ )
			{
				l_freePages[index] = NULL;
				l_completePages[index] = 0;
			}
			l_initialized = 1;
		}

		index = getexp( size ) + MODE;
		if ( index < MINEXP ) index = MINEXP;


		// Find one big enough.
			tag = l_freePages[ index ];				// Start at the front of the list.
			while ( tag != NULL )
			{
					// If there's enough space in this tag.
				if ( (tag->real_size - sizeof(struct boundary_tag))
								>= (size + sizeof(struct boundary_tag) ) )
				{
					break;
				}

				tag = tag->next;
			}


			// No page found. Make one.
			if ( tag == NULL )
			{
				if ( (tag = allocate_new_tag( size )) == NULL )
				{
					liballoc_unlock();
					return NULL;
				}

				index = getexp( tag->real_size - sizeof(struct boundary_tag) );
			}
			else
			{
				remove_tag( tag );

				if ( (tag->split_left == NULL) && (tag->split_right == NULL) )
					l_completePages[ index ] -= 1;
			}

		// We have a free page.  Remove it from the free pages list.

		tag->size = size;

		// Removed... see if we can re-use the excess space.

		unsigned int remainder = tag->real_size - size - sizeof( struct boundary_tag ) * 2; // Support a new tag + remainder

		if ( ((int)(remainder) > 0) /*&& ( (tag->real_size - remainder) >= (1<<MINEXP))*/ )
		{
			int childIndex = getexp( remainder );

			if ( childIndex >= 0 )
			{
				struct boundary_tag *new_tag = split_tag( tag );

				new_tag = new_tag;	// Get around the compiler warning about unused variables.
			}
		}



	ptr = (void*)((unsigned int)tag + sizeof( struct boundary_tag ) );

	liballoc_unlock();
	return ptr;
}
Пример #2
0
void *malloc(size_t size)
{
	int index;
	void *ptr;
	struct boundary_tag *tag = NULL;

	liballoc_lock();

		if ( l_initialized == 0 )
		{
			#ifdef DEBUG
			printf("%s\n","liballoc initializing.");
			#endif
			for ( index = 0; index < MAXEXP; index++ )
			{
				l_freePages[index] = NULL;
				l_completePages[index] = 0;
			}
			l_initialized = 1;
		}

		index = getexp( size ) + MODE;
		if ( index < MINEXP ) index = MINEXP;


		// Find one big enough.
			tag = l_freePages[ index ];				// Start at the front of the list.
			while ( tag != NULL )
			{
					// If there's enough space in this tag.
				if ( (tag->real_size - sizeof(struct boundary_tag))
								>= (size + sizeof(struct boundary_tag) ) )
				{
					#ifdef DEBUG
					printf("Tag search found %i >= %i\n",(tag->real_size - sizeof(struct boundary_tag)), (size + sizeof(struct boundary_tag) ) );
					#endif
					break;
				}

				tag = tag->next;
			}


			// No page found. Make one.
			if ( tag == NULL )
			{
				if ( (tag = allocate_new_tag( size )) == NULL )
				{
					liballoc_unlock();
					return NULL;
				}

				index = getexp( tag->real_size - sizeof(struct boundary_tag) );
			}
			else
			{
				remove_tag( tag );

				if ( (tag->split_left == NULL) && (tag->split_right == NULL) )
					l_completePages[ index ] -= 1;
			}

		// We have a free page.  Remove it from the free pages list.

		tag->size = size;

		// Removed... see if we can re-use the excess space.

		#ifdef DEBUG
		printf("Found tag with %i bytes available (requested %i bytes, leaving %i), which has exponent: %i (%i bytes)\n", tag->real_size - sizeof(struct boundary_tag), size, tag->real_size - size - sizeof(struct boundary_tag), index, 1<<index );
		#endif

		unsigned int remainder = tag->real_size - size - sizeof( struct boundary_tag ) * 2; // Support a new tag + remainder

		if ( ((int)(remainder) > 0) /*&& ( (tag->real_size - remainder) >= (1<<MINEXP))*/ )
		{
			int childIndex = getexp( remainder );

			if ( childIndex >= 0 )
			{
				#ifdef DEBUG
				printf("Seems to be splittable: %i >= 2^%i .. %i\n", remainder, childIndex, (1<<childIndex) );
				#endif

				struct boundary_tag *new_tag = split_tag( tag );

				new_tag = new_tag;	// Get around the compiler warning about unused variables.

				#ifdef DEBUG
				printf("Old tag has become %i bytes, new tag is now %i bytes (%i exp)\n", tag->real_size, new_tag->real_size, new_tag->index );
				#endif
			}
		}



	ptr = (void*)((unsigned int)tag + sizeof( struct boundary_tag ) );



	#ifdef DEBUG
	l_inuse += size;
	printf("malloc: %x,  %i, %i\n", ptr, (int)l_inuse / 1024, (int)l_allocated / 1024 );
	dump_array();
	#endif


	liballoc_unlock();
	return ptr;
}