⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mix_vm.c

📁 汇编语言编程源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
			    mix_src_file_get_path (sfile)));    }  vm_reset_reload_ (vm, reload);  if ( mix_code_file_is_debug (file) )    {      vm->symbol_table = mix_code_file_get_symbol_table (file);      vm->line_table = g_tree_new (cmp_uint_);      vm->address_table = g_tree_new (cmp_uint_);    }  vm->src_file = sfile;    while ( mix_code_file_get_ins (file, &ins) )     {      set_cell_ (vm, ins.address, ins.ins);      if ( vm->line_table != NULL )	{	  g_tree_insert (vm->line_table, 			 GUINT_TO_POINTER (ins.lineno),			 GUINT_TO_POINTER ((guint)ins.address));	  g_tree_insert (vm->address_table, 			 GUINT_TO_POINTER ((guint)ins.address),			 GUINT_TO_POINTER (ins.lineno));	}    }  set_loc_ (vm, mix_code_file_get_start_addr (file));  set_start_ (vm, get_loc_ (vm));  mix_code_file_delete (file);    set_status_ (vm, MIX_VM_LOADED);  return TRUE;}const mix_src_file_t *mix_vm_get_src_file (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, NULL);  return vm->src_file;}const mix_symbol_table_t *mix_vm_get_symbol_table (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, NULL);  return vm->symbol_table;}mix_address_t mix_vm_get_prog_count (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, MIX_SHORT_ZERO);  return get_loc_ (vm);}/* Get the source line number for a given address */guintmix_vm_get_address_lineno (const mix_vm_t *vm, mix_address_t addr){  gpointer gp_addr = GUINT_TO_POINTER ((guint)addr);  guint lineno;  g_return_val_if_fail (vm != NULL, 0);  g_return_val_if_fail (MEMOK_ (addr), 0);  lineno = GPOINTER_TO_UINT (g_tree_lookup (vm->address_table, gp_addr));  return lineno;}/* Get the address for a given source line number */typedef struct {  guint lineno;  mix_address_t result;} addr_traverse_t;static gintget_address_ (gpointer key, gpointer value, gpointer data){  addr_traverse_t *tr = (addr_traverse_t *)data;  if (GPOINTER_TO_UINT (key) == tr->lineno)    {      tr->result = mix_short_new (GPOINTER_TO_UINT (value));      return TRUE;    }  return (GPOINTER_TO_UINT (key) < tr->lineno)? FALSE:TRUE;}mix_address_tmix_vm_get_lineno_address (const mix_vm_t *vm, guint lineno){  addr_traverse_t tr;    g_return_val_if_fail (vm != NULL, MIX_VM_CELL_NO);  if (!vm->line_table) return MIX_VM_CELL_NO;  tr.lineno = lineno;  tr.result = MIX_VM_CELL_NO;  g_tree_traverse (vm->line_table, get_address_, G_IN_ORDER, (gpointer)&tr);  return tr.result;}/* continue execution of instructions in memory */mix_vm_status_tmix_vm_run (mix_vm_t *vm){  mix_ins_t ins;  g_return_val_if_fail (vm != NULL, MIX_VM_ERROR);    while ( !is_halted_ (vm) )    {      mix_word_to_ins_uncheck (get_cell_ (vm, get_loc_ (vm)), ins);      vm->address_list =	g_slist_prepend (vm->address_list,			 GINT_TO_POINTER ((gint)get_loc_ (vm)));      if ( !(*ins_handlers_[ins.opcode]) (vm,&ins) ) 	return set_status_ (vm, MIX_VM_ERROR);      else	update_time_ (vm, &ins);      if (bp_is_set_ (vm, get_loc_ (vm)))	return set_status_ (vm, MIX_VM_BREAK);      if (mix_predicate_list_eval (get_pred_list_ (vm)))	return set_status_ (vm, MIX_VM_COND_BREAK);      if (get_loc_ (vm) >= MIX_VM_CELL_NO) halt_ (vm, TRUE);    }  return set_status_ (vm, MIX_VM_HALT);}/* execute next memory instruction */mix_vm_status_tmix_vm_exec_next (mix_vm_t *vm){  mix_ins_t ins;  g_return_val_if_fail (vm != NULL, MIX_VM_ERROR);  if (get_loc_ (vm) >= MIX_VM_CELL_NO) halt_ (vm, TRUE);  if (is_halted_ (vm)) return set_status_ (vm, MIX_VM_HALT);  vm->address_list =    g_slist_prepend (vm->address_list,		     GINT_TO_POINTER ((gint)get_loc_ (vm)));  mix_word_to_ins_uncheck (get_cell_ (vm, get_loc_ (vm)), ins);  if (!(*ins_handlers_[ins.opcode]) (vm, &ins))    return set_status_ (vm, MIX_VM_ERROR);  else    update_time_ (vm, &ins);  if (is_halted_ (vm)) return set_status_ (vm, MIX_VM_HALT);  if (bp_is_set_ (vm, get_loc_ (vm))) return set_status_ (vm, MIX_VM_BREAK);  if (mix_predicate_list_eval (get_pred_list_ (vm)))    return set_status_ (vm, MIX_VM_COND_BREAK);  return set_status_ (vm, MIX_VM_RUNNING);}/* get the current execution status */mix_vm_status_tmix_vm_get_run_status (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, MIX_VM_ERROR);  return get_status_ (vm);}/* Breakpoints */gulongmix_vm_get_break_lineno (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, 0);  if (vm->address_table == NULL)    return 0;  else    {      gpointer loc = GUINT_TO_POINTER ((guint)get_loc_ (vm));      return GPOINTER_TO_UINT (g_tree_lookup (vm->address_table,loc));    }}typedef struct {  mix_vm_t *vm;  guint lineno;  gint result;} bp_traverse_t;static gintset_break_ (gpointer key, gpointer value, gpointer data){  bp_traverse_t *tr = (bp_traverse_t *)data;  if (GPOINTER_TO_UINT (key) >= tr->lineno)    {      bp_set_ (tr->vm, mix_short_new (GPOINTER_TO_UINT (value)));      tr->lineno = GPOINTER_TO_UINT (key);      tr->result = MIX_VM_BP_OK;      return TRUE;    }  return FALSE;}gint /* if >0 the line no. of the break point */mix_vm_set_breakpoint (mix_vm_t *vm, guint lineno){  bp_traverse_t tr;    g_return_val_if_fail (vm != NULL, MIX_VM_BP_ERROR);  if (!vm->line_table) return MIX_VM_BP_NDEBUG;  tr.lineno = lineno;  tr.vm = vm;  tr.result = MIX_VM_BP_INV_LINE;  g_tree_traverse (vm->line_table, set_break_, G_IN_ORDER, (gpointer)&tr);  if (tr.result == MIX_VM_BP_OK)    return tr.lineno;  else    return tr.result;}gintmix_vm_set_breakpoint_address (mix_vm_t *vm, guint address) {  g_return_val_if_fail (vm != NULL, MIX_VM_BP_ERROR);  if (address >= MIX_VM_CELL_NO)    return MIX_VM_BP_INV_ADDRESS;  else    bp_set_ (vm, mix_short_new (address));  return MIX_VM_BP_OK;}gbooleanmix_vm_has_breakpoint_at_address (const mix_vm_t *vm, guint address){  g_return_val_if_fail (vm != NULL, FALSE);  if (address >= MIX_VM_CELL_NO) return FALSE;  return  (bp_is_set_ (vm, address));}static gintclear_break_ (gpointer key, gpointer value, gpointer data){  bp_traverse_t *tr = (bp_traverse_t *)data;  if (GPOINTER_TO_UINT (key) == tr->lineno)    {      bp_clear_ (tr->vm, mix_short_new (GPOINTER_TO_UINT (value)));      tr->result = MIX_VM_BP_OK;      return TRUE;    }  else if (GPOINTER_TO_UINT (key) > tr->lineno)    return TRUE;    return FALSE;}gint /* one of MIX_VM_BP_ */mix_vm_clear_breakpoint (mix_vm_t *vm, guint lineno){  bp_traverse_t tr;    g_return_val_if_fail (vm != NULL, MIX_VM_BP_ERROR);  if (!vm->line_table) return MIX_VM_BP_NDEBUG;  tr.lineno = lineno;  tr.vm = vm;  tr.result = MIX_VM_BP_INV_LINE;  g_tree_traverse (vm->line_table, clear_break_, G_IN_ORDER, (gpointer)&tr);  return tr.result;}gintmix_vm_clear_breakpoint_address (mix_vm_t *vm, guint address) {  g_return_val_if_fail (vm != NULL, MIX_VM_BP_ERROR);  if (address >= MIX_VM_CELL_NO)    return MIX_VM_BP_INV_ADDRESS;  else    bp_clear_ (vm, mix_short_new (address));  return MIX_VM_BP_OK;}voidmix_vm_clear_all_breakpoints (mix_vm_t *vm){  g_return_if_fail (vm != NULL);  bp_clear_all_ (vm);  mix_predicate_list_clear (get_pred_list_ (vm));}gbooleanmix_vm_set_conditional_breakpoint (mix_vm_t *vm, mix_predicate_t *pred){  g_return_val_if_fail (vm != NULL, FALSE);  g_return_val_if_fail (pred != NULL, FALSE);  mix_predicate_list_add (get_pred_list_ (vm), pred);  return TRUE;}gbooleanmix_vm_clear_conditional_breakpoint (mix_vm_t *vm, mix_predicate_t *pred){  g_return_val_if_fail (vm != NULL, FALSE);  g_return_val_if_fail (pred != NULL, FALSE);  return mix_predicate_list_remove (get_pred_list_ (vm), pred);}const gchar *mix_vm_get_last_breakpoint_message (const mix_vm_t *vm){  const mix_predicate_t *last = NULL;  g_return_val_if_fail (vm != NULL, NULL);  if ((last = mix_predicate_list_last_true_eval (get_pred_list_ (vm))) != NULL)    return mix_predicate_get_message (last);  return NULL;}mix_predicate_type_tmix_vm_get_last_conditional_breakpoint_type (const mix_vm_t *vm){  const mix_predicate_t *last = NULL;  g_return_val_if_fail (vm != NULL, MIX_PRED_INVALID);  last = mix_predicate_list_last_true_eval (get_pred_list_ (vm));  return last? mix_predicate_get_type (last) : MIX_PRED_INVALID;}/* Get the vm uptime, defined as the time spent executing instructions */mix_time_tmix_vm_get_uptime (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, 0);  return mix_vm_clock_get_time (get_clock_ (vm));}/* Get the list of addresses for executed instructions */const GSList *mix_vm_get_backtrace (const mix_vm_t *vm){  g_return_val_if_fail (vm != NULL, NULL);  return get_address_list_ (vm);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -