/** * reiser4_delete_dir_common - delete_object of file_plugin * @inode: inode to be deleted * * This is common implementation of delete_object method of file_plugin for * typical directory. It calls done method of dir_plugin to remove "." and * removes stat data and safe-link. */ int reiser4_delete_dir_common(struct inode *inode) { int result; dir_plugin *dplug; assert("", (get_current_context() && get_current_context()->trans->atom == NULL)); dplug = inode_dir_plugin(inode); assert("vs-1101", dplug && dplug->done); /* kill cursors which might be attached to inode */ reiser4_kill_cursors(inode); /* grab space enough for removing two items */ if (reiser4_grab_space (2 * estimate_one_item_removal(reiser4_tree_by_inode(inode)), BA_RESERVED | BA_CAN_COMMIT)) return RETERR(-ENOSPC); result = dplug->done(inode); if (!result) result = common_object_delete_no_reserve(inode); return result; }
/* Intended to be called from interrupt context only */ void task_trigger_exception (struct task *task, int exception, busword_t textaddr, busword_t data, int code) { DECLARE_CRITICAL_SECTION (except); ASSERT (get_current_context () == KERNEL_CONTEXT_INTERRUPT); ASSERT (get_current_task () == task); if (exception < 0 || exception >= EX_MAX) FAIL ("exception code unrecognized\n"); if (task->ts_ex_handlers[exception] == NULL) { /* Process shall be killed */ TASK_ATOMIC_ENTER (except); (void) wake_up (task, TASK_STATE_EXITED, 0); task_destroy (task); schedule (); TASK_ATOMIC_LEAVE (except); } else (task->ts_ex_handlers[exception]) (task, exception, textaddr, data, code); }
int reiser4_grab_space(__u64 count, reiser4_ba_flags_t flags) { int ret; reiser4_context *ctx; assert("nikita-2964", ergo(flags & BA_CAN_COMMIT, lock_stack_isclean(get_current_lock_stack ()))); ctx = get_current_context(); if (!(flags & BA_FORCE) && !is_grab_enabled(ctx)) return 0; ret = reiser4_grab(ctx, count, flags); if (ret == -ENOSPC) { /* Trying to commit the all transactions if BA_CAN_COMMIT flag present */ if (flags & BA_CAN_COMMIT) { txnmgr_force_commit_all(ctx->super, 0); ctx->grab_enabled = 1; ret = reiser4_grab(ctx, count, flags); } } /* * allocation from reserved pool cannot fail. This is severe error. */ assert("nikita-3005", ergo(flags & BA_RESERVED, ret == 0)); return ret; }
/** * get_nonexclusive_access - get nonexclusive access to a file * @uf_info: unix file specific part of inode to obtain access to * * Nonexclusive access is obtained on a file before read, write, readpage. */ void get_nonexclusive_access(struct unix_file_info *uf_info) { assert("nikita-3029", reiser4_schedulable()); assert("nikita-3361", get_current_context()->trans->atom == NULL); down_read(&uf_info->latch); nea_grabbed(uf_info); }
RapiContext* rapi_context_current()/*{{{*/ { RapiContext *context = NULL; context = get_current_context(); /* If the current context is not initialized, setup a new one and return it */ if (!context) { RapiContext *new_context = rapi_context_new(); set_current_context(new_context); context = get_current_context(); } return context; }/*}}}*/
void fake_allocated2free(__u64 count, reiser4_ba_flags_t flags) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); fake_allocated2grabbed(ctx, sbinfo, count, flags); grabbed2free(ctx, sbinfo, count); }
void cluster_reserved2free(int count) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); cluster_reserved2grabbed(count); grabbed2free(ctx, sbinfo, count); }
void grabbed2free_mark(__u64 mark) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); assert("nikita-3007", (__s64) mark >= 0); assert("nikita-3006", ctx->grabbed_blocks >= mark); grabbed2free(ctx, sbinfo, ctx->grabbed_blocks - mark); }
void rapi_context_set(RapiContext* context) { RapiContext *old_context = NULL; /* Get the current context, if any */ old_context = get_current_context(); set_current_context(context); if (context) rapi_context_ref(context); if (old_context) rapi_context_unref(old_context); }
static reiser4_super_info_data *grabbed2fake_allocated_head(int count) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sub_from_ctx_grabbed(ctx, count); sbinfo = get_super_private(ctx->super); spin_lock_reiser4_super(sbinfo); sub_from_sb_grabbed(sbinfo, count); /* return sbinfo locked */ return sbinfo; }
static int do_printenv(struct command *cmdtp, int argc, char *argv[]) { struct variable_d *var; struct env_context *c, *current_c; if (argc == 2) { const char *val = getenv(argv[1]); if (val) { printf("%s=%s\n", argv[1], val); return 0; } printf("## Error: \"%s\" not defined\n", argv[1]); return 1; } current_c = get_current_context(); var = current_c->local->next; printf("locals:\n"); while (var) { printf("%s=%s\n", var_name(var), var_val(var)); var = var->next; } printf("globals:\n"); c = get_current_context(); while(c) { var = c->global->next; while (var) { printf("%s=%s\n", var_name(var), var_val(var)); var = var->next; } c = c->parent; } return 0; }
/* called at the beginning of jnode_flush to register flusher thread with ent * daemon */ void reiser4_enter_flush(struct super_block *super) { entd_context *ent; assert("zam-1029", super != NULL); ent = get_entd_context(super); assert("zam-1030", ent != NULL); spin_lock(&ent->guard); ent->flushers++; #if REISER4_DEBUG list_add(&get_current_context()->flushers_link, &ent->flushers_list); #endif spin_unlock(&ent->guard); }
static int reiser4_grab(reiser4_context * ctx, __u64 count, reiser4_ba_flags_t flags) { __u64 free_blocks; int ret = 0, use_reserved = flags & BA_RESERVED; reiser4_super_info_data *sbinfo; assert("vs-1276", ctx == get_current_context()); /* Do not grab anything on ro-mounted fs. */ if (rofs_super(ctx->super)) { ctx->grab_enabled = 0; return 0; } sbinfo = get_super_private(ctx->super); spin_lock_reiser4_super(sbinfo); free_blocks = sbinfo->blocks_free; if ((use_reserved && free_blocks < count) || (!use_reserved && free_blocks < count + sbinfo->blocks_reserved)) { ret = RETERR(-ENOSPC); goto unlock_and_ret; } add_to_ctx_grabbed(ctx, count); sbinfo->blocks_grabbed += count; sbinfo->blocks_free -= count; #if REISER4_DEBUG if (ctx->grabbed_initially == 0) ctx->grabbed_initially = count; #endif assert("nikita-2986", reiser4_check_block_counters(ctx->super)); /* disable grab space in current context */ ctx->grab_enabled = 0; unlock_and_ret: spin_unlock_reiser4_super(sbinfo); return ret; }
void cluster_reserved2grabbed(int count) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); spin_lock_reiser4_super(sbinfo); sub_from_cluster_reserved(sbinfo, count); sbinfo->blocks_grabbed += count; assert("edward-505", reiser4_check_block_counters(ctx->super)); spin_unlock_reiser4_super(sbinfo); add_to_ctx_grabbed(ctx, count); }
static void rapi_context_free(RapiContext* context)/*{{{*/ { if (!context) return; /* check it against the current context, * this should never happen */ RapiContext* check_context = get_current_context(); if (check_context == context) set_current_context(NULL); rapi_buffer_free(context->send_buffer); rapi_buffer_free(context->recv_buffer); synce_socket_free(context->socket); if (context->own_info && context->info) synce_info_destroy(context->info); free(context); }/*}}}*/
/* called at the end of jnode_flush */ void reiser4_leave_flush(struct super_block *super) { entd_context *ent; int wake_up_ent; assert("zam-1027", super != NULL); ent = get_entd_context(super); assert("zam-1028", ent != NULL); spin_lock(&ent->guard); ent->flushers--; wake_up_ent = (ent->flushers == 0 && ent->nr_todo_reqs != 0); #if REISER4_DEBUG list_del_init(&get_current_context()->flushers_link); #endif spin_unlock(&ent->guard); if (wake_up_ent) wake_up_process(ent->tsk); }
void grabbed2flush_reserved_nolock(txn_atom * atom, __u64 count) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; assert("vs-1095", atom); ctx = get_current_context(); sbinfo = get_super_private(ctx->super); sub_from_ctx_grabbed(ctx, count); add_to_atom_flush_reserved_nolock(atom, count); spin_lock_reiser4_super(sbinfo); sbinfo->blocks_flush_reserved += count; sub_from_sb_grabbed(sbinfo, count); assert("vpf-292", reiser4_check_block_counters(ctx->super)); spin_unlock_reiser4_super(sbinfo); }
void flush_reserved2grabbed(txn_atom * atom, __u64 count) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; assert("nikita-2788", atom != NULL); assert_spin_locked(&(atom->alock)); ctx = get_current_context(); sbinfo = get_super_private(ctx->super); add_to_ctx_grabbed(ctx, count); sub_from_atom_flush_reserved_nolock(atom, (__u32) count); spin_lock_reiser4_super(sbinfo); sbinfo->blocks_grabbed += count; sub_from_sb_flush_reserved(sbinfo, count); assert("vpf-292", reiser4_check_block_counters(ctx->super)); spin_unlock_reiser4_super(sbinfo); }
assert("zam-502", get_current_super_private() != NULL); sa_pre_commit_hook(); return 0; } /* an actor which applies delete set to block allocator data */ static int apply_dset(txn_atom * atom UNUSED_ARG, const reiser4_block_nr * a, const reiser4_block_nr * b, void *data UNUSED_ARG) { reiser4_context *ctx; reiser4_super_info_data *sbinfo; __u64 len = 1; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); assert("zam-877", atom->stage >= ASTAGE_PRE_COMMIT); assert("zam-552", sbinfo != NULL); if (b != NULL) len = *b; if (REISER4_DEBUG) { spin_lock_reiser4_super(sbinfo); assert("zam-554", *a < reiser4_block_count(ctx->super)); assert("zam-555", *a + len <= reiser4_block_count(ctx->super)); spin_unlock_reiser4_super(sbinfo);
/* Allocate "real" disk blocks by calling a proper space allocation plugin * method. Blocks are allocated in one contiguous disk region. The plugin * independent part accounts blocks by subtracting allocated amount from grabbed * or fake block counter and add the same amount to the counter of allocated * blocks. * * @hint -- a reiser4 blocknr hint object which contains further block * allocation hints and parameters (search start, a stage of block * which will be mapped to disk, etc.), * @blk -- an out parameter for the beginning of the allocated region, * @len -- in/out parameter, it should contain the maximum number of allocated * blocks, after block allocation completes, it contains the length of * allocated disk region. * @flags -- see reiser4_ba_flags_t description. * * @return -- 0 if success, error code otherwise. */ int reiser4_alloc_blocks(reiser4_blocknr_hint * hint, reiser4_block_nr * blk, reiser4_block_nr * len, reiser4_ba_flags_t flags) { __u64 needed = *len; reiser4_context *ctx; reiser4_super_info_data *sbinfo; int ret; assert("zam-986", hint != NULL); ctx = get_current_context(); sbinfo = get_super_private(ctx->super); /* For write-optimized data we use default search start value, which is * close to last write location. */ if (flags & BA_USE_DEFAULT_SEARCH_START) get_blocknr_hint_default(&hint->blk); /* VITALY: allocator should grab this for internal/tx-lists/similar only. */ /* VS-FIXME-HANS: why is this comment above addressed to vitaly (from vitaly)?*/ if (hint->block_stage == BLOCK_NOT_COUNTED) { ret = reiser4_grab_space_force(*len, flags); if (ret != 0) return ret; } ret = sa_alloc_blocks(reiser4_get_space_allocator(ctx->super), hint, (int)needed, blk, len); if (!ret) { assert("zam-680", *blk < reiser4_block_count(ctx->super)); assert("zam-681", *blk + *len <= reiser4_block_count(ctx->super)); if (flags & BA_PERMANENT) { /* we assume that current atom exists at this moment */ txn_atom *atom = get_current_atom_locked(); atom->nr_blocks_allocated += *len; spin_unlock_atom(atom); } switch (hint->block_stage) { case BLOCK_NOT_COUNTED: case BLOCK_GRABBED: grabbed2used(ctx, sbinfo, *len); break; case BLOCK_UNALLOCATED: fake_allocated2used(sbinfo, *len, flags); break; case BLOCK_FLUSH_RESERVED: { txn_atom *atom = get_current_atom_locked(); flush_reserved2used(atom, *len); spin_unlock_atom(atom); } break; default: impossible("zam-531", "wrong block stage"); } } else { assert("zam-821", ergo(hint->max_dist == 0 && !hint->backward, ret != -ENOSPC)); if (hint->block_stage == BLOCK_NOT_COUNTED) grabbed2free(ctx, sbinfo, needed); } return ret; }
/** * all_grabbed2free - releases all blocks grabbed in context * * Decreases context's and super block's grabbed block counters by number of * blocks grabbed by current context and increases super block's free block * counter correspondingly. */ void all_grabbed2free(void) { reiser4_context *ctx = get_current_context(); grabbed2free(ctx, get_super_private(ctx->super), ctx->grabbed_blocks); }
int reiser4_dealloc_blocks(const reiser4_block_nr * start, const reiser4_block_nr * len, block_stage_t target_stage, reiser4_ba_flags_t flags) { txn_atom *atom = NULL; int ret; reiser4_context *ctx; reiser4_super_info_data *sbinfo; ctx = get_current_context(); sbinfo = get_super_private(ctx->super); if (REISER4_DEBUG) { assert("zam-431", *len != 0); assert("zam-432", *start != 0); assert("zam-558", !reiser4_blocknr_is_fake(start)); spin_lock_reiser4_super(sbinfo); assert("zam-562", *start < sbinfo->block_count); spin_unlock_reiser4_super(sbinfo); } if (flags & BA_DEFER) { blocknr_set_entry *bsep = NULL; /* storing deleted block numbers in a blocknr set datastructure for further actual deletion */ do { atom = get_current_atom_locked(); assert("zam-430", atom != NULL); ret = blocknr_set_add_extent(atom, &atom->delete_set, &bsep, start, len); if (ret == -ENOMEM) return ret; /* This loop might spin at most two times */ } while (ret == -E_REPEAT); assert("zam-477", ret == 0); assert("zam-433", atom != NULL); spin_unlock_atom(atom); } else { assert("zam-425", get_current_super_private() != NULL); sa_dealloc_blocks(reiser4_get_space_allocator(ctx->super), *start, *len); if (flags & BA_PERMANENT) { /* These blocks were counted as allocated, we have to * revert it back if allocation is discarded. */ txn_atom *atom = get_current_atom_locked(); atom->nr_blocks_allocated -= *len; spin_unlock_atom(atom); } switch (target_stage) { case BLOCK_NOT_COUNTED: assert("vs-960", flags & BA_FORMATTED); /* VITALY: This is what was grabbed for internal/tx-lists/similar only */ used2free(sbinfo, *len); break; case BLOCK_GRABBED: used2grabbed(ctx, sbinfo, *len); break; case BLOCK_UNALLOCATED: used2fake_allocated(sbinfo, *len, flags & BA_FORMATTED); break; case BLOCK_FLUSH_RESERVED:{ txn_atom *atom; atom = get_current_atom_locked(); used2flush_reserved(sbinfo, atom, *len, flags & BA_FORMATTED); spin_unlock_atom(atom); break; } default: impossible("zam-532", "wrong block stage"); } } return 0; }