Blame source/vdo/base/slabSummary.h

Packit Service 75d76b
/*
Packit Service 75d76b
 * Copyright (c) 2020 Red Hat, Inc.
Packit Service 75d76b
 *
Packit Service 75d76b
 * This program is free software; you can redistribute it and/or
Packit Service 75d76b
 * modify it under the terms of the GNU General Public License
Packit Service 75d76b
 * as published by the Free Software Foundation; either version 2
Packit Service 75d76b
 * of the License, or (at your option) any later version.
Packit Service 75d76b
 * 
Packit Service 75d76b
 * This program is distributed in the hope that it will be useful,
Packit Service 75d76b
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
Packit Service 75d76b
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
Packit Service 75d76b
 * GNU General Public License for more details.
Packit Service 75d76b
 * 
Packit Service 75d76b
 * You should have received a copy of the GNU General Public License
Packit Service 75d76b
 * along with this program; if not, write to the Free Software
Packit Service 75d76b
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
Packit Service 75d76b
 * 02110-1301, USA. 
Packit Service 75d76b
 *
Packit Service 75d76b
 * $Id: //eng/vdo-releases/aluminum/src/c++/vdo/base/slabSummary.h#5 $
Packit Service 75d76b
 */
Packit Service 75d76b
Packit Service 75d76b
#ifndef SLAB_SUMMARY_H
Packit Service 75d76b
#define SLAB_SUMMARY_H
Packit Service 75d76b
Packit Service 75d76b
#include "completion.h"
Packit Service 75d76b
#include "fixedLayout.h"
Packit Service 75d76b
#include "slab.h"
Packit Service 75d76b
#include "statistics.h"
Packit Service 75d76b
#include "types.h"
Packit Service 75d76b
#include "waitQueue.h"
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * The SlabSummary provides hints during load and recovery about the state
Packit Service 75d76b
 * of the slabs in order to avoid the need to read the slab journals in their
Packit Service 75d76b
 * entirety before a VDO can come online.
Packit Service 75d76b
 *
Packit Service 75d76b
 * The information in the summary for each slab includes the rough number of
Packit Service 75d76b
 * free blocks (which is used to prioritize scrubbing), the cleanliness of a
Packit Service 75d76b
 * slab (so that clean slabs containing free space will be used on restart),
Packit Service 75d76b
 * and the location of the tail block of the slab's journal.
Packit Service 75d76b
 *
Packit Service 75d76b
 * The SlabSummary has its own partition at the end of the volume which is
Packit Service 75d76b
 * sized to allow for a complete copy of the summary for each of up to 16
Packit Service 75d76b
 * physical zones.
Packit Service 75d76b
 *
Packit Service 75d76b
 * During resize, the SlabSummary moves its backing partition and is saved once
Packit Service 75d76b
 * moved; the SlabSummary is not permitted to overwrite the previous recovery
Packit Service 75d76b
 * journal space.
Packit Service 75d76b
 *
Packit Service 75d76b
 * The SlabSummary does not have its own version information, but relies on the
Packit Service 75d76b
 * master version number.
Packit Service 75d76b
 **/
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * The offset of a slab journal tail block.
Packit Service 75d76b
 **/
Packit Service 75d76b
typedef uint8_t TailBlockOffset;
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * A slab status is a very small structure for use in determining the ordering
Packit Service 75d76b
 * of slabs in the scrubbing process.
Packit Service 75d76b
 **/
Packit Service 75d76b
typedef struct slabStatus {
Packit Service 75d76b
  SlabCount slabNumber;
Packit Service 75d76b
  bool      isClean;
Packit Service 75d76b
  uint8_t   emptiness;
Packit Service 75d76b
} SlabStatus;
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Returns the size on disk of the SlabSummary structure.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param blockSize  The block size of the physical layer
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return the blocks required to store the SlabSummary on disk
Packit Service 75d76b
 **/
Packit Service 75d76b
BlockCount getSlabSummarySize(BlockSize blockSize)
Packit Service 75d76b
__attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Create a slab summary.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param [in]  layer                     The layer
Packit Service 75d76b
 * @param [in]  partition                 The partition to hold the summary
Packit Service 75d76b
 * @param [in]  threadConfig              The thread config of the VDO
Packit Service 75d76b
 * @param [in]  slabSizeShift             The number of bits in the slab size
Packit Service 75d76b
 * @param [in]  maximumFreeBlocksPerSlab  The maximum number of free blocks a
Packit Service 75d76b
 *                                        slab can have
Packit Service 75d76b
 * @param [in]  readOnlyNotifier          The context for entering read-only
Packit Service 75d76b
 *                                        mode
Packit Service 75d76b
 * @param [out] slabSummaryPtr            A pointer to hold the summary
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return VDO_SUCCESS or an error
Packit Service 75d76b
 **/
Packit Service 75d76b
int makeSlabSummary(PhysicalLayer       *layer,
Packit Service 75d76b
                    Partition           *partition,
Packit Service 75d76b
                    const ThreadConfig  *threadConfig,
Packit Service 75d76b
                    unsigned int         slabSizeShift,
Packit Service 75d76b
                    BlockCount           maximumFreeBlocksPerSlab,
Packit Service 75d76b
                    ReadOnlyNotifier    *readOnlyNotifier,
Packit Service 75d76b
                    SlabSummary        **slabSummaryPtr)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Destroy a SlabSummary and NULL out the reference to it.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param [in,out] slabSummaryPtr A pointer to the SlabSummary to free
Packit Service 75d76b
 **/
Packit Service 75d76b
void freeSlabSummary(SlabSummary **slabSummaryPtr);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the portion of the slab summary for a specified zone.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summary  The slab summary
Packit Service 75d76b
 * @param zone     The zone
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return The portion of the slab summary for the specified zone
Packit Service 75d76b
 **/
Packit Service 75d76b
SlabSummaryZone *getSummaryForZone(SlabSummary *summary, ZoneCount zone)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Drain a zone of the slab summary.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone  The zone to drain
Packit Service 75d76b
 * @param operation    The type of drain to perform
Packit Service 75d76b
 * @param parent       The object to notify when the suspend is complete
Packit Service 75d76b
 **/
Packit Service 75d76b
void drainSlabSummaryZone(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                          AdminStateCode   operation,
Packit Service 75d76b
                          VDOCompletion   *parent);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Resume a zone of the slab summary.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone  The zone to resume
Packit Service 75d76b
 * @param parent       The object to notify when the zone is resumed
Packit Service 75d76b
 **/
Packit Service 75d76b
void resumeSlabSummaryZone(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                           VDOCompletion   *parent);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Update the entry for a slab.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone     The SlabSummaryZone for the zone of the slab
Packit Service 75d76b
 * @param waiter          The waiter that is updating the summary
Packit Service 75d76b
 * @param slabNumber      The slab number to update
Packit Service 75d76b
 * @param tailBlockOffset The offset of slab journal's tail block
Packit Service 75d76b
 * @param loadRefCounts   Whether the refCounts must be loaded from the layer
Packit Service 75d76b
 *                        on the next load
Packit Service 75d76b
 * @param isClean         Whether the slab is clean
Packit Service 75d76b
 * @param freeBlocks      The number of free blocks
Packit Service 75d76b
 **/
Packit Service 75d76b
void updateSlabSummaryEntry(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                            Waiter          *waiter,
Packit Service 75d76b
                            SlabCount        slabNumber,
Packit Service 75d76b
                            TailBlockOffset  tailBlockOffset,
Packit Service 75d76b
                            bool             loadRefCounts,
Packit Service 75d76b
                            bool             isClean,
Packit Service 75d76b
                            BlockCount       freeBlocks);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the stored tail block offset for a slab.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone       The SlabSummaryZone to use
Packit Service 75d76b
 * @param slabNumber        The slab number to get the offset for
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return The tail block offset for the slab
Packit Service 75d76b
 **/
Packit Service 75d76b
TailBlockOffset getSummarizedTailBlockOffset(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                                             SlabCount        slabNumber)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Whether refCounts must be loaded from the layer.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone   The SlabSummaryZone to use
Packit Service 75d76b
 * @param slabNumber    The slab number to get information for
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return Whether refCounts must be loaded
Packit Service 75d76b
 **/
Packit Service 75d76b
bool mustLoadRefCounts(SlabSummaryZone *summaryZone, SlabCount slabNumber)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the stored cleanliness information for a single slab.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone   The SlabSummaryZone to use
Packit Service 75d76b
 * @param slabNumber    The slab number to get information for
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return Whether the slab is clean
Packit Service 75d76b
 **/
Packit Service 75d76b
bool getSummarizedCleanliness(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                              SlabCount        slabNumber)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the stored emptiness information for a single slab.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summaryZone    The SlabSummaryZone to use
Packit Service 75d76b
 * @param slabNumber     The slab number to get information for
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return An approximation to the free blocks in the slab
Packit Service 75d76b
 **/
Packit Service 75d76b
BlockCount getSummarizedFreeBlockCount(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                                       SlabCount        slabNumber)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the stored RefCounts state information for a single slab. Used
Packit Service 75d76b
 * in testing only.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param [in]  summaryZone     The SlabSummaryZone to use
Packit Service 75d76b
 * @param [in]  slabNumber      The slab number to get information for
Packit Service 75d76b
 * @param [out] freeBlockHint   The approximate number of free blocks
Packit Service 75d76b
 * @param [out] isClean         Whether the slab is clean
Packit Service 75d76b
 **/
Packit Service 75d76b
void getSummarizedRefCountsState(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                                 SlabCount        slabNumber,
Packit Service 75d76b
                                 size_t          *freeBlockHint,
Packit Service 75d76b
                                 bool            *isClean);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Get the stored slab statuses for all slabs in a zone.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param [in]     summaryZone   The SlabSummaryZone to use
Packit Service 75d76b
 * @param [in]     slabCount     The number of slabs to fetch
Packit Service 75d76b
 * @param [in,out] statuses      An array of SlabStatuses to populate
Packit Service 75d76b
 **/
Packit Service 75d76b
void getSummarizedSlabStatuses(SlabSummaryZone *summaryZone,
Packit Service 75d76b
                               SlabCount        slabCount,
Packit Service 75d76b
                               SlabStatus      *statuses);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Set the origin of the slab summary relative to the physical layer.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summary    The SlabSummary to update
Packit Service 75d76b
 * @param partition  The slab summary partition
Packit Service 75d76b
 **/
Packit Service 75d76b
void setSlabSummaryOrigin(SlabSummary *summary, Partition *partition);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Read in all the slab summary data from the slab summary partition,
Packit Service 75d76b
 * combine all the previously used zones into a single zone, and then
Packit Service 75d76b
 * write the combined summary back out to each possible zones' summary
Packit Service 75d76b
 * region.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summary         The summary to load
Packit Service 75d76b
 * @param operation       The type of load to perform
Packit Service 75d76b
 * @param zonesToCombine  The number of zones to be combined; if set to 0,
Packit Service 75d76b
 *                        all of the summary will be initialized as new.
Packit Service 75d76b
 * @param parent          The parent of this operation
Packit Service 75d76b
 **/
Packit Service 75d76b
void loadSlabSummary(SlabSummary    *summary,
Packit Service 75d76b
                     AdminStateCode  operation,
Packit Service 75d76b
                     ZoneCount       zonesToCombine,
Packit Service 75d76b
                     VDOCompletion  *parent);
Packit Service 75d76b
Packit Service 75d76b
/**
Packit Service 75d76b
 * Fetch the cumulative statistics for all slab summary zones in a summary.
Packit Service 75d76b
 *
Packit Service 75d76b
 * @param summary       The summary in question
Packit Service 75d76b
 *
Packit Service 75d76b
 * @return the cumulative slab summary statistics for the summary
Packit Service 75d76b
 **/
Packit Service 75d76b
SlabSummaryStatistics getSlabSummaryStatistics(const SlabSummary *summary)
Packit Service 75d76b
  __attribute__((warn_unused_result));
Packit Service 75d76b
Packit Service 75d76b
#endif // SLAB_SUMMARY_H