@@ -76,19 +76,29 @@ struct OMapInnerNode
7676 }
7777
7878 void prepare_commit () final {
79+ if (unlikely (!is_seen_by_users ())) {
80+ ceph_assert (is_rewrite ());
81+ auto &prior = *get_prior_instance ()->template cast <OMapInnerNode>();
82+ if (!prior.is_seen_by_users ()) {
83+ return ;
84+ }
85+ set_seen_by_users ();
86+ }
7987 this ->parent_node_t ::prepare_commit ();
80- if (is_rewrite () && ! is_btree_root () ) {
88+ if (is_rewrite ()) {
8189 auto &prior = *get_prior_instance ()->template cast <OMapInnerNode>();
82- if (prior.base_child_t ::has_parent_tracker ()) {
83- assert (prior.is_seen_by_users ());
90+ assert (prior.is_seen_by_users ());
91+ // Chances are that this transaction is in parallel with another
92+ // user transaction that set the prior's root to true, so we need
93+ // to do this.
94+ set_root (prior.is_btree_root ());
95+ if (!is_btree_root ()) {
96+ assert (prior.base_child_t ::has_parent_tracker ());
97+ assert (prior.is_seen_by_users ());
8498 // unlike fixed-kv nodes, rewriting child nodes of the omap tree
8599 // won't affect parent nodes, so we have to manually take prior
86100 // instances' parent trackers here.
87101 this ->child_node_t ::take_parent_from_prior ();
88- } else {
89- // dirty omap extent may not be accessed yet during rewrite,
90- // this means the extent may not be initalized yet as linked.
91- assert (!prior.is_seen_by_users ());
92102 }
93103 }
94104 }
@@ -292,18 +302,28 @@ struct OMapLeafNode
292302 }
293303
294304 void prepare_commit () final {
295- if (is_rewrite () && !is_btree_root ()) {
305+ if (unlikely (!is_seen_by_users ())) {
306+ ceph_assert (is_rewrite ());
307+ auto &prior = *get_prior_instance ()->template cast <OMapLeafNode>();
308+ if (!prior.is_seen_by_users ()) {
309+ return ;
310+ }
311+ set_seen_by_users ();
312+ }
313+ if (is_rewrite ()) {
296314 auto &prior = *get_prior_instance ()->template cast <OMapLeafNode>();
297- if (prior.base_child_t ::has_parent_tracker ()) {
298- assert (prior.is_seen_by_users ());
315+ assert (prior.is_seen_by_users ());
316+ // Chances are that this transaction is in parallel with another
317+ // user transaction that set the prior's root to true, so we need
318+ // to do this.
319+ set_root (prior.is_btree_root ());
320+ if (!is_btree_root ()) {
321+ assert (prior.base_child_t ::has_parent_tracker ());
322+ assert (prior.is_seen_by_users ());
299323 // unlike fixed-kv nodes, rewriting child nodes of the omap tree
300324 // won't affect parent nodes, so we have to manually take prior
301325 // instances' parent trackers here.
302326 this ->child_node_t ::take_parent_from_prior ();
303- } else {
304- // dirty omap extent may not be accessed yet during rewrite,
305- // this means the extent may not be initalized yet as linked.
306- assert (!prior.is_seen_by_users ());
307327 }
308328 }
309329 }
0 commit comments