Repository: tikv/tikv
File: components/resolved_ts/src/endpoint.rs (Rust)

Code before:

    fn run(&mut self, task: Task) {
        debug!("run resolved-ts task"; "task" => ?task);
        if self.last_active_memory_quota_check.elapsed()
            >= self.cfg.memory_quota_active_check_interval.0
        {
            self.last_active_memory_quota_check = std::time::Instant::now();
            // Check whether memory quota is exceeded actively.
            if let Err(e) = self.memory_quota.alloc(0) {
                self.re_register_all_regions(Some(e.to_string().as_str()));
            }
        }

        match task {
            Task::RegionDestroyed(region) => self.region_destroyed(region),
            Task::RegionUpdated(region) => self.region_updated(region),
            Task::RegisterRegion { region } => self.register_region(region, None),
            Task::DeRegisterRegion { region_id } => self.deregister_region(region_id),
            Task::ReRegisterRegion {
                region_id,
                observe_id,
                cause,
            } => self.re_register_region(
                region_id,
                observe_id,
                Some(cause.to_string().as_str()),
                None,
            ),
            Task::AdvanceResolvedTs { leader_resolver } => {
                self.handle_advance_resolved_ts(leader_resolver)
            }
            Task::ResolvedTsAdvanced {
                regions,
                ts,
                ts_source,
            } => self.handle_resolved_ts_advanced(regions, ts, ts_source),
            Task::ChangeLog { cmd_batch } => {
                self.handle_change_log(cmd_batch);
            }
            Task::ScanLocks {
                region_id,
                observe_id,
                entries,
                apply_index,
            } => self.handle_scan_locks(region_id, observe_id, entries, apply_index),
            Task::ChangeConfig { change } => self.handle_change_config(change),
            Task::GetDiagnosisInfo {
                region_id,
                log_locks,
                min_start_ts,
                callback,

Review comment (bug):
Converting `cause.to_string().as_str()` creates a temporary String that is immediately converted to a string slice. The temporary String is dropped at the end of the statement, making the string slice invalid. This is a use-after-free bug. Instead, pass `&cause.to_string()` or use a temporary variable to store the String.

Code after:

    fn run(&mut self, task: Task) {
        debug!("run resolved-ts task"; "task" => ?task);
        if self.last_active_memory_quota_check.elapsed()
            >= self.cfg.memory_quota_active_check_interval.0
        {
            self.last_active_memory_quota_check = std::time::Instant::now();
            // Check whether memory quota is exceeded actively.
            if let Err(e) = self.memory_quota.alloc(0) {
                self.re_register_all_regions(Some(&e.to_string()));
            }
        }

        match task {
            Task::RegionDestroyed(region) => self.region_destroyed(region),
            Task::RegionUpdated(region) => self.region_updated(region),
            Task::RegisterRegion { region } => self.register_region(region, None),
            Task::DeRegisterRegion { region_id } => self.deregister_region(region_id),
            Task::ReRegisterRegion {
                region_id,
                observe_id,
                cause,
            } => self.re_register_region(region_id, observe_id, Some(&cause.to_string()), None),
            Task::AdvanceResolvedTs { leader_resolver } => {
                self.handle_advance_resolved_ts(leader_resolver)
            }
            Task::ResolvedTsAdvanced {
                regions,
                ts,
                ts_source,
            } => self.handle_resolved_ts_advanced(regions, ts, ts_source),
            Task::ChangeLog { cmd_batch } => {
                self.handle_change_log(cmd_batch);
            }
            Task::ScanLocks {
                region_id,
                observe_id,
                entries,
                apply_index,
            } => self.handle_scan_locks(region_id, observe_id, entries, apply_index),
            Task::ChangeConfig { change } => self.handle_change_config(change),
            Task::GetDiagnosisInfo {
                region_id,
                log_locks,
                min_start_ts,
                callback,
            } => self.handle_get_diagnosis_info(region_id, log_locks, min_start_ts, callback),
        }
    }
}