1 /* 2 * Copyright 2013, Jérôme Duval, korli@users.berlios.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 #ifndef VIRTIO_PRIVATE_H 6 #define VIRTIO_PRIVATE_H 7 8 9 #include <new> 10 #include <stdio.h> 11 #include <string.h> 12 13 #include <lock.h> 14 #include <util/AutoLock.h> 15 #include <virtio.h> 16 17 #include "virtio_ring.h" 18 19 20 //#define VIRTIO_TRACE 21 #ifdef VIRTIO_TRACE 22 # define TRACE(x...) dprintf("\33[33mvirtio:\33[0m " x) 23 #else 24 # define TRACE(x...) 25 #endif 26 #define TRACE_ALWAYS(x...) dprintf("\33[33mvirtio:\33[0m " x) 27 #define ERROR(x...) TRACE_ALWAYS(x) 28 #define CALLED() TRACE("CALLED %s\n", __PRETTY_FUNCTION__) 29 30 31 #define VIRTIO_SIM_MODULE_NAME "bus_managers/virtio/sim/driver_v1" 32 33 34 class VirtioDevice; 35 class VirtioQueue; 36 37 extern device_manager_info *gDeviceManager; 38 39 40 class VirtioDevice { 41 public: 42 VirtioDevice(device_node *node); 43 ~VirtioDevice(); 44 45 status_t InitCheck(); 46 uint32 ID() const { return fID; } 47 48 status_t NegotiateFeatures(uint32 supported, 49 uint32* negotiated, 50 const char* (*get_feature_name)(uint32)); 51 52 status_t ReadDeviceConfig(uint8 offset, void* buffer, 53 size_t bufferSize); 54 status_t WriteDeviceConfig(uint8 offset, 55 const void* buffer, size_t bufferSize); 56 57 status_t AllocateQueues(size_t count, 58 virtio_queue *queues); 59 void FreeQueues(); 60 status_t SetupInterrupt(virtio_intr_func config_handler, 61 void *driverCookie); 62 status_t FreeInterrupts(); 63 64 uint16 Alignment() const { return fAlignment; } 65 uint32 Features() const { return fFeatures; } 66 67 void* DriverCookie() { return fDriverCookie; } 68 69 status_t SetupQueue(uint16 queueNumber, 70 phys_addr_t physAddr); 71 void NotifyQueue(uint16 queueNumber); 72 73 status_t QueueInterrupt(uint16 queueNumber); 74 status_t ConfigInterrupt(); 75 76 private: 77 void _DumpFeatures(const char* title, 78 uint32 features, 79 const char* (*get_feature_name)(uint32)); 80 void _DestroyQueues(size_t count); 81 82 83 84 device_node * fNode; 85 uint32 fID; 86 virtio_sim_interface *fController; 87 void * fCookie; 88 status_t fStatus; 89 VirtioQueue** fQueues; 90 size_t fQueueCount; 91 uint32 fFeatures; 92 uint16 fAlignment; 93 94 virtio_intr_func fConfigHandler; 95 void* fDriverCookie; 96 }; 97 98 99 class TransferDescriptor; 100 101 102 class VirtioQueue { 103 public: 104 VirtioQueue(VirtioDevice *device, 105 uint16 queueNumber, uint16 ringSize); 106 ~VirtioQueue(); 107 status_t InitCheck() { return fStatus; } 108 109 void NotifyHost(); 110 status_t Interrupt(); 111 112 bool IsFull() const { return fRingFree == 0; } 113 bool IsEmpty() const { return fRingFree == fRingSize; } 114 uint16 Size() const { return fRingSize; } 115 116 VirtioDevice* Device() { return fDevice; } 117 118 status_t QueueRequest(const physical_entry* vector, 119 size_t readVectorCount, 120 size_t writtenVectorCount, 121 void *cookie); 122 status_t QueueRequestIndirect( 123 const physical_entry* vector, 124 size_t readVectorCount, 125 size_t writtenVectorCount, 126 void *cookie); 127 128 status_t SetupInterrupt(virtio_callback_func handler, 129 void *cookie); 130 131 void EnableInterrupt(); 132 void DisableInterrupt(); 133 134 void* Dequeue(uint16* _size = NULL); 135 136 private: 137 void UpdateAvailable(uint16 index); 138 uint16 QueueVector(uint16 insertIndex, 139 struct vring_desc *desc, 140 const physical_entry* vector, 141 size_t readVectorCount, 142 size_t writtenVectorCount); 143 144 VirtioDevice* fDevice; 145 uint16 fQueueNumber; 146 uint16 fRingSize; 147 uint16 fRingFree; 148 149 struct vring fRing; 150 uint16 fRingHeadIndex; 151 uint16 fRingUsedIndex; 152 status_t fStatus; 153 size_t fAreaSize; 154 area_id fArea; 155 156 uint16 fIndirectMaxSize; 157 158 TransferDescriptor** fDescriptors; 159 160 virtio_callback_func fCallback; 161 void* fCookie; 162 163 }; 164 165 #endif // VIRTIO_PRIVATE_H 166