RBD创建一个image

RBD创建一个image的过程分析。

rbd.cc
do_create(librbd::RBD &rbd, librados::IoCtx& io_ctx,const char *imgname,
          uint64_t size, int *order,int format, uint64_t features,
          uint64_t stripe_unit, uint64_t stripe_count) //创建一个image
    >rbd.create3(io_ctx, imgname, size, features, order,stripe_unit, stripe_count)/create(...) //rbd 创建image
        >librbd::create(io_ctx, name, size, false, features, order,stripe_unit, stripe_count) //librbd 创建image
            >detect_format(io_ctx, imgname, NULL, NULL) //获取image的格式,这里用它来判断该image是否存在
            >uint64_t bid = rados.get_instance_id()
            >create_v1(io_ctx, imgname, bid, size, *order) //format == 1
            >create_v2(io_ctx, imgname, bid, size, *order, features,stripe_unit, stripe_count) //format ==2 以v2为例
                >validate_pool(io_ctx, cct) //判断pool是否有效
                >id_obj_name(imgname) //构建image的ID rbd_id.{imgname}
                >io_ctx.create(id_obj, true) //创建image的ID对象
                    >io_ctx_impl->create(obj, exclusive) //创建object_t的实例
                        >io_ctx_impl->create(obj, exclusive)
                            >op.create(exclusive) //op(ObjectOperation)
                                >::ObjectOperation *o = (::ObjectOperation *)impl;
                                >o->create(exclusive)
                                    >OSDOp& o = add_op(CEPH_OSD_OP_CREATE)
                            >operate(oid, &op, NULL)
                                >Objecter::Op *objecter_op = objecter->prepare_mutate_op(oid, oloc,*o, snapc, ut, flags,NULL, oncommit, &ver)
                                >objecter->op_submit(objecter_op) //提交Objecter::Op,进入Objecter层
                >cls_client::set_id(&io_ctx, id_obj, id) //设置image的id (通过命令模式实现)
                    >ioctx->exec(oid, "rbd", "set_id", in, out)
                        >io_ctx_impl->exec(obj, cls, method, inbl, outbl)
                            >(::ObjectOperation)rd.call(cls, method, inbl) //将该操作封装成OSDOp,放入ObjectOperation对象的vector集合中
                                >add_call(CEPH_OSD_OP_CALL, cname, method, indata, NULL, NULL, NULL)
                            >operate_read(oid, &rd, &outbl) //发起读请求
                                >Objecter::Op *objecter_op = objecter->prepare_read_op(oid, oloc,*o, snap_seq, pbl, flags,onack, &ver) //创建Op的实例   数据结构变成Op
                                >objecter->op_submit(objecter_op) //提交到objecter层 操作对象为Objecter::Op
                                    >_op_submit_with_budget(op, lc, ctx_budget)
                                        >int op_budget = _take_op_budget(op) //减去该Op的预算for throttle;
                                            >int op_budget = calc_op_budget(op) //预算值是该Op的字节大小
                                            > _throttle_op(op, op_budget) //这里是Objecter的Throttle层,如果keep_balanced_budget=true,能实现对速度的限制(op_throttle_bytes&op_throttle_ops)
                                        >_op_submit(op, lc)
                                            >_calc_target(&op->target, &op->last_force_resend) //计算该op的操作对象(用到CRUSH算法)
                                            >_get_session(op->target.osd, &s, lc) //为该Op构建与osd对应的OSDSession
                                            >_send_op_account(op) //登记该次op操作
                                            > m = _prepare_osd_op(op) //使用Op中的信息,初始化MOSDOp的实例
                                            >_session_op_assign(s, op) //将Op与OSDSession相关联。
                                            > _send_op(op, m)
                                                >op->session->con->send_message(m) //进入Massenger层,操作对象MOSDOp
                                                    >static_cast<SimpleMessenger*>(msgr)->send_message(m, this) //使用使用massenger层的SimpleMessenger的实例发生消息
                                                        >_send_message(m, con)
                                                            >submit_message(m, static_cast<PipeConnection*>(con),con->get_peer_addr(), con->get_peer_type(), false) //提交信息
                                                                >static_cast<PipeConnection*>(con)->try_get_pipe(&pipe) //获取该PipConnection对应的Pipe的实例
                                                                    >pipe->_send(m) //通过Pipe发送消息,即:把消息放入到Pipe::out_q队列中,并通知Pipe中的写线程来做实际的发生操作。
                                                                        >out_q[m->get_priority()].push_back(m);
                                                                    >dispatch_queue.local_delivery(m, m->get_priority()) //如果发送端与接收端是同一个,则直接将消息投递到DispathcQueue::local_messages中。


                >cls_client::dir_add_image(&io_ctx, RBD_DIRECTORY, imgname, id) //将新建的image注册到RBD_DIRECTORY中
                    >ioctx->exec(oid, "rbd", "dir_add_image", in, out) //做用于跨网络传输的序列化工作
                        >io_ctx_impl->exec(obj, cls, method, inbl, outbl) 
                            >rd.call(cls, method, inbl) //rd是(::ObjectOperation)的实例
                            >operate_read(oid, &rd, &outbl)
                                >Objecter::Op *objecter_op = objecter->prepare_read_op(oid, oloc,*o, snap_seq, pbl, flags,onack, &ver) //构建Objecter::Op的实例
                                >objecter->op_submit(objecter_op) //进入Objecter层
                                ...同上
                >header_name(id) //构建image的header标识
                >cls_client::create_image(&io_ctx, header_oid, size, order,features, oss.str()) //创建image的header对象
                    >ioctx->exec(oid, "rbd", "create", bl, bl2) //命令模式,为跨网络传输做序列化工作
                        >io_ctx_impl->exec(obj, cls, method, inbl, outbl) 
                            >rd.call(cls, method, inbl)
                            >operate_read(oid, &rd, &outbl)
                                >Objecter::Op *objecter_op = objecter->prepare_read_op(oid, oloc,*o, snap_seq, pbl, flags,onack, &ver)
                                >objecter->op_submit(objecter_op) //进入Objecter层
                                ...同上
                >cls_client::set_stripe_unit_count(&io_ctx, header_oid,stripe_unit, stripe_count) //设置image stripe的相关属性,与header对象关联
                    >ioctx->exec(oid, "rbd", "set_stripe_unit_count", in, out)
                        >io_ctx_impl->exec(obj, cls, method, inbl, outbl) 
                            >rd.call(cls, method, inbl)
                            >operate_read(oid, &rd, &outbl)
                                >Objecter::Op *objecter_op = objecter->prepare_read_op(oid, oloc,*o, snap_seq, pbl, flags,onack, &ver) //构建Objecter::Op的实例
                                >objecter->op_submit(objecter_op) //进入Objecter层
                >cls_client::object_map_resize(&op, Striper::get_num_objects(layout, size),OBJECT_NONEXISTENT) //构建op,该op用于resize object map
                    >rados_op->exec("rbd", "object_map_resize", in) //rados_op(librados::ObjectWriteOperation) 做序列化工作
                        >::ObjectOperation *o = (::ObjectOperation *)impl; 
                        >o->call(cls, method, inbl);
                >io_ctx.operate(ObjectMap::object_map_name(id, CEPH_NOSNAP), &op) //执行op
                    >io_ctx_impl->operate(obj, (::ObjectOperation*)o->impl, o->pmtime)
                        >Objecter::Op *objecter_op = objecter->prepare_mutate_op(oid, oloc,*o, snapc, ut, flags,NULL, oncommit, &ver) //创建Objecter::Op的实例,将ObjectOperation转化成Objecter::Op
                        >objecter->op_submit(objecter_op) //提交Objecter::Op,进入Objecter层



创建一个Image的步骤(新image组成格式):
1.创建image的ID对象 rbd_id.{imagename}
2.创建image的id(随机生产的,与image的ID对象完全不同)
3.将该image注册到RBD_DIRECTORY中(imagename ,id)
4.创建image的header对象
6.将image的相关元信息,绑定到header对象上。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值