OLF_IDX_IN_FID = 0x0010,
};
+/* There are some overhead to detect OI inconsistency automatically
+ * during normal RPC handling. We do not want to always auto detect
+ * OI inconsistency especailly when OI scrub just done recently.
+ *
+ * The 'auto_scrub' defines the time (united as second) interval to
+ * enable auto detect OI inconsistency since last OI scurb done. */
+enum auto_scrub {
+ /* Disable auto scrub. */
+ AS_NEVER = 0,
+
+ /* 1 second is too short interval, it is almost equal to always auto
+ * detect inconsistent OI, usually used for test. */
+ AS_ALWAYS = 1,
+
+ /* Enable auto detect OI inconsistency one month (60 * 60 * 24 * 30)
+ * after last OI scrub. */
+ AS_DEFAULT = 2592000LL,
+};
+
struct scrub_file {
/* 128-bit uuid for volume. */
__u8 sf_uuid[16];
goto found;
}
- if (dev->od_noscrub) {
+ if (dev->od_auto_scrub_interval == AS_NEVER) {
if (!remote)
GOTO(out, result = -EREMCHG);
if (!fid_is_norm(fid) && !fid_is_igif(fid))
RETURN(0);
- if (dev->od_noscrub && !thread_is_running(&scrub->os_thread))
+ if (thread_is_running(&scrub->os_thread) &&
+ scrub->os_pos_current > id->oii_ino)
RETURN(0);
- if (scrub->os_pos_current > id->oii_ino)
+ if (dev->od_auto_scrub_interval == AS_NEVER ||
+ cfs_time_before(ktime_get_real_seconds(),
+ scrub->os_file.sf_time_last_complete +
+ dev->od_auto_scrub_interval))
RETURN(0);
again:
GOTO(out, rc);
}
- if (!dev->od_noscrub && ++once == 1) {
+ if (dev->od_auto_scrub_interval != AS_NEVER && ++once == 1) {
rc = osd_scrub_start(oti->oti_env, dev, SS_AUTO_PARTIAL |
SS_CLEAR_DRYRUN | SS_CLEAR_FAILOUT);
CDEBUG(D_LFSCK | D_CONSOLE | D_WARNING,
}
if (lmd_flags & LMD_FLG_NOSCRUB)
- o->od_noscrub = 1;
+ o->od_auto_scrub_interval = AS_NEVER;
GOTO(out, rc = 0);
o->od_read_cache = 1;
o->od_writethrough_cache = 1;
o->od_readcache_max_filesize = OSD_MAX_CACHE_SIZE;
+ o->od_auto_scrub_interval = AS_DEFAULT;
cplen = strlcpy(o->od_svname, lustre_cfg_string(cfg, 4),
sizeof(o->od_svname));
*/
unsigned int od_fl_capa:1,
od_maybe_new:1,
- od_noscrub:1,
od_igif_inoi:1,
od_check_ff:1,
od_is_ost:1,
od_index_in_idif:1;
+ __s64 od_auto_scrub_interval;
__u32 od_dirent_journal;
int od_index;
struct proc_dir_entry *od_proc_entry;
if (unlikely(dev->od_mnt == NULL))
return -EINPROGRESS;
- seq_printf(m, "%d\n", !dev->od_noscrub);
+ seq_printf(m, "%lld\n", dev->od_auto_scrub_interval);
return 0;
}
if (rc)
return rc;
- dev->od_noscrub = !val;
+ dev->od_auto_scrub_interval = val;
return count;
}
LPROC_SEQ_FOPS(ldiskfs_osd_auto_scrub);
scrub->os_pos_current = sf->sf_pos_latest_start;
sf->sf_status = SS_SCANNING;
- sf->sf_time_latest_start = cfs_time_current_sec();
+ sf->sf_time_latest_start = ktime_get_real_seconds();
sf->sf_time_last_checkpoint = sf->sf_time_latest_start;
sf->sf_pos_last_checkpoint = sf->sf_pos_latest_start - 1;
rc = scrub_file_store(env, scrub);
scrub->os_new_checked = 0;
sf->sf_pos_last_checkpoint = scrub->os_pos_current;
}
- sf->sf_time_last_checkpoint = cfs_time_current_sec();
+ sf->sf_time_last_checkpoint = ktime_get_real_seconds();
if (result > 0) {
dev->od_igif_inoi = 1;
dev->od_check_ff = 0;
sf->sf_pos_latest_start = LDISKFS_FIRST_INO(osd_sb(dev)) + 1;
scrub->os_pos_current = sf->sf_pos_latest_start;
- sf->sf_time_latest_start = cfs_time_current_sec();
+ sf->sf_time_latest_start = ktime_get_real_seconds();
sf->sf_time_last_checkpoint = sf->sf_time_latest_start;
sf->sf_pos_last_checkpoint = sf->sf_pos_latest_start - 1;
rc = scrub_file_store(env, scrub);
* later if found that the system is upgrading. */
dev->od_igif_inoi = 1;
- if (!dev->od_dt_dev.dd_rdonly && !dev->od_noscrub &&
+ if (!dev->od_dt_dev.dd_rdonly &&
+ dev->od_auto_scrub_interval != AS_NEVER &&
((sf->sf_status == SS_PAUSED) ||
(sf->sf_status == SS_CRASHED &&
sf->sf_flags & (SF_RECREATED | SF_INCONSISTENT |
oii->oii_insert = insert;
if (lscrub->os_partial_scan) {
- __u64 now = cfs_time_current_sec();
+ __u64 now = ktime_get_real_seconds();
/* If there haven't been errors in a long time,
* decay old count until either the errors are