Пример #1
0
void
writeLog(void* drcontext){
	char logname[MAXIMUM_PATH];
	char *dirsep;
    	int len;
	len = dr_snprintf(logname, sizeof(logname)/sizeof(logname[0]),
                      "%s", dr_get_client_path(client_id));
	DR_ASSERT(len > 0);
	for (dirsep = logname + len; *dirsep != '/'; dirsep--)
        DR_ASSERT(dirsep > logname);
    	len = dr_snprintf(dirsep + 1,
                      (sizeof(logname) - (dirsep - logname))/sizeof(logname[0]),
                      "floatingpoint.%d.log", dr_get_thread_id(drcontext));
    	DR_ASSERT(len > 0);
    	NULL_TERMINATE(logname);
    	logF = dr_open_file(logname, 
                             DR_FILE_WRITE_OVERWRITE | DR_FILE_ALLOW_LARGE);
    	DR_ASSERT(logF != INVALID_FILE);
    	dr_log(drcontext, LOG_ALL, 1, 
           "floating point: log for thread %d is fp.%03d\n",
           dr_get_thread_id(drcontext), dr_get_thread_id(drcontext));
	#ifdef SHOW_RESULTS
    	if (dr_is_notify_on()) {
//        	dr_fprintf(STDERR, "<floating point instruction operands for thread %d in %s>\n",
//                  dr_get_thread_id(drcontext), logname);
    	}
	#endif	
	thread_id_for_log = dr_get_thread_id(drcontext);
}
Пример #2
0
static void
event_thread_init(void *drcontext)
{
    if (main_thread == 0)
        main_thread = dr_get_thread_id(drcontext);
    drmgr_set_tls_field(drcontext, tls_idx,
                        (void *)(ptr_int_t)dr_get_thread_id(drcontext));
}
Пример #3
0
<client_name>_thread_exit(void *drcontext){
	per_thread_t * data;
	data = drmgr_get_tls_field(drcontext, tls_index);
	dr_thread_free(drcontext, data, sizeof(per_thread_t));
	DEBUG_PRINT("%s - exiting thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));

}
Пример #4
0
void
instrace_thread_exit(void *drcontext)
{
    per_thread_t *data;
	int i;

	if (client_arg->instrace_mode == INS_TRACE){
		ins_trace(drcontext);
	}

    data = drmgr_get_tls_field(drcontext, tls_index);
    dr_mutex_lock(mutex);
    num_refs += data->num_refs;
    dr_mutex_unlock(mutex);

    dr_close_file(data->outfile);
	if (log_mode){
		dr_close_file(data->logfile);
	}

	dr_thread_free(drcontext, data->buf_base, INSTR_BUF_SIZE);
	dr_thread_free(drcontext, data->output_array, OUTPUT_BUF_SIZE);

	DEBUG_PRINT("%s - thread id : %d, cloned instructions freeing now - %d\n",ins_pass_name, dr_get_thread_id(drcontext),data->static_ptr);

	for(i=0 ; i<data->static_ptr; i++){
		instr_destroy(dr_get_current_drcontext(),data->static_array[i]);
	}

	dr_thread_free(drcontext, data->static_array, sizeof(instr_t *)*client_arg->static_info_size);
    dr_thread_free(drcontext, data, sizeof(per_thread_t));

	DEBUG_PRINT("%s - exiting thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));

}
Пример #5
0
static void
event_thread_context_exit(void *drcontext, bool thread_exit)
{
    if (!thread_exit && dr_get_thread_id(drcontext) != main_thread) {
#if VERBOSE
        dr_fprintf(STDERR, "  non-main thread exiting callback depth=%d cls=%d\n",
                   cb_depth, (int)(ptr_int_t) drmgr_get_cls_field(drcontext, cls_idx));
#endif
        CHECK(drmgr_get_cls_field(drcontext, cls_idx) ==
              (void *)(ptr_int_t)cb_depth,
              "cls not preserved");
        cb_depth--;
        CHECK(drmgr_get_tls_field(drcontext, tls_idx) ==
              (void *)(ptr_int_t)dr_get_thread_id(drcontext), "tls not preserved");
    }
}
Пример #6
0
static void
event_thread_init(void *drcontext)
{
    if (main_thread == 0)
        main_thread = dr_get_thread_id(drcontext);
    drmgr_set_tls_field(drcontext, tls_idx,
                        (void *)(ptr_int_t)dr_get_thread_id(drcontext));
    if (!in_event_thread_init) {
        dr_mutex_lock(threadlock);
        if (!in_event_thread_init) {
            dr_fprintf(STDERR, "in event_thread_init\n");
            in_event_thread_init = true;
        }
        dr_mutex_unlock(threadlock);
    }
}
Пример #7
0
/* event_bb_insert calls necessary functions to fill up the static info about an instruction and 
   to instrument memory instructions to get its runtime address using dynamic instrumentation
 */
dr_emit_flags_t
instrace_bb_instrumentation(void *drcontext, void *tag, instrlist_t *bb,
                instr_t *instr, bool for_trace, bool translating,
                void *user_data)
{
   /* algorithm
	  1. First we need to filter the instructions to instrument 
	  2. call the static info filler function to get a slot at the global instruction array
      3. send the data appropriately to instrumentation function
	*/
	instr_t * instr_info;
	module_data_t * md;
	uint offset = 0;
	per_thread_t * data;
	

	/* these are for the use of the caller - instrlist_first(bb) */
	if(filter_from_list(head,instr,client_arg->filter_mode) && should_filter_thread(dr_get_thread_id(drcontext))){
			//dr_printf("entering static instrumentation\n");
			instr_info = static_info_instrumentation(drcontext, instr);
			if(instr_info != NULL){ 
				//can only be entered in the DISASSEMBLY_TRACE or INS_TRACE
				DR_ASSERT(client_arg->instrace_mode == INS_TRACE || client_arg->instrace_mode == DISASSEMBLY_TRACE);
				dynamic_info_instrumentation(drcontext, bb, instr, instr_info);
			}
			//instrlist_disassemble(drcontext, tag, bb, logfile);
	}


	return DR_EMIT_DEFAULT;
			
}
Пример #8
0
static void
event_thread_exit(void *drcontext)
{
    CHECK(drmgr_get_tls_field(drcontext, tls_idx) ==
          (void *)(ptr_int_t)dr_get_thread_id(drcontext),
          "tls not preserved");
}
Пример #9
0
/* callbacks for threads */
void <client_name>_thread_init(void *drcontext){
	per_thread_t * data;

	DEBUG_PRINT("%s - initializing thread %d\n", ins_pass_name, dr_get_thread_id(drcontext));
	data = dr_thread_alloc(drcontext, sizeof(per_thread_t));
	drmgr_set_tls_field(drcontext, tls_index, data);

}
Пример #10
0
static void
event_thread_context_init(void *drcontext, bool new_depth)
{
    if (dr_get_thread_id(drcontext) != main_thread) {
        cb_depth++;
#if VERBOSE
        /* # cbs differs on xp vs win7 so not part of output */
        dr_fprintf(STDERR, "non-main thread entering callback depth=%d\n", cb_depth);
#endif
        CHECK(new_depth || drmgr_get_cls_field(drcontext, cls_idx) ==
              (void *)(ptr_int_t)cb_depth,
              "not re-using prior callback value");
        drmgr_set_cls_field(drcontext, cls_idx, (void *)(ptr_int_t)cb_depth);
        CHECK(drmgr_get_tls_field(drcontext, tls_idx) ==
              (void *)(ptr_int_t)dr_get_thread_id(drcontext), "tls not preserved");
    }
}
Пример #11
0
static void
event_thread_init(void *drcontext)
{
    per_thread_t *data;
    static volatile int thread_count;

    if (options.native_until_thread > 0) {
        int local_count = dr_atomic_add32_return_sum(&thread_count, 1);
        NOTIFY(1, "@@@@@@@@@@@@@ new thread #%d "TIDFMT"\n",
               local_count, dr_get_thread_id(drcontext));
        if (go_native && local_count == options.native_until_thread) {
            void **drcontexts = NULL;
            uint num_threads, i;
            go_native = false;
            NOTIFY(1, "thread "TIDFMT" suspending all threads\n",
                   dr_get_thread_id(drcontext));
            if (dr_suspend_all_other_threads_ex(&drcontexts, &num_threads, NULL,
                                                DR_SUSPEND_NATIVE)) {
                NOTIFY(1, "suspended %d threads\n", num_threads);
                for (i = 0; i < num_threads; i++) {
                    if (dr_is_thread_native(drcontexts[i])) {
                        NOTIFY(2, "\txxx taking over thread #%d "TIDFMT"\n",
                               i, dr_get_thread_id(drcontexts[i]));
                        dr_retakeover_suspended_native_thread(drcontexts[i]);
                    } else {
                        NOTIFY(2, "\tthread #%d "TIDFMT" under DR\n",
                               i, dr_get_thread_id(drcontexts[i]));
                    }
                }
                if (!dr_resume_all_other_threads(drcontexts, num_threads)) {
                    ASSERT(false, "failed to resume threads");
                }
            } else {
                ASSERT(false, "failed to suspend threads");
            }
        }

    }
    /* allocate thread private data for per-thread cache */
    if (drcov_per_thread)
        data = thread_data_create(drcontext);
    else
        data = thread_data_copy(drcontext);
    drmgr_set_tls_field(drcontext, tls_idx, data);
}
Пример #12
0
static void
umbra_client_thread_init(void *drcontext, umbra_info_t *umbra_info)
{
    client_tls_data_t *tls_data;

    /* allocate client tls data */
    tls_data = dr_thread_alloc(drcontext, sizeof(client_tls_data_t));
    umbra_info->client_tls_data = tls_data;
    tls_data->tid = dr_get_thread_id(drcontext);
}
Пример #13
0
static void
check_tls_write_from_cache(void)
{
    void *drcontext = dr_get_current_drcontext();
    CHECK(drmgr_get_tls_field(drcontext, tls_idx) == (void *) MAGIC_NUMBER_FROM_CACHE,
          "cls write from cache incorrect");
    /* now restore */
    drmgr_set_tls_field(drcontext, tls_idx,
                        (void *)(ptr_int_t)dr_get_thread_id(drcontext));
    checked_tls_write_from_cache = true;
}
Пример #14
0
void
funcwrap_thread_exit(void *drcontext){
	per_thread_t * data;
	data = drmgr_get_tls_field(drcontext, tls_index);
	if (log_mode){
		dr_close_file(data->logfile);
	}
	dr_thread_free(drcontext, data, sizeof(per_thread_t));

	DEBUG_PRINT("%s - exiting thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));

}
Пример #15
0
dr_emit_flags_t
funcwrap_bb_instrumentation(void *drcontext, void *tag, instrlist_t *bb,
instr_t *instr, bool for_trace, bool translating,
void *user_data)
{

	instr_t * first = instrlist_first(bb);
	app_pc pc = instr_get_app_pc(first);
	module_data_t * module_data;
	per_thread_t * data = drmgr_get_tls_field(dr_get_current_drcontext(), tls_index);
	module_t * md;
	app_pc offset;
	
	
	if (instr != first || data->nesting != 0){
		return DR_EMIT_DEFAULT;
	}

	module_data = dr_lookup_module(pc);
	data = drmgr_get_tls_field(drcontext, tls_index);

	
	if (module_data != NULL){
		md = md_lookup_module(head, module_data->full_path);
		if (md != NULL){
			offset = pc - module_data->start;
			
			for (int i = 1; i <= md->bbs[0].start_addr; i++){
				if (offset == md->bbs[i].start_addr){
					DEBUG_PRINT("bb instrumenting function\n");
					data->filter_func = true;
					dr_insert_clean_call(drcontext, bb, instr, clean_call, false, 1, OPND_CREATE_INTPTR(instr_get_app_pc(instr)));
					wrap_thread_id = dr_get_thread_id(drcontext);
					DEBUG_PRINT("done bb instrumenting function\n");

				}
			}
		}
	}

	

	/*if (data->filter_func){
		instrlist_disassemble(drcontext, instr_get_app_pc(instrlist_first(bb)), bb, logfile);
	}*/

	dr_free_module_data(module_data);


	return DR_EMIT_DEFAULT;

}
Пример #16
0
void handle_thread_exit(void* ctx) {
  thread_id_t thread_id;
  struct trace_buffer_t* tb;

  check_ctx(ctx, "handle_thread_exit");
  thread_id = dr_get_thread_id(ctx);
  dr_fprintf(STDERR,
             "info: cleaning up thread 0x%" PRIx64 "..\n",
             (uint64_t)thread_id);
  tb = dr_get_tls_field(ctx);
  tb_delete(tb);
  dr_set_tls_field(ctx, NULL);
}
Пример #17
0
static void
event_thread_init(void *drcontext)
{
    /* create an instance of our data structure for this thread */
    per_thread_t *data = (per_thread_t *)dr_thread_alloc(drcontext, sizeof(per_thread_t));
    /* store it in the slot provided in the drcontext */
    drmgr_set_tls_field(drcontext, tls_idx, data);
    data->num_direct_calls = 0;
    data->num_indirect_calls = 0;
    data->num_returns = 0;
    dr_log(drcontext, DR_LOG_ALL, 1, "countcalls: set up for thread " TIDFMT "\n",
           dr_get_thread_id(drcontext));
}
Пример #18
0
static void
event_thread_context_exit(void *drcontext, bool thread_exit)
{
#ifdef SHOW_RESULTS
    dr_fprintf(STDERR, "resuming prior thread context id="TIDFMT"\n",
               dr_get_thread_id(drcontext));
#endif
    if (thread_exit) {
        per_thread_t *data = (per_thread_t *) drmgr_get_cls_field(drcontext, tcls_idx);
        dr_thread_free(drcontext, data, sizeof(per_thread_t));
    }
    /* else, nothing to do: we leave the struct for re-use on next context */
}
Пример #19
0
void handle_thread_init(void* ctx) {
  thread_id_t thread_id;
  struct trace_buffer_t* tb;

  check_ctx(ctx, "handle_thread_init");
  thread_id = dr_get_thread_id(ctx);
  dr_fprintf(STDERR,
             "info: initializing thread 0x%" PRIx64 "..\n",
             (uint64_t)thread_id);
  tb = tb_create(thread_id);
  dr_set_tls_field(ctx, tb);
  tb_tlv(tb, TYPE_TRACE);
}
Пример #20
0
static void
event_thread_exit(void *drcontext)
{
    CHECK(drmgr_get_tls_field(drcontext, tls_idx) ==
          (void *)(ptr_int_t)dr_get_thread_id(drcontext),
          "tls not preserved");
    if (!in_event_thread_exit) {
        dr_mutex_lock(threadlock);
        if (!in_event_thread_exit) {
            dr_fprintf(STDERR, "in event_thread_exit\n");
            in_event_thread_exit = true;
        }
        dr_mutex_unlock(threadlock);
    }
}
Пример #21
0
/* callbacks for threads */
void funcwrap_thread_init(void *drcontext){
	
	per_thread_t * data;
	char logfilename[MAX_STRING_LENGTH];
	char thread_id[MAX_STRING_LENGTH];

	DEBUG_PRINT("%s - initializing thread %d\n", ins_pass_name, dr_get_thread_id(drcontext));
	
	data = dr_thread_alloc(drcontext, sizeof(per_thread_t));
	if (log_mode){
		dr_snprintf(thread_id, MAX_STRING_LENGTH, "%d", dr_get_thread_id(drcontext));
		populate_conv_filename(logfilename, logdir, ins_pass_name, thread_id);
		data->logfile = dr_open_file(logfilename, DR_FILE_WRITE_OVERWRITE);
	}

	

	data->filter_func = false;
	data->nesting = 0;
	drmgr_set_tls_field(drcontext, tls_index, data);

	DEBUG_PRINT("%s - initializing thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));

}
Пример #22
0
static void
event_thread_context_init(void *drcontext, bool new_depth)
{
    /* create an instance of our data structure for this thread context */
    per_thread_t *data;
#ifdef SHOW_RESULTS
    dr_fprintf(STDERR, "new thread context id="TIDFMT"%s\n", dr_get_thread_id(drcontext),
               new_depth ? " new depth" : "");
#endif
    if (new_depth) {
        data = (per_thread_t *) dr_thread_alloc(drcontext, sizeof(per_thread_t));
        drmgr_set_cls_field(drcontext, tcls_idx, data);
    } else
        data = (per_thread_t *) drmgr_get_cls_field(drcontext, tcls_idx);
    memset(data, 0, sizeof(*data));
}
Пример #23
0
void tb_flush(struct trace_buffer_t* tb) {
  size_t size;
  int64 pos;
  size_t written;
  void* aligned_current;

  tb_tlv_complete(tb);

  // Align current position to block boundary.
  aligned_current = aligned_block(tb->current);
  memset(tb->current, 'X', aligned_current - tb->current);
  tb->current = aligned_current;

  size = tb->current - (void*)&tb->block;
  if(size == sizeof(struct block_t)) {
    // Nothing to do.
    return;
  }
  tb->block.length = (uint32_t)size;
  tb->block.crc32 = 0;
  tb->block.crc32 = crc32((char*)&tb->block, size);

  // Write data.
  dr_mutex_lock(tb->mutex);
  pos = dr_file_tell(tb->file);
  if(pos == -1) {
    dr_fprintf(STDERR, "fatal: dr_file_tell() failed\n");
    dr_exit_process(1);
  }
  dr_fprintf(STDERR,
             "info: flushing tb=%p file-offset=%" PRId64 " size=%u"
             " tb-thread=0x%" PRIx64 " current-thread=0x%" PRIx64 "\n",
             tb,
             pos,
             (unsigned int)size,
             tb->block.thread_id,
             (uint64_t)dr_get_thread_id(dr_get_current_drcontext()));
  written = dr_write_file(tb->file, &tb->block, size);
  dr_mutex_unlock(tb->mutex);
  if(written != size) {
    dr_fprintf(STDERR, "fatal: dr_write_file() failed\n");
    dr_exit_process(1);
  }

  // Reset position.
  tb->current = tb + 1;
}
Пример #24
0
void memtrace_thread_exit(void *drcontext)
{
    per_thread_t *data;

    memtrace(drcontext);
    data = drmgr_get_tls_field(drcontext, tls_index);
    dr_mutex_lock(mutex);
    num_refs += data->num_refs;
    dr_mutex_unlock(mutex);
	if (log_mode){
		dr_close_file(data->logfile);
	}
	dr_close_file(data->outfile);
    dr_thread_free(drcontext, data->buf_base, MEM_BUF_SIZE);
    dr_thread_free(drcontext, data, sizeof(per_thread_t));

	DEBUG_PRINT("%s - exiting thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));
}
Пример #25
0
/****************************************************************************
 * Utility Functions
 */
static file_t
log_file_create_helper(void *drcontext, const char *suffix, char *buf, size_t buf_els)
{
    file_t log =
        drx_open_unique_appid_file(options.logdir, drcontext == NULL ?
                                   dr_get_process_id() : dr_get_thread_id(drcontext),
                                   "drcov", suffix,
#ifndef WINDOWS
                                   DR_FILE_CLOSE_ON_FORK |
#endif
                                   DR_FILE_ALLOW_LARGE,
                                   buf, buf_els);
    if (log != INVALID_FILE) {
        dr_log(drcontext, DR_LOG_ALL, 1, "drcov: log file is %s\n", buf);
        NOTIFY(1, "<created log file %s>\n", buf);
    }
    return log;
}
Пример #26
0
static void 
event_thread_exit(void *drcontext)
{
    per_thread_t *data = (per_thread_t *) dr_get_tls_field(drcontext);
    char msg[512];
    int len;

    len = dr_snprintf(msg, sizeof(msg)/sizeof(msg[0]),
                      "Thread %d exited - ", dr_get_thread_id(drcontext));
    DR_ASSERT(len > 0);
    NULL_TERMINATE(msg);

    /* display thread private counts data */
    display_results(data, msg);

    /* clean up memory */
    dr_thread_free(drcontext, data, sizeof(per_thread_t));
}
Пример #27
0
void instrace_thread_init(void *drcontext)
{
    char outfilename[MAX_STRING_LENGTH];
	char logfilename[MAX_STRING_LENGTH];
	char thread_id[MAX_STRING_LENGTH];
	char extra_info[MAX_STRING_LENGTH];

    char *dirsep;
    int len;
    per_thread_t *data;
	char * mode;

	uint * stack_base;
	uint * deallocation_stack;

	DEBUG_PRINT("%s - initializing thread %d\n", ins_pass_name, dr_get_thread_id(drcontext));

    /* allocate thread private data */
    data = dr_thread_alloc(drcontext, sizeof(per_thread_t));
    drmgr_set_tls_field(drcontext, tls_index, data);
    data->buf_base = dr_thread_alloc(drcontext, INSTR_BUF_SIZE);
    data->buf_ptr  = data->buf_base;
    /* set buf_end to be negative of address of buffer end for the lea later */
	data->buf_end  = -(ptr_int_t)(data->buf_base + INSTR_BUF_SIZE);
    data->num_refs = 0;

    /* We're going to dump our data to a per-thread file.
     * On Windows we need an absolute path so we place it in
     * the same directory as our library. We could also pass
     * in a path and retrieve with dr_get_options().
     */
	dr_snprintf(thread_id, MAX_STRING_LENGTH, "%d", dr_get_thread_id(drcontext));
	if (log_mode){
		populate_conv_filename(logfilename, logdir, ins_pass_name, thread_id);
		data->logfile = dr_open_file(logfilename, DR_FILE_WRITE_OVERWRITE | DR_FILE_ALLOW_LARGE);
	}

	/* instrace types */
	if (client_arg->instrace_mode == OPERAND_TRACE){
		mode = "opnd";
	}
	else if (client_arg->instrace_mode == OPCODE_TRACE){
		mode = "opcode";
	}
	else if (client_arg->instrace_mode == DISASSEMBLY_TRACE){
		mode = "disasm";
	}
	else if (client_arg->instrace_mode == INS_DISASM_TRACE){
		mode = "asm_instr";
	}
	else{
		mode = "instr";
	}
	
	

	dr_snprintf(extra_info, MAX_STRING_LENGTH, "%s_%s_%s", client_arg->extra_info, mode, thread_id);

	populate_conv_filename(outfilename, client_arg->output_folder, ins_pass_name, extra_info);
	data->outfile = dr_open_file(outfilename, DR_FILE_WRITE_OVERWRITE | DR_FILE_ALLOW_LARGE);
	DR_ASSERT(data->outfile != INVALID_FILE);

	DEBUG_PRINT("%s - thread id : %d, new thread logging at - %s\n",ins_pass_name, dr_get_thread_id(drcontext),logfilename);

	data->static_array = (instr_t **)dr_thread_alloc(drcontext,sizeof(instr_t *)*client_arg->static_info_size);
	data->static_array_size = client_arg->static_info_size;
	data->static_ptr = 0;

	data->output_array = (output_t *)dr_thread_alloc(drcontext,OUTPUT_BUF_SIZE);

	deallocation_stack = &data->deallocation_stack;
	stack_base = &data->stack_base;

	__asm{
		mov EAX, FS : [0x04]
		mov EBX, stack_base
		mov [EBX], EAX
		mov EAX, FS : [0xE0C]
		mov EBX, deallocation_stack
		mov [EBX], EAX
	}

	DEBUG_PRINT("%s - thread %d stack information - stack_base %x stack_reserve %x\n", ins_pass_name,
		dr_get_thread_id(drcontext), data->stack_base, data->deallocation_stack);

	DEBUG_PRINT("%s - initializing thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));


}
Пример #28
0
void memtrace_thread_init(void *drcontext)
{
    char logfilename[MAX_STRING_LENGTH];
	char outfilename[MAX_STRING_LENGTH];
	char thread_id[MAX_STRING_LENGTH];
	char extra_info[MAX_STRING_LENGTH];

    char *dirsep;
    int len;
    per_thread_t *data;

	uint * stack_base;
	uint * deallocation_stack;

	int i = 0;

	DEBUG_PRINT("%s - initializing thread %d\n", ins_pass_name, dr_get_thread_id(drcontext));

    /* allocate thread private data */
    data = dr_thread_alloc(drcontext, sizeof(per_thread_t));
    drmgr_set_tls_field(drcontext, tls_index, data);
    data->buf_base = dr_thread_alloc(drcontext, MEM_BUF_SIZE);
    data->buf_ptr  = data->buf_base;
    /* set buf_end to be negative of address of buffer end for the lea later */
    data->buf_end  = -(ptr_int_t)(data->buf_base + MEM_BUF_SIZE);
    data->num_refs = 0;

    /* We're going to dump our data to a per-thread file.
     * On Windows we need an absolute path so we place it in
     * the same directory as our library. We could also pass
     * in a path and retrieve with dr_get_options().
     */

	dr_snprintf(thread_id, MAX_STRING_LENGTH, "%d", dr_get_thread_id(drcontext));

	if (log_mode){
		populate_conv_filename(logfilename, logdir, ins_pass_name, thread_id);
		data->logfile = dr_open_file(logfilename, DR_FILE_WRITE_OVERWRITE | DR_FILE_ALLOW_LARGE);
	}



	dr_snprintf(extra_info, MAX_STRING_LENGTH, "%s_%s", client_arg->extra_info, thread_id);

	populate_conv_filename(outfilename, client_arg->output_folder, ins_pass_name, extra_info);
	data->outfile = dr_open_file(outfilename, DR_FILE_WRITE_OVERWRITE | DR_FILE_ALLOW_LARGE);
	DR_ASSERT(data->outfile != INVALID_FILE);

	/* this is done for 32 bit applications */
	deallocation_stack = &data->stack_limit;
	stack_base = &data->stack_base;

	__asm{
			mov EAX, FS : [0x04]
			mov EBX, stack_base
			mov[EBX], EAX
			mov EAX, FS : [0xE0C]
			mov EBX, deallocation_stack
			mov[EBX], EAX
	}

	DEBUG_PRINT("%s - stack boundaries - %x,%x\n", ins_pass_name, data->stack_base, data->stack_limit);

	DEBUG_PRINT("%s - initializing thread done %d\n", ins_pass_name, dr_get_thread_id(drcontext));

}