diff options
| -rw-r--r-- | tools/virtio/ringtest/main.c | 12 | ||||
| -rw-r--r-- | tools/virtio/ringtest/main.h | 4 | ||||
| -rw-r--r-- | tools/virtio/ringtest/noring.c | 6 | ||||
| -rw-r--r-- | tools/virtio/ringtest/ptr_ring.c | 22 | ||||
| -rw-r--r-- | tools/virtio/ringtest/ring.c | 18 | ||||
| -rw-r--r-- | tools/virtio/ringtest/virtio_ring_0_9.c | 64 |
6 files changed, 43 insertions, 83 deletions
diff --git a/tools/virtio/ringtest/main.c b/tools/virtio/ringtest/main.c index bda7f0dad981..b00ecd619969 100644 --- a/tools/virtio/ringtest/main.c +++ b/tools/virtio/ringtest/main.c | |||
| @@ -96,6 +96,12 @@ void set_affinity(const char *arg) | |||
| 96 | assert(!ret); | 96 | assert(!ret); |
| 97 | } | 97 | } |
| 98 | 98 | ||
| 99 | void poll_used(void) | ||
| 100 | { | ||
| 101 | while (used_empty()) | ||
| 102 | busy_wait(); | ||
| 103 | } | ||
| 104 | |||
| 99 | static void __attribute__((__flatten__)) run_guest(void) | 105 | static void __attribute__((__flatten__)) run_guest(void) |
| 100 | { | 106 | { |
| 101 | int completed_before; | 107 | int completed_before; |
| @@ -149,6 +155,12 @@ static void __attribute__((__flatten__)) run_guest(void) | |||
| 149 | } | 155 | } |
| 150 | } | 156 | } |
| 151 | 157 | ||
| 158 | void poll_avail(void) | ||
| 159 | { | ||
| 160 | while (avail_empty()) | ||
| 161 | busy_wait(); | ||
| 162 | } | ||
| 163 | |||
| 152 | static void __attribute__((__flatten__)) run_host(void) | 164 | static void __attribute__((__flatten__)) run_host(void) |
| 153 | { | 165 | { |
| 154 | int completed_before; | 166 | int completed_before; |
diff --git a/tools/virtio/ringtest/main.h b/tools/virtio/ringtest/main.h index 16917acb0ade..34e63cc4c572 100644 --- a/tools/virtio/ringtest/main.h +++ b/tools/virtio/ringtest/main.h | |||
| @@ -56,15 +56,15 @@ void alloc_ring(void); | |||
| 56 | int add_inbuf(unsigned, void *, void *); | 56 | int add_inbuf(unsigned, void *, void *); |
| 57 | void *get_buf(unsigned *, void **); | 57 | void *get_buf(unsigned *, void **); |
| 58 | void disable_call(); | 58 | void disable_call(); |
| 59 | bool used_empty(); | ||
| 59 | bool enable_call(); | 60 | bool enable_call(); |
| 60 | void kick_available(); | 61 | void kick_available(); |
| 61 | void poll_used(); | ||
| 62 | /* host side */ | 62 | /* host side */ |
| 63 | void disable_kick(); | 63 | void disable_kick(); |
| 64 | bool avail_empty(); | ||
| 64 | bool enable_kick(); | 65 | bool enable_kick(); |
| 65 | bool use_buf(unsigned *, void **); | 66 | bool use_buf(unsigned *, void **); |
| 66 | void call_used(); | 67 | void call_used(); |
| 67 | void poll_avail(); | ||
| 68 | 68 | ||
| 69 | /* implemented by main */ | 69 | /* implemented by main */ |
| 70 | extern bool do_sleep; | 70 | extern bool do_sleep; |
diff --git a/tools/virtio/ringtest/noring.c b/tools/virtio/ringtest/noring.c index eda2f4824130..b8d1c1daac7c 100644 --- a/tools/virtio/ringtest/noring.c +++ b/tools/virtio/ringtest/noring.c | |||
| @@ -24,8 +24,9 @@ void *get_buf(unsigned *lenp, void **bufp) | |||
| 24 | return "Buffer"; | 24 | return "Buffer"; |
| 25 | } | 25 | } |
| 26 | 26 | ||
| 27 | void poll_used(void) | 27 | bool used_empty() |
| 28 | { | 28 | { |
| 29 | return false; | ||
| 29 | } | 30 | } |
| 30 | 31 | ||
| 31 | void disable_call() | 32 | void disable_call() |
| @@ -54,8 +55,9 @@ bool enable_kick() | |||
| 54 | assert(0); | 55 | assert(0); |
| 55 | } | 56 | } |
| 56 | 57 | ||
| 57 | void poll_avail(void) | 58 | bool avail_empty() |
| 58 | { | 59 | { |
| 60 | return false; | ||
| 59 | } | 61 | } |
| 60 | 62 | ||
| 61 | bool use_buf(unsigned *lenp, void **bufp) | 63 | bool use_buf(unsigned *lenp, void **bufp) |
diff --git a/tools/virtio/ringtest/ptr_ring.c b/tools/virtio/ringtest/ptr_ring.c index bd2ad1d3b7a9..635b07b4fdd3 100644 --- a/tools/virtio/ringtest/ptr_ring.c +++ b/tools/virtio/ringtest/ptr_ring.c | |||
| @@ -133,18 +133,9 @@ void *get_buf(unsigned *lenp, void **bufp) | |||
| 133 | return datap; | 133 | return datap; |
| 134 | } | 134 | } |
| 135 | 135 | ||
| 136 | void poll_used(void) | 136 | bool used_empty() |
| 137 | { | 137 | { |
| 138 | void *b; | 138 | return (tailcnt == headcnt || __ptr_ring_full(&array)); |
| 139 | |||
| 140 | do { | ||
| 141 | if (tailcnt == headcnt || __ptr_ring_full(&array)) { | ||
| 142 | b = NULL; | ||
| 143 | barrier(); | ||
| 144 | } else { | ||
| 145 | b = "Buffer\n"; | ||
| 146 | } | ||
| 147 | } while (!b); | ||
| 148 | } | 139 | } |
| 149 | 140 | ||
| 150 | void disable_call() | 141 | void disable_call() |
| @@ -173,14 +164,9 @@ bool enable_kick() | |||
| 173 | assert(0); | 164 | assert(0); |
| 174 | } | 165 | } |
| 175 | 166 | ||
| 176 | void poll_avail(void) | 167 | bool avail_empty() |
| 177 | { | 168 | { |
| 178 | void *b; | 169 | return !__ptr_ring_peek(&array); |
| 179 | |||
| 180 | do { | ||
| 181 | barrier(); | ||
| 182 | b = __ptr_ring_peek(&array); | ||
| 183 | } while (!b); | ||
| 184 | } | 170 | } |
| 185 | 171 | ||
| 186 | bool use_buf(unsigned *lenp, void **bufp) | 172 | bool use_buf(unsigned *lenp, void **bufp) |
diff --git a/tools/virtio/ringtest/ring.c b/tools/virtio/ringtest/ring.c index c25c8d248b6b..747c5dd47be8 100644 --- a/tools/virtio/ringtest/ring.c +++ b/tools/virtio/ringtest/ring.c | |||
| @@ -163,12 +163,11 @@ void *get_buf(unsigned *lenp, void **bufp) | |||
| 163 | return datap; | 163 | return datap; |
| 164 | } | 164 | } |
| 165 | 165 | ||
| 166 | void poll_used(void) | 166 | bool used_empty() |
| 167 | { | 167 | { |
| 168 | unsigned head = (ring_size - 1) & guest.last_used_idx; | 168 | unsigned head = (ring_size - 1) & guest.last_used_idx; |
| 169 | 169 | ||
| 170 | while (ring[head].flags & DESC_HW) | 170 | return (ring[head].flags & DESC_HW); |
| 171 | busy_wait(); | ||
| 172 | } | 171 | } |
| 173 | 172 | ||
| 174 | void disable_call() | 173 | void disable_call() |
| @@ -180,13 +179,11 @@ void disable_call() | |||
| 180 | 179 | ||
| 181 | bool enable_call() | 180 | bool enable_call() |
| 182 | { | 181 | { |
| 183 | unsigned head = (ring_size - 1) & guest.last_used_idx; | ||
| 184 | |||
| 185 | event->call_index = guest.last_used_idx; | 182 | event->call_index = guest.last_used_idx; |
| 186 | /* Flush call index write */ | 183 | /* Flush call index write */ |
| 187 | /* Barrier D (for pairing) */ | 184 | /* Barrier D (for pairing) */ |
| 188 | smp_mb(); | 185 | smp_mb(); |
| 189 | return ring[head].flags & DESC_HW; | 186 | return used_empty(); |
| 190 | } | 187 | } |
| 191 | 188 | ||
| 192 | void kick_available(void) | 189 | void kick_available(void) |
| @@ -213,20 +210,17 @@ void disable_kick() | |||
| 213 | 210 | ||
| 214 | bool enable_kick() | 211 | bool enable_kick() |
| 215 | { | 212 | { |
| 216 | unsigned head = (ring_size - 1) & host.used_idx; | ||
| 217 | |||
| 218 | event->kick_index = host.used_idx; | 213 | event->kick_index = host.used_idx; |
| 219 | /* Barrier C (for pairing) */ | 214 | /* Barrier C (for pairing) */ |
| 220 | smp_mb(); | 215 | smp_mb(); |
| 221 | return !(ring[head].flags & DESC_HW); | 216 | return avail_empty(); |
| 222 | } | 217 | } |
| 223 | 218 | ||
| 224 | void poll_avail(void) | 219 | bool avail_empty() |
| 225 | { | 220 | { |
| 226 | unsigned head = (ring_size - 1) & host.used_idx; | 221 | unsigned head = (ring_size - 1) & host.used_idx; |
| 227 | 222 | ||
| 228 | while (!(ring[head].flags & DESC_HW)) | 223 | return !(ring[head].flags & DESC_HW); |
| 229 | busy_wait(); | ||
| 230 | } | 224 | } |
| 231 | 225 | ||
| 232 | bool use_buf(unsigned *lenp, void **bufp) | 226 | bool use_buf(unsigned *lenp, void **bufp) |
diff --git a/tools/virtio/ringtest/virtio_ring_0_9.c b/tools/virtio/ringtest/virtio_ring_0_9.c index 761866212aac..bbc3043b2fb1 100644 --- a/tools/virtio/ringtest/virtio_ring_0_9.c +++ b/tools/virtio/ringtest/virtio_ring_0_9.c | |||
| @@ -194,24 +194,16 @@ void *get_buf(unsigned *lenp, void **bufp) | |||
| 194 | return datap; | 194 | return datap; |
| 195 | } | 195 | } |
| 196 | 196 | ||
| 197 | void poll_used(void) | 197 | bool used_empty() |
| 198 | { | 198 | { |
| 199 | unsigned short last_used_idx = guest.last_used_idx; | ||
| 199 | #ifdef RING_POLL | 200 | #ifdef RING_POLL |
| 200 | unsigned head = (ring_size - 1) & guest.last_used_idx; | 201 | unsigned short head = last_used_idx & (ring_size - 1); |
| 202 | unsigned index = ring.used->ring[head].id; | ||
| 201 | 203 | ||
| 202 | for (;;) { | 204 | return (index ^ last_used_idx ^ 0x8000) & ~(ring_size - 1); |
| 203 | unsigned index = ring.used->ring[head].id; | ||
| 204 | |||
| 205 | if ((index ^ guest.last_used_idx ^ 0x8000) & ~(ring_size - 1)) | ||
| 206 | busy_wait(); | ||
| 207 | else | ||
| 208 | break; | ||
| 209 | } | ||
| 210 | #else | 205 | #else |
| 211 | unsigned head = guest.last_used_idx; | 206 | return ring.used->idx == last_used_idx; |
| 212 | |||
| 213 | while (ring.used->idx == head) | ||
| 214 | busy_wait(); | ||
| 215 | #endif | 207 | #endif |
| 216 | } | 208 | } |
| 217 | 209 | ||
| @@ -224,22 +216,11 @@ void disable_call() | |||
| 224 | 216 | ||
| 225 | bool enable_call() | 217 | bool enable_call() |
| 226 | { | 218 | { |
| 227 | unsigned short last_used_idx; | 219 | vring_used_event(&ring) = guest.last_used_idx; |
| 228 | |||
| 229 | vring_used_event(&ring) = (last_used_idx = guest.last_used_idx); | ||
| 230 | /* Flush call index write */ | 220 | /* Flush call index write */ |
| 231 | /* Barrier D (for pairing) */ | 221 | /* Barrier D (for pairing) */ |
| 232 | smp_mb(); | 222 | smp_mb(); |
| 233 | #ifdef RING_POLL | 223 | return used_empty(); |
| 234 | { | ||
| 235 | unsigned short head = last_used_idx & (ring_size - 1); | ||
| 236 | unsigned index = ring.used->ring[head].id; | ||
| 237 | |||
| 238 | return (index ^ last_used_idx ^ 0x8000) & ~(ring_size - 1); | ||
| 239 | } | ||
| 240 | #else | ||
| 241 | return ring.used->idx == last_used_idx; | ||
| 242 | #endif | ||
| 243 | } | 224 | } |
| 244 | 225 | ||
| 245 | void kick_available(void) | 226 | void kick_available(void) |
| @@ -266,36 +247,21 @@ void disable_kick() | |||
| 266 | 247 | ||
| 267 | bool enable_kick() | 248 | bool enable_kick() |
| 268 | { | 249 | { |
| 269 | unsigned head = host.used_idx; | 250 | vring_avail_event(&ring) = host.used_idx; |
| 270 | |||
| 271 | vring_avail_event(&ring) = head; | ||
| 272 | /* Barrier C (for pairing) */ | 251 | /* Barrier C (for pairing) */ |
| 273 | smp_mb(); | 252 | smp_mb(); |
| 274 | #ifdef RING_POLL | 253 | return avail_empty(); |
| 275 | { | ||
| 276 | unsigned index = ring.avail->ring[head & (ring_size - 1)]; | ||
| 277 | |||
| 278 | return (index ^ head ^ 0x8000) & ~(ring_size - 1); | ||
| 279 | } | ||
| 280 | #else | ||
| 281 | return head == ring.avail->idx; | ||
| 282 | #endif | ||
| 283 | } | 254 | } |
| 284 | 255 | ||
| 285 | void poll_avail(void) | 256 | bool avail_empty() |
| 286 | { | 257 | { |
| 287 | unsigned head = host.used_idx; | 258 | unsigned head = host.used_idx; |
| 288 | #ifdef RING_POLL | 259 | #ifdef RING_POLL |
| 289 | for (;;) { | 260 | unsigned index = ring.avail->ring[head & (ring_size - 1)]; |
| 290 | unsigned index = ring.avail->ring[head & (ring_size - 1)]; | 261 | |
| 291 | if ((index ^ head ^ 0x8000) & ~(ring_size - 1)) | 262 | return ((index ^ head ^ 0x8000) & ~(ring_size - 1)); |
| 292 | busy_wait(); | ||
| 293 | else | ||
| 294 | break; | ||
| 295 | } | ||
| 296 | #else | 263 | #else |
| 297 | while (ring.avail->idx == head) | 264 | return head == ring.avail->idx; |
| 298 | busy_wait(); | ||
| 299 | #endif | 265 | #endif |
| 300 | } | 266 | } |
| 301 | 267 | ||
