static inline void finalize_ssa_uses (struct function *fn, gimple *stmt) { unsigned new_i; struct use_optype_d new_list; use_optype_p old_ops, ptr, last; /* Pre-pend the VUSE we may have built. */ if (build_vuse != NULL_TREE) { tree oldvuse = gimple_vuse (stmt); if (oldvuse && TREE_CODE (oldvuse) == SSA_NAME) oldvuse = SSA_NAME_VAR (oldvuse); if (oldvuse != (build_vuse != NULL_TREE ? build_vuse : build_vdef)) gimple_set_vuse (stmt, NULL_TREE); build_uses.safe_insert (0, gimple_vuse_ptr (stmt)); } new_list.next = NULL; last = &new_list; old_ops = gimple_use_ops (stmt); /* Clear a no longer necessary VUSE. */ if (build_vuse == NULL_TREE && gimple_vuse (stmt) != NULL_TREE) gimple_set_vuse (stmt, NULL_TREE); /* If there is anything in the old list, free it. */ if (old_ops) { for (ptr = old_ops; ptr->next; ptr = ptr->next) delink_imm_use (USE_OP_PTR (ptr)); delink_imm_use (USE_OP_PTR (ptr)); ptr->next = gimple_ssa_operands (fn)->free_uses; gimple_ssa_operands (fn)->free_uses = old_ops; } /* If we added a VUSE, make sure to set the operand if it is not already present and mark it for renaming. */ if (build_vuse != NULL_TREE && gimple_vuse (stmt) == NULL_TREE) { gimple_set_vuse (stmt, gimple_vop (fn)); fn->gimple_df->rename_vops = 1; fn->gimple_df->ssa_renaming_needed = 1; } /* Now create nodes for all the new nodes. */ for (new_i = 0; new_i < build_uses.length (); new_i++) { tree *op = build_uses[new_i]; last = add_use_op (fn, stmt, op, last); } /* Now set the stmt's operands. */ gimple_set_use_ops (stmt, new_list.next); }
void free_stmt_operands (gimple stmt) { def_optype_p defs = gimple_def_ops (stmt), last_def; use_optype_p uses = gimple_use_ops (stmt), last_use; if (defs) { for (last_def = defs; last_def->next; last_def = last_def->next) continue; last_def->next = gimple_ssa_operands (cfun)->free_defs; gimple_ssa_operands (cfun)->free_defs = defs; gimple_set_def_ops (stmt, NULL); } if (uses) { for (last_use = uses; last_use->next; last_use = last_use->next) delink_imm_use (USE_OP_PTR (last_use)); delink_imm_use (USE_OP_PTR (last_use)); last_use->next = gimple_ssa_operands (cfun)->free_uses; gimple_ssa_operands (cfun)->free_uses = uses; gimple_set_use_ops (stmt, NULL); } if (gimple_has_mem_ops (stmt)) { gimple_set_vuse (stmt, NULL_TREE); gimple_set_vdef (stmt, NULL_TREE); } }
static void remove_phi_arg_num (gimple phi, int i) { int num_elem = gimple_phi_num_args (phi); gcc_assert (i < num_elem); /* Delink the item which is being removed. */ delink_imm_use (gimple_phi_arg_imm_use_ptr (phi, i)); /* If it is not the last element, move the last element to the element we want to delete, resetting all the links. */ if (i != num_elem - 1) { use_operand_p old_p, new_p; old_p = gimple_phi_arg_imm_use_ptr (phi, num_elem - 1); new_p = gimple_phi_arg_imm_use_ptr (phi, i); /* Set use on new node, and link into last element's place. */ *(new_p->use) = *(old_p->use); relink_imm_use (new_p, old_p); } /* Shrink the vector and return. Note that we do not have to clear PHI_ARG_DEF because the garbage collector will not look at those elements beyond the first PHI_NUM_ARGS elements of the array. */ phi->gimple_phi.nargs--; }
static inline void finalize_ssa_uses (gimple stmt) { unsigned new_i; struct use_optype_d new_list; use_optype_p old_ops, ptr, last; /* Pre-pend the VUSE we may have built. */ if (build_vuse != NULL_TREE) { tree oldvuse = gimple_vuse (stmt); if (oldvuse && TREE_CODE (oldvuse) == SSA_NAME) oldvuse = SSA_NAME_VAR (oldvuse); if (oldvuse != (build_vuse != NULL_TREE ? build_vuse : build_vdef)) gimple_set_vuse (stmt, NULL_TREE); VEC_safe_insert (tree, heap, build_uses, 0, (tree)gimple_vuse_ptr (stmt)); } new_list.next = NULL; last = &new_list; old_ops = gimple_use_ops (stmt); /* Clear a no longer necessary VUSE. */ if (build_vuse == NULL_TREE && gimple_vuse (stmt) != NULL_TREE) gimple_set_vuse (stmt, NULL_TREE); /* If there is anything in the old list, free it. */ if (old_ops) { for (ptr = old_ops; ptr; ptr = ptr->next) delink_imm_use (USE_OP_PTR (ptr)); old_ops->next = gimple_ssa_operands (cfun)->free_uses; gimple_ssa_operands (cfun)->free_uses = old_ops; } /* If we added a VUSE, make sure to set the operand if it is not already present and mark it for renaming. */ if (build_vuse != NULL_TREE && gimple_vuse (stmt) == NULL_TREE) { gimple_set_vuse (stmt, gimple_vop (cfun)); mark_sym_for_renaming (gimple_vop (cfun)); } /* Now create nodes for all the new nodes. */ for (new_i = 0; new_i < VEC_length (tree, build_uses); new_i++) last = add_use_op (stmt, (tree *) VEC_index (tree, build_uses, new_i), last); /* Now set the stmt's operands. */ gimple_set_use_ops (stmt, new_list.next); }
void release_phi_node (gimple phi) { size_t bucket; size_t len = gimple_phi_capacity (phi); size_t x; for (x = 0; x < gimple_phi_num_args (phi); x++) { use_operand_p imm; imm = gimple_phi_arg_imm_use_ptr (phi, x); delink_imm_use (imm); } bucket = len > NUM_BUCKETS - 1 ? NUM_BUCKETS - 1 : len; bucket -= 2; VEC_safe_push (gimple, gc, free_phinodes[bucket], phi); free_phinode_count++; }
void release_phi_node (tree phi) { int bucket; int len = PHI_ARG_CAPACITY (phi); int x; for (x = 0; x < PHI_NUM_ARGS (phi); x++) { use_operand_p imm; imm = &(PHI_ARG_IMM_USE_NODE (phi, x)); delink_imm_use (imm); } bucket = len > NUM_BUCKETS - 1 ? NUM_BUCKETS - 1 : len; bucket -= 2; PHI_CHAIN (phi) = free_phinodes[bucket]; free_phinodes[bucket] = phi; free_phinode_count++; }
void release_ssa_name (tree var) { if (!var) return; /* Never release the default definition for a symbol. It's a special SSA name that should always exist once it's created. */ if (SSA_NAME_IS_DEFAULT_DEF (var)) return; /* If VAR has been registered for SSA updating, don't remove it. After update_ssa has run, the name will be released. */ if (name_registered_for_update_p (var)) { release_ssa_name_after_update_ssa (var); return; } /* release_ssa_name can be called multiple times on a single SSA_NAME. However, it should only end up on our free list one time. We keep a status bit in the SSA_NAME node itself to indicate it has been put on the free list. Note that once on the freelist you can not reference the SSA_NAME's defining statement. */ if (! SSA_NAME_IN_FREE_LIST (var)) { tree saved_ssa_name_var = SSA_NAME_VAR (var); int saved_ssa_name_version = SSA_NAME_VERSION (var); use_operand_p imm = &(SSA_NAME_IMM_USE_NODE (var)); if (MAY_HAVE_DEBUG_STMTS) insert_debug_temp_for_var_def (NULL, var); #ifdef ENABLE_CHECKING verify_imm_links (stderr, var); #endif while (imm->next != imm) delink_imm_use (imm->next); (*SSANAMES (cfun))[SSA_NAME_VERSION (var)] = NULL_TREE; memset (var, 0, tree_size (var)); imm->prev = imm; imm->next = imm; imm->loc.ssa_name = var; /* First put back the right tree node so that the tree checking macros do not complain. */ TREE_SET_CODE (var, SSA_NAME); /* Restore the version number. */ SSA_NAME_VERSION (var) = saved_ssa_name_version; /* Hopefully this can go away once we have the new incremental SSA updating code installed. */ SET_SSA_NAME_VAR_OR_IDENTIFIER (var, saved_ssa_name_var); /* Note this SSA_NAME is now in the first list. */ SSA_NAME_IN_FREE_LIST (var) = 1; /* And finally put it on the free list. */ vec_safe_push (FREE_SSANAMES (cfun), var); } }