/* * Copyright (c) 2020 Red Hat, Inc. * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA * 02110-1301, USA. * * $Id: //eng/vdo-releases/aluminum/src/c++/vdo/base/vioPool.h#4 $ */ #ifndef VIO_POOL_H #define VIO_POOL_H #include "permassert.h" #include "completion.h" #include "types.h" #include "waitQueue.h" /** * A VIOPool is a collection of preallocated VIOs used to write arbitrary * metadata blocks. **/ /** * An VIOPoolEntry is the pair of VIO and buffer whether in use or not. **/ typedef struct { RingNode node; VIO *vio; void *buffer; void *parent; void *context; } VIOPoolEntry; /** * A function which constructs a VIO for a pool. * * @param [in] layer The physical layer in which the VIO will operate * @param [in] parent The parent of the VIO * @param [in] buffer The data buffer for the VIO * @param [out] vioPtr A pointer to hold the new VIO **/ typedef int VIOConstructor(PhysicalLayer *layer, void *parent, void *buffer, VIO **vioPtr); /** * Create a new VIO pool. * * @param [in] layer the physical layer to write to and read from * @param [in] poolSize the number of VIOs in the pool * @param [in] threadID the ID of the thread using this pool * @param [in] vioConstructor the constructor for VIOs in the pool * @param [in] context the context that each entry will have * @param [out] poolPtr the resulting pool * * @return a success or error code **/ int makeVIOPool(PhysicalLayer *layer, size_t poolSize, ThreadID threadID, VIOConstructor *vioConstructor, void *context, VIOPool **poolPtr) __attribute__((warn_unused_result)); /** * Destroy a VIO pool * * @param poolPtr the pointer holding the pool, which will be nulled out **/ void freeVIOPool(VIOPool **poolPtr); /** * Check whether an VIO pool has outstanding entries. * * @return true if the pool is busy **/ bool isVIOPoolBusy(VIOPool *pool) __attribute__((warn_unused_result)); /** * Acquire a VIO and buffer from the pool (asynchronous). * * @param pool the VIO pool * @param waiter object that is requesting a VIO * * @return VDO_SUCCESS or an error **/ int acquireVIOFromPool(VIOPool *pool, Waiter *waiter); /** * Return a VIO and its buffer to the pool. * * @param pool the VIO pool * @param entry a VIO pool entry **/ void returnVIOToPool(VIOPool *pool, VIOPoolEntry *entry); /** * Convert a RingNode to the VIOPoolEntry that contains it. * * @param node The RingNode to convert * * @return The VIOPoolEntry wrapping the RingNode **/ static inline VIOPoolEntry *asVIOPoolEntry(RingNode *node) { STATIC_ASSERT(offsetof(VIOPoolEntry, node) == 0); return (VIOPoolEntry *) node; } /** * Return the outage count of an VIO pool. * * @param pool The pool * * @return the number of times an acquisition request had to wait **/ uint64_t getVIOPoolOutageCount(VIOPool *pool) __attribute__((warn_unused_result)); #endif // VIO_POOL_H