linux/include/linux/virtio_config.h
<<
>>
Prefs
   1#ifndef _LINUX_VIRTIO_CONFIG_H
   2#define _LINUX_VIRTIO_CONFIG_H
   3/* This header, excluding the #ifdef __KERNEL__ part, is BSD licensed so
   4 * anyone can use the definitions to implement compatible drivers/servers.
   5 *
   6 * Redistribution and use in source and binary forms, with or without
   7 * modification, are permitted provided that the following conditions
   8 * are met:
   9 * 1. Redistributions of source code must retain the above copyright
  10 *    notice, this list of conditions and the following disclaimer.
  11 * 2. Redistributions in binary form must reproduce the above copyright
  12 *    notice, this list of conditions and the following disclaimer in the
  13 *    documentation and/or other materials provided with the distribution.
  14 * 3. Neither the name of IBM nor the names of its contributors
  15 *    may be used to endorse or promote products derived from this software
  16 *    without specific prior written permission.
  17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND
  18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  20 * ARE DISCLAIMED.  IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE
  21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  27 * SUCH DAMAGE. */
  28
  29/* Virtio devices use a standardized configuration space to define their
  30 * features and pass configuration information, but each implementation can
  31 * store and access that space differently. */
  32#include <linux/types.h>
  33
  34/* Status byte for guest to report progress, and synchronize features. */
  35/* We have seen device and processed generic fields (VIRTIO_CONFIG_F_VIRTIO) */
  36#define VIRTIO_CONFIG_S_ACKNOWLEDGE     1
  37/* We have found a driver for the device. */
  38#define VIRTIO_CONFIG_S_DRIVER          2
  39/* Driver has used its parts of the config, and is happy */
  40#define VIRTIO_CONFIG_S_DRIVER_OK       4
  41/* We've given up on this device. */
  42#define VIRTIO_CONFIG_S_FAILED          0x80
  43
  44/* Some virtio feature bits (currently bits 28 through 31) are reserved for the
  45 * transport being used (eg. virtio_ring), the rest are per-device feature
  46 * bits. */
  47#define VIRTIO_TRANSPORT_F_START        28
  48#define VIRTIO_TRANSPORT_F_END          32
  49
  50/* Do we get callbacks when the ring is completely used, even if we've
  51 * suppressed them? */
  52#define VIRTIO_F_NOTIFY_ON_EMPTY        24
  53
  54#ifdef __KERNEL__
  55#include <linux/err.h>
  56#include <linux/bug.h>
  57#include <linux/virtio.h>
  58
  59/**
  60 * virtio_config_ops - operations for configuring a virtio device
  61 * @get: read the value of a configuration field
  62 *      vdev: the virtio_device
  63 *      offset: the offset of the configuration field
  64 *      buf: the buffer to write the field value into.
  65 *      len: the length of the buffer
  66 * @set: write the value of a configuration field
  67 *      vdev: the virtio_device
  68 *      offset: the offset of the configuration field
  69 *      buf: the buffer to read the field value from.
  70 *      len: the length of the buffer
  71 * @get_status: read the status byte
  72 *      vdev: the virtio_device
  73 *      Returns the status byte
  74 * @set_status: write the status byte
  75 *      vdev: the virtio_device
  76 *      status: the new status byte
  77 * @reset: reset the device
  78 *      vdev: the virtio device
  79 *      After this, status and feature negotiation must be done again
  80 *      Device must not be reset from its vq/config callbacks, or in
  81 *      parallel with being added/removed.
  82 * @find_vqs: find virtqueues and instantiate them.
  83 *      vdev: the virtio_device
  84 *      nvqs: the number of virtqueues to find
  85 *      vqs: on success, includes new virtqueues
  86 *      callbacks: array of callbacks, for each virtqueue
  87 *      names: array of virtqueue names (mainly for debugging)
  88 *      Returns 0 on success or error status
  89 * @del_vqs: free virtqueues found by find_vqs().
  90 * @get_features: get the array of feature bits for this device.
  91 *      vdev: the virtio_device
  92 *      Returns the first 32 feature bits (all we currently need).
  93 * @finalize_features: confirm what device features we'll be using.
  94 *      vdev: the virtio_device
  95 *      This gives the final feature bits for the device: it can change
  96 *      the dev->feature bits if it wants.
  97 * @bus_name: return the bus name associated with the device
  98 *      vdev: the virtio_device
  99 *      This returns a pointer to the bus name a la pci_name from which
 100 *      the caller can then copy.
 101 */
 102typedef void vq_callback_t(struct virtqueue *);
 103struct virtio_config_ops {
 104        void (*get)(struct virtio_device *vdev, unsigned offset,
 105                    void *buf, unsigned len);
 106        void (*set)(struct virtio_device *vdev, unsigned offset,
 107                    const void *buf, unsigned len);
 108        u8 (*get_status)(struct virtio_device *vdev);
 109        void (*set_status)(struct virtio_device *vdev, u8 status);
 110        void (*reset)(struct virtio_device *vdev);
 111        int (*find_vqs)(struct virtio_device *, unsigned nvqs,
 112                        struct virtqueue *vqs[],
 113                        vq_callback_t *callbacks[],
 114                        const char *names[]);
 115        void (*del_vqs)(struct virtio_device *);
 116        u32 (*get_features)(struct virtio_device *vdev);
 117        void (*finalize_features)(struct virtio_device *vdev);
 118        const char *(*bus_name)(struct virtio_device *vdev);
 119};
 120
 121/* If driver didn't advertise the feature, it will never appear. */
 122void virtio_check_driver_offered_feature(const struct virtio_device *vdev,
 123                                         unsigned int fbit);
 124
 125/**
 126 * virtio_has_feature - helper to determine if this device has this feature.
 127 * @vdev: the device
 128 * @fbit: the feature bit
 129 */
 130static inline bool virtio_has_feature(const struct virtio_device *vdev,
 131                                      unsigned int fbit)
 132{
 133        /* Did you forget to fix assumptions on max features? */
 134        if (__builtin_constant_p(fbit))
 135                BUILD_BUG_ON(fbit >= 32);
 136        else
 137                BUG_ON(fbit >= 32);
 138
 139        if (fbit < VIRTIO_TRANSPORT_F_START)
 140                virtio_check_driver_offered_feature(vdev, fbit);
 141
 142        return test_bit(fbit, vdev->features);
 143}
 144
 145/**
 146 * virtio_config_val - look for a feature and get a virtio config entry.
 147 * @vdev: the virtio device
 148 * @fbit: the feature bit
 149 * @offset: the type to search for.
 150 * @v: a pointer to the value to fill in.
 151 *
 152 * The return value is -ENOENT if the feature doesn't exist.  Otherwise
 153 * the config value is copied into whatever is pointed to by v. */
 154#define virtio_config_val(vdev, fbit, offset, v) \
 155        virtio_config_buf((vdev), (fbit), (offset), (v), sizeof(*v))
 156
 157#define virtio_config_val_len(vdev, fbit, offset, v, len) \
 158        virtio_config_buf((vdev), (fbit), (offset), (v), (len))
 159
 160static inline int virtio_config_buf(struct virtio_device *vdev,
 161                                    unsigned int fbit,
 162                                    unsigned int offset,
 163                                    void *buf, unsigned len)
 164{
 165        if (!virtio_has_feature(vdev, fbit))
 166                return -ENOENT;
 167
 168        vdev->config->get(vdev, offset, buf, len);
 169        return 0;
 170}
 171
 172static inline
 173struct virtqueue *virtio_find_single_vq(struct virtio_device *vdev,
 174                                        vq_callback_t *c, const char *n)
 175{
 176        vq_callback_t *callbacks[] = { c };
 177        const char *names[] = { n };
 178        struct virtqueue *vq;
 179        int err = vdev->config->find_vqs(vdev, 1, &vq, callbacks, names);
 180        if (err < 0)
 181                return ERR_PTR(err);
 182        return vq;
 183}
 184
 185static inline
 186const char *virtio_bus_name(struct virtio_device *vdev)
 187{
 188        if (!vdev->config->bus_name)
 189                return "virtio";
 190        return vdev->config->bus_name(vdev);
 191}
 192
 193#endif /* __KERNEL__ */
 194#endif /* _LINUX_VIRTIO_CONFIG_H */
 195
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.