Esempio n. 1
0
/**
 *  Insert a formatted representation of the %arena onto the output stream 'o'.
 */
void Arena::insert(std::ostream& o) const
{
 /* Recurse through the list of arenas that runs through the parent attribute,
    building up a name of the form 'root/.../parent-arena/arena' in the string
    from which we inherit. Note that this list is short - no more than a dozen
    links, at most - and that each  recursive call pushes just two pointers on
    the stack, so the consumption of stack space is minimal...*/

    struct pathname : std::string
    {
        void traverse(const Arena& arena)                // Build up the name
        {
            if (ArenaPtr p = arena.parent())             // Has a parent arena?
            {
                traverse(*p);                            // ...traverse parent
                *this += '/';                            // ...add a delimiter
            }

            *this += arena.name();                       // Append arena name
        }

        pathname(const Arena& arena) {traverse(arena);}  // Traverse ancestors
    };

    o <<  "name=\""      << pathname(*this) << '"'       // Emit path name
      << ",available="   << bytes_t (available())        // Emit available()
      << ",allocated="   << bytes_t (allocated())        // Emit allocated()
      << ",peakusage="   << bytes_t (peakusage())        // Emit peakusage()
      << ",allocations=" << size_t  (allocations());     // Emit allocations()
}
Esempio n. 2
0
void MemoryAllocatorTrace::exit (void)
{
    check_allocations();

	_alloc_recording = false;
    
	LOG_MESSAGE << "---- MEMORY DUMP -------------------------------------------------------------";
	LOG_MESSAGE << "Total Allocations:   " << _total_allocs << " bytes (" << _total_allocs/(1024.0F*1024.0F) << " MB)";
	LOG_MESSAGE << "Peak Allocations:    " << _peak_allocs << " bytes (" << _peak_allocs/(1024.0F*1024.0F) << " MB)";
	LOG_MESSAGE << "Current Allocations: " << _current_allocs << " bytes (" << _current_allocs/(1024.0F*1024.0F) << " MB)";

    //
    // Named objects
    //

    std::multimap<char *, Allocation*, std::less<char *>> grouped;

	LOG_MESSAGE << "Named objects leaked: ";
    FOR_EACH (i,allocations()) {
	    if (i->second._name) {
            grouped.insert(std::make_pair(i->second._name, &(i->second)));
		}
	}	
	
	for (auto grouped_i = grouped.begin(); grouped_i != grouped.end(); grouped_i = grouped.upper_bound(grouped_i->first) ) {
		
		auto lower = grouped.lower_bound(grouped_i->first);
		auto upper = grouped.upper_bound(grouped_i->first);

        DTuint count = 0;
        DTsize size = 0;
		for (auto grouped_j = lower; grouped_j != upper; ++grouped_j) {
            ++count;
            size += grouped_j->second->_size;
		}	
	
        LOG_MESSAGE << " Kind " << grouped_i->first <<   "   Num " << count << "  Total Size: " << size;
	}

    //
    // Unnamed objects
    //

	LOG_MESSAGE << "Unnamed objects leaked: ";
    
    std::multimap<DTuint, Allocation*, std::greater<DTuint>> ordered;
    FOR_EACH (i,allocations()) {
	    if (!i->second._name) {
            ordered.insert(std::make_pair(i->second._size, &(i->second)));
        }
	}
    
	for (auto ordered_i = ordered.begin(); ordered_i != ordered.end(); ordered_i = ordered.upper_bound(ordered_i->first) ) {
		
		auto lower = ordered.lower_bound(ordered_i->first);
		auto upper = ordered.upper_bound(ordered_i->first);

        DTuint count = 0;
		for (auto ordered_j = lower; ordered_j != upper; ++ordered_j) {
            ++count;
		}	
	
        LOG_MESSAGE << " Num bytes " << ordered_i->first <<   "   Num " << count;
	}
    
}