fast_commit.c (b21ebf143af219207214c79bc217beb39c43212a) fast_commit.c (a80f7fcf18672ae4971a6b713b58c0d389aa99fe)
1// SPDX-License-Identifier: GPL-2.0
2
3/*
4 * fs/ext4/fast_commit.c
5 *
6 * Written by Harshad Shirwadkar <harshadshirwadkar@gmail.com>
7 *
8 * Ext4 fast commits routines.

--- 309 unchanged lines hidden (view full) ---

318 * __fc_track_fn() with update = 0. If we have already been called after a full
319 * commit, we pass update = 1. Based on that, the track function can determine
320 * if it needs to track a field for the first time or if it needs to just
321 * update the previously tracked value.
322 *
323 * If enqueue is set, this function enqueues the inode in fast commit list.
324 */
325static int ext4_fc_track_template(
1// SPDX-License-Identifier: GPL-2.0
2
3/*
4 * fs/ext4/fast_commit.c
5 *
6 * Written by Harshad Shirwadkar <harshadshirwadkar@gmail.com>
7 *
8 * Ext4 fast commits routines.

--- 309 unchanged lines hidden (view full) ---

318 * __fc_track_fn() with update = 0. If we have already been called after a full
319 * commit, we pass update = 1. Based on that, the track function can determine
320 * if it needs to track a field for the first time or if it needs to just
321 * update the previously tracked value.
322 *
323 * If enqueue is set, this function enqueues the inode in fast commit list.
324 */
325static int ext4_fc_track_template(
326 struct inode *inode, int (*__fc_track_fn)(struct inode *, void *, bool),
326 handle_t *handle, struct inode *inode,
327 int (*__fc_track_fn)(struct inode *, void *, bool),
327 void *args, int enqueue)
328{
328 void *args, int enqueue)
329{
329 tid_t running_txn_tid;
330 bool update = false;
331 struct ext4_inode_info *ei = EXT4_I(inode);
332 struct ext4_sb_info *sbi = EXT4_SB(inode->i_sb);
330 bool update = false;
331 struct ext4_inode_info *ei = EXT4_I(inode);
332 struct ext4_sb_info *sbi = EXT4_SB(inode->i_sb);
333 tid_t tid = 0;
333 int ret;
334
335 if (!test_opt2(inode->i_sb, JOURNAL_FAST_COMMIT) ||
336 (sbi->s_mount_state & EXT4_FC_REPLAY))
337 return -EOPNOTSUPP;
338
339 if (ext4_fc_is_ineligible(inode->i_sb))
340 return -EINVAL;
341
334 int ret;
335
336 if (!test_opt2(inode->i_sb, JOURNAL_FAST_COMMIT) ||
337 (sbi->s_mount_state & EXT4_FC_REPLAY))
338 return -EOPNOTSUPP;
339
340 if (ext4_fc_is_ineligible(inode->i_sb))
341 return -EINVAL;
342
342 running_txn_tid = sbi->s_journal ?
343 sbi->s_journal->j_commit_sequence + 1 : 0;
344
343 tid = handle->h_transaction->t_tid;
345 mutex_lock(&ei->i_fc_lock);
344 mutex_lock(&ei->i_fc_lock);
346 if (running_txn_tid == ei->i_sync_tid) {
345 if (tid == ei->i_sync_tid) {
347 update = true;
348 } else {
349 ext4_fc_reset_inode(inode);
346 update = true;
347 } else {
348 ext4_fc_reset_inode(inode);
350 ei->i_sync_tid = running_txn_tid;
349 ei->i_sync_tid = tid;
351 }
352 ret = __fc_track_fn(inode, args, update);
353 mutex_unlock(&ei->i_fc_lock);
354
355 if (!enqueue)
356 return ret;
357
358 spin_lock(&sbi->s_fc_lock);

--- 58 unchanged lines hidden (view full) ---

417 else
418 list_add_tail(&node->fcd_list, &sbi->s_fc_dentry_q[FC_Q_MAIN]);
419 spin_unlock(&sbi->s_fc_lock);
420 mutex_lock(&ei->i_fc_lock);
421
422 return 0;
423}
424
350 }
351 ret = __fc_track_fn(inode, args, update);
352 mutex_unlock(&ei->i_fc_lock);
353
354 if (!enqueue)
355 return ret;
356
357 spin_lock(&sbi->s_fc_lock);

--- 58 unchanged lines hidden (view full) ---

416 else
417 list_add_tail(&node->fcd_list, &sbi->s_fc_dentry_q[FC_Q_MAIN]);
418 spin_unlock(&sbi->s_fc_lock);
419 mutex_lock(&ei->i_fc_lock);
420
421 return 0;
422}
423
425void ext4_fc_track_unlink(struct inode *inode, struct dentry *dentry)
424void __ext4_fc_track_unlink(handle_t *handle,
425 struct inode *inode, struct dentry *dentry)
426{
427 struct __track_dentry_update_args args;
428 int ret;
429
430 args.dentry = dentry;
431 args.op = EXT4_FC_TAG_UNLINK;
432
426{
427 struct __track_dentry_update_args args;
428 int ret;
429
430 args.dentry = dentry;
431 args.op = EXT4_FC_TAG_UNLINK;
432
433 ret = ext4_fc_track_template(inode, __track_dentry_update,
433 ret = ext4_fc_track_template(handle, inode, __track_dentry_update,
434 (void *)&args, 0);
435 trace_ext4_fc_track_unlink(inode, dentry, ret);
436}
437
434 (void *)&args, 0);
435 trace_ext4_fc_track_unlink(inode, dentry, ret);
436}
437
438void ext4_fc_track_link(struct inode *inode, struct dentry *dentry)
438void ext4_fc_track_unlink(handle_t *handle, struct dentry *dentry)
439{
439{
440 __ext4_fc_track_unlink(handle, d_inode(dentry), dentry);
441}
442
443void __ext4_fc_track_link(handle_t *handle,
444 struct inode *inode, struct dentry *dentry)
445{
440 struct __track_dentry_update_args args;
441 int ret;
442
443 args.dentry = dentry;
444 args.op = EXT4_FC_TAG_LINK;
445
446 struct __track_dentry_update_args args;
447 int ret;
448
449 args.dentry = dentry;
450 args.op = EXT4_FC_TAG_LINK;
451
446 ret = ext4_fc_track_template(inode, __track_dentry_update,
452 ret = ext4_fc_track_template(handle, inode, __track_dentry_update,
447 (void *)&args, 0);
448 trace_ext4_fc_track_link(inode, dentry, ret);
449}
450
453 (void *)&args, 0);
454 trace_ext4_fc_track_link(inode, dentry, ret);
455}
456
451void ext4_fc_track_create(struct inode *inode, struct dentry *dentry)
457void ext4_fc_track_link(handle_t *handle, struct dentry *dentry)
452{
458{
459 __ext4_fc_track_link(handle, d_inode(dentry), dentry);
460}
461
462void ext4_fc_track_create(handle_t *handle, struct dentry *dentry)
463{
453 struct __track_dentry_update_args args;
464 struct __track_dentry_update_args args;
465 struct inode *inode = d_inode(dentry);
454 int ret;
455
456 args.dentry = dentry;
457 args.op = EXT4_FC_TAG_CREAT;
458
466 int ret;
467
468 args.dentry = dentry;
469 args.op = EXT4_FC_TAG_CREAT;
470
459 ret = ext4_fc_track_template(inode, __track_dentry_update,
471 ret = ext4_fc_track_template(handle, inode, __track_dentry_update,
460 (void *)&args, 0);
461 trace_ext4_fc_track_create(inode, dentry, ret);
462}
463
464/* __track_fn for inode tracking */
465static int __track_inode(struct inode *inode, void *arg, bool update)
466{
467 if (update)
468 return -EEXIST;
469
470 EXT4_I(inode)->i_fc_lblk_len = 0;
471
472 return 0;
473}
474
472 (void *)&args, 0);
473 trace_ext4_fc_track_create(inode, dentry, ret);
474}
475
476/* __track_fn for inode tracking */
477static int __track_inode(struct inode *inode, void *arg, bool update)
478{
479 if (update)
480 return -EEXIST;
481
482 EXT4_I(inode)->i_fc_lblk_len = 0;
483
484 return 0;
485}
486
475void ext4_fc_track_inode(struct inode *inode)
487void ext4_fc_track_inode(handle_t *handle, struct inode *inode)
476{
477 int ret;
478
479 if (S_ISDIR(inode->i_mode))
480 return;
481
488{
489 int ret;
490
491 if (S_ISDIR(inode->i_mode))
492 return;
493
482 ret = ext4_fc_track_template(inode, __track_inode, NULL, 1);
494 ret = ext4_fc_track_template(handle, inode, __track_inode, NULL, 1);
483 trace_ext4_fc_track_inode(inode, ret);
484}
485
486struct __track_range_args {
487 ext4_lblk_t start, end;
488};
489
490/* __track_fn for tracking data updates */

--- 19 unchanged lines hidden (view full) ---

510 } else {
511 ei->i_fc_lblk_start = __arg->start;
512 ei->i_fc_lblk_len = __arg->end - __arg->start + 1;
513 }
514
515 return 0;
516}
517
495 trace_ext4_fc_track_inode(inode, ret);
496}
497
498struct __track_range_args {
499 ext4_lblk_t start, end;
500};
501
502/* __track_fn for tracking data updates */

--- 19 unchanged lines hidden (view full) ---

522 } else {
523 ei->i_fc_lblk_start = __arg->start;
524 ei->i_fc_lblk_len = __arg->end - __arg->start + 1;
525 }
526
527 return 0;
528}
529
518void ext4_fc_track_range(struct inode *inode, ext4_lblk_t start,
530void ext4_fc_track_range(handle_t *handle, struct inode *inode, ext4_lblk_t start,
519 ext4_lblk_t end)
520{
521 struct __track_range_args args;
522 int ret;
523
524 if (S_ISDIR(inode->i_mode))
525 return;
526
527 args.start = start;
528 args.end = end;
529
531 ext4_lblk_t end)
532{
533 struct __track_range_args args;
534 int ret;
535
536 if (S_ISDIR(inode->i_mode))
537 return;
538
539 args.start = start;
540 args.end = end;
541
530 ret = ext4_fc_track_template(inode, __track_range, &args, 1);
542 ret = ext4_fc_track_template(handle, inode, __track_range, &args, 1);
531
532 trace_ext4_fc_track_range(inode, start, end, ret);
533}
534
535static void ext4_fc_submit_bh(struct super_block *sb)
536{
537 int write_flags = REQ_SYNC;
538 struct buffer_head *bh = EXT4_SB(sb)->s_fc_bh;

--- 719 unchanged lines hidden (view full) ---

1258 old_parent = ext4_iget(sb, darg.parent_ino,
1259 EXT4_IGET_NORMAL);
1260 if (IS_ERR_OR_NULL(old_parent)) {
1261 jbd_debug(1, "Dir with inode %d not found", darg.parent_ino);
1262 iput(inode);
1263 return 0;
1264 }
1265
543
544 trace_ext4_fc_track_range(inode, start, end, ret);
545}
546
547static void ext4_fc_submit_bh(struct super_block *sb)
548{
549 int write_flags = REQ_SYNC;
550 struct buffer_head *bh = EXT4_SB(sb)->s_fc_bh;

--- 719 unchanged lines hidden (view full) ---

1270 old_parent = ext4_iget(sb, darg.parent_ino,
1271 EXT4_IGET_NORMAL);
1272 if (IS_ERR_OR_NULL(old_parent)) {
1273 jbd_debug(1, "Dir with inode %d not found", darg.parent_ino);
1274 iput(inode);
1275 return 0;
1276 }
1277
1266 ret = __ext4_unlink(old_parent, &entry, inode);
1278 ret = __ext4_unlink(NULL, old_parent, &entry, inode);
1267 /* -ENOENT ok coz it might not exist anymore. */
1268 if (ret == -ENOENT)
1269 ret = 0;
1270 iput(old_parent);
1271 iput(inode);
1272 return ret;
1273}
1274

--- 876 unchanged lines hidden ---
1279 /* -ENOENT ok coz it might not exist anymore. */
1280 if (ret == -ENOENT)
1281 ret = 0;
1282 iput(old_parent);
1283 iput(inode);
1284 return ret;
1285}
1286

--- 876 unchanged lines hidden ---