Repository: firecracker-microvm/firecracker
File: src/vmm/src/devices/acpi/vmclock.rs (Rust)

Code before:
        let mut inner = vmclock_abi {
            magic: VMCLOCK_MAGIC,
            size: VMCLOCK_SIZE,
            version: 1,
            clock_status: VMCLOCK_STATUS_UNKNOWN,
            counter_id: VMCLOCK_COUNTER_INVALID,
            flags: VMCLOCK_FLAG_VM_GEN_COUNTER_PRESENT | VMCLOCK_FLAG_NOTIFICATION_PRESENT,
            ..Default::default()
        };

        VmClock {
            guest_address: GuestAddress(addr),
            interrupt_evt,
            gsi,
            inner,
        }
    }

    /// Activate [`VmClock`] device
    pub fn activate(&self, mem: &GuestMemoryMmap) -> Result<(), GuestMemoryError> {
        mem.write_slice(self.inner.as_slice(), self.guest_address)?;
        Ok(())
    }

    /// Bump the VM generation counter and notify guest after snapshot restore
    pub fn post_restore(&mut self, mem: &GuestMemoryMmap) {
        write_vmclock_field!(self, mem, seq_count, self.inner.seq_count | 1);

        // This fence ensures guest sees all previous writes. It is matched to a
        // read barrier in the guest.
        fence(Ordering::Release);

        write_vmclock_field!(
            self,
            mem,
            disruption_marker,
            self.inner.disruption_marker.wrapping_add(1)
        );

        write_vmclock_field!(
            self,
            mem,
            vm_generation_counter,
            self.inner.vm_generation_counter.wrapping_add(1)
        );

        // This fence ensures guest sees the `disruption_marker` and `vm_generation_counter`
        // updates. It is matched to a read barrier in the guest.
        fence(Ordering::Release);

        write_vmclock_field!(self, mem, seq_count, self.inner.seq_count.wrapping_add(1));

Review comment (suggestion):
This is a nit, so feel free to disagree/ignore: 

I feel like the function name `post_restore` doesn't immediately make it clear that we're doing something that might alter the program state. I think something like `do_post_restore` makes it easier to tell from a glance that we're mutating something.

Code after:
                VMCLOCK_SIZE as u64,
                AllocPolicy::LastMatch,
            )
            .map_err(VmClockError::AllocateMemory)?;

        let gsi = resource_allocator
            .allocate_gsi_legacy(1)
            .map_err(VmClockError::AllocateGsi)?[0];

        let interrupt_evt = EventFdTrigger::new(
            EventFd::new(libc::EFD_NONBLOCK).map_err(VmClockError::CreateEventFd)?,
        );

        let mut inner = vmclock_abi {
            magic: VMCLOCK_MAGIC,
            size: VMCLOCK_SIZE,
            version: 1,
            clock_status: VMCLOCK_STATUS_UNKNOWN,
            counter_id: VMCLOCK_COUNTER_INVALID,
            flags: VMCLOCK_FLAG_VM_GEN_COUNTER_PRESENT | VMCLOCK_FLAG_NOTIFICATION_PRESENT,
            ..Default::default()
        };

        Ok(VmClock {
            guest_address: GuestAddress(addr),
            interrupt_evt,
            gsi,
            inner,
        })
    }

    /// Activate [`VmClock`] device
    pub fn activate(&self, mem: &GuestMemoryMmap) -> Result<(), VmClockError> {
        mem.write_slice(self.inner.as_slice(), self.guest_address)?;
        Ok(())
    }

    /// Bump the VM generation counter and notify guest after snapshot restore
    pub fn post_restore(&mut self, mem: &GuestMemoryMmap) -> Result<(), VmClockError> {
        write_vmclock_field!(self, mem, seq_count, self.inner.seq_count | 1);

        // This fence ensures guest sees all previous writes. It is matched to a
        // read barrier in the guest.
        fence(Ordering::Release);

        write_vmclock_field!(
            self,
            mem,
            disruption_marker,
            self.inner.disruption_marker.wrapping_add(1)
        );