char * direct_dbg_strdup( const char* file, int line, const char *func, const char *string ) { void *mem; unsigned long *val; size_t bytes = string ? direct_strlen( string ) + 1 : 1; D_DEBUG_AT( Direct_Mem, " +"_ZUn(6)" bytes [%s:%d in %s()] <- \"%30s\"\n", bytes, file, line, func, string ); if (direct_config->debugmem) { MemDesc *desc; mem = direct_malloc( bytes + sizeof(MemDesc) ); D_DEBUG_AT( Direct_Mem, " '-> %p\n", mem ); if (!mem) return NULL; desc = fill_mem_desc( mem, bytes, func, file, line, direct_trace_copy_buffer(NULL) ); direct_mutex_lock( &alloc_lock ); direct_hash_insert( &alloc_hash, (unsigned long) desc->mem, desc ); direct_mutex_unlock( &alloc_lock ); if (string) direct_memcpy( desc->mem, string, bytes ); else *(u8*)desc->mem = 0; return desc->mem; } mem = direct_malloc( bytes + DISABLED_OFFSET ); D_DEBUG_AT( Direct_Mem, " '-> %p\n", mem ); if (!mem) return NULL; val = mem; val[0] = ~0; if (string) direct_memcpy( (char*) mem + DISABLED_OFFSET, string, bytes ); else *((u8*)mem + DISABLED_OFFSET) = 0; return (char*) mem + DISABLED_OFFSET; }
void * direct_dbg_malloc( const char* file, int line, const char *func, size_t bytes ) { void *mem; unsigned long *val; D_DEBUG_AT( Direct_Mem, " +"_ZUn(6)" bytes [%s:%d in %s()]\n", bytes, file, line, func ); if (direct_config->debugmem) { MemDesc *desc; mem = direct_malloc( bytes + sizeof(MemDesc) ); D_DEBUG_AT( Direct_Mem, " '-> %p\n", mem ); if (!mem) return NULL; desc = fill_mem_desc( mem, bytes, func, file, line, direct_trace_copy_buffer(NULL) ); direct_mutex_lock( &alloc_lock ); direct_hash_insert( &alloc_hash, (unsigned long) desc->mem, desc ); direct_mutex_unlock( &alloc_lock ); return desc->mem; } mem = direct_malloc( bytes + DISABLED_OFFSET ); if (!mem) return NULL; D_DEBUG_AT( Direct_Mem, " '-> %p\n", mem ); val = mem; val[0] = ~0; return (char*) mem + DISABLED_OFFSET; }
DirectResult direct_print( char *buf, size_t size, const char *format, va_list args, char **ret_ptr ) { int len = 1; *ret_ptr = buf; if (buf) { buf[0] = 0; #ifdef __GNUC__ va_list args_copy; va_copy( args_copy, args ); len = direct_vsnprintf( buf, size, format, args_copy ); va_end( args_copy ); #else len = direct_vsnprintf( buf, size, format, args ); #endif if (len < 0) return DR_FAILURE; } else size = 0; if (len >= (int) size) { char *ptr = buf; ptr = direct_malloc( len+1 ); if (!ptr) return DR_NOLOCALMEMORY; len = direct_vsnprintf( ptr, len+1, format, args ); if (len < 0) { direct_free( ptr ); return DR_FAILURE; } *ret_ptr = ptr; } return DR_OK; }
String & String::PrintF( const char *format, va_list args, size_t stack_buffer ) { size_t len; char buf[stack_buffer]; char *ptr = buf; D_ASSERT( format != NULL ); // TODO: check if va_copy is required here #ifdef __GNUC__ va_list ap2; va_copy( ap2, args ); len = direct_vsnprintf( buf, sizeof(buf), format, ap2 ); va_end( ap2 ); #else len = direct_vsnprintf( buf, sizeof(buf), format, args ); #endif if (len < 0) return *this; if (len >= sizeof(buf)) { ptr = (char*) direct_malloc( len+1 ); if (!ptr) { D_OOM(); return *this; } len = direct_vsnprintf( ptr, len+1, format, args ); if (len < 0) { direct_free( ptr ); return *this; } } str.append( ptr ); if (ptr != buf) direct_free( ptr ); return *this; }