aboutsummaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2016-05-24 12:46:45 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2016-05-24 12:46:45 -0400
commitecaba7185894778c24895356d117a7f92e3c92de (patch)
tree03567db9d31a453f4262c923c9717e4d394e6881 /tools
parente989cc564691901d42e957059592fe3e7b6893fc (diff)
parentbb991288728e6a47a6f0fac6a4e9dfaeecc27956 (diff)
Merge tag 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost
Pull virtio updates from Michael Tsirkin: "Looks like a quiet cycle for virtio. There's a new inorder option for the ringtest tool, and a bugfix for balloon for ppc platforms when using virtio 1 mode" * tag 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost: ringtest: pass buf != NULL virtio_balloon: fix PFN format for virtio-1 virtio: add inorder option
Diffstat (limited to 'tools')
-rw-r--r--tools/virtio/ringtest/Makefile5
-rw-r--r--tools/virtio/ringtest/main.c2
-rw-r--r--tools/virtio/ringtest/virtio_ring_0_9.c49
-rw-r--r--tools/virtio/ringtest/virtio_ring_inorder.c2
4 files changed, 55 insertions, 3 deletions
diff --git a/tools/virtio/ringtest/Makefile b/tools/virtio/ringtest/Makefile
index feaa64ac4630..6ba745529833 100644
--- a/tools/virtio/ringtest/Makefile
+++ b/tools/virtio/ringtest/Makefile
@@ -1,6 +1,6 @@
1all: 1all:
2 2
3all: ring virtio_ring_0_9 virtio_ring_poll 3all: ring virtio_ring_0_9 virtio_ring_poll virtio_ring_inorder
4 4
5CFLAGS += -Wall 5CFLAGS += -Wall
6CFLAGS += -pthread -O2 -ggdb 6CFLAGS += -pthread -O2 -ggdb
@@ -10,13 +10,16 @@ main.o: main.c main.h
10ring.o: ring.c main.h 10ring.o: ring.c main.h
11virtio_ring_0_9.o: virtio_ring_0_9.c main.h 11virtio_ring_0_9.o: virtio_ring_0_9.c main.h
12virtio_ring_poll.o: virtio_ring_poll.c virtio_ring_0_9.c main.h 12virtio_ring_poll.o: virtio_ring_poll.c virtio_ring_0_9.c main.h
13virtio_ring_inorder.o: virtio_ring_inorder.c virtio_ring_0_9.c main.h
13ring: ring.o main.o 14ring: ring.o main.o
14virtio_ring_0_9: virtio_ring_0_9.o main.o 15virtio_ring_0_9: virtio_ring_0_9.o main.o
15virtio_ring_poll: virtio_ring_poll.o main.o 16virtio_ring_poll: virtio_ring_poll.o main.o
17virtio_ring_inorder: virtio_ring_inorder.o main.o
16clean: 18clean:
17 -rm main.o 19 -rm main.o
18 -rm ring.o ring 20 -rm ring.o ring
19 -rm virtio_ring_0_9.o virtio_ring_0_9 21 -rm virtio_ring_0_9.o virtio_ring_0_9
20 -rm virtio_ring_poll.o virtio_ring_poll 22 -rm virtio_ring_poll.o virtio_ring_poll
23 -rm virtio_ring_inorder.o virtio_ring_inorder
21 24
22.PHONY: all clean 25.PHONY: all clean
diff --git a/tools/virtio/ringtest/main.c b/tools/virtio/ringtest/main.c
index 3a5ff438bd62..147abb452a6c 100644
--- a/tools/virtio/ringtest/main.c
+++ b/tools/virtio/ringtest/main.c
@@ -115,7 +115,7 @@ static void run_guest(void)
115 do { 115 do {
116 if (started < bufs && 116 if (started < bufs &&
117 started - completed < max_outstanding) { 117 started - completed < max_outstanding) {
118 r = add_inbuf(0, NULL, "Hello, world!"); 118 r = add_inbuf(0, "Buffer\n", "Hello, world!");
119 if (__builtin_expect(r == 0, true)) { 119 if (__builtin_expect(r == 0, true)) {
120 ++started; 120 ++started;
121 if (!--tokick) { 121 if (!--tokick) {
diff --git a/tools/virtio/ringtest/virtio_ring_0_9.c b/tools/virtio/ringtest/virtio_ring_0_9.c
index 47c9a1a18d36..761866212aac 100644
--- a/tools/virtio/ringtest/virtio_ring_0_9.c
+++ b/tools/virtio/ringtest/virtio_ring_0_9.c
@@ -26,6 +26,14 @@ struct vring ring;
26 * high bits of ring id ^ 0x8000). 26 * high bits of ring id ^ 0x8000).
27 */ 27 */
28/* #ifdef RING_POLL */ 28/* #ifdef RING_POLL */
29/* enabling the below activates experimental in-order code
30 * (which skips ring updates and reads and writes len in descriptor).
31 */
32/* #ifdef INORDER */
33
34#if defined(RING_POLL) && defined(INORDER)
35#error "RING_POLL and INORDER are mutually exclusive"
36#endif
29 37
30/* how much padding is needed to avoid false cache sharing */ 38/* how much padding is needed to avoid false cache sharing */
31#define HOST_GUEST_PADDING 0x80 39#define HOST_GUEST_PADDING 0x80
@@ -35,7 +43,11 @@ struct guest {
35 unsigned short last_used_idx; 43 unsigned short last_used_idx;
36 unsigned short num_free; 44 unsigned short num_free;
37 unsigned short kicked_avail_idx; 45 unsigned short kicked_avail_idx;
46#ifndef INORDER
38 unsigned short free_head; 47 unsigned short free_head;
48#else
49 unsigned short reserved_free_head;
50#endif
39 unsigned char reserved[HOST_GUEST_PADDING - 10]; 51 unsigned char reserved[HOST_GUEST_PADDING - 10];
40} guest; 52} guest;
41 53
@@ -66,8 +78,10 @@ void alloc_ring(void)
66 guest.avail_idx = 0; 78 guest.avail_idx = 0;
67 guest.kicked_avail_idx = -1; 79 guest.kicked_avail_idx = -1;
68 guest.last_used_idx = 0; 80 guest.last_used_idx = 0;
81#ifndef INORDER
69 /* Put everything in free lists. */ 82 /* Put everything in free lists. */
70 guest.free_head = 0; 83 guest.free_head = 0;
84#endif
71 for (i = 0; i < ring_size - 1; i++) 85 for (i = 0; i < ring_size - 1; i++)
72 ring.desc[i].next = i + 1; 86 ring.desc[i].next = i + 1;
73 host.used_idx = 0; 87 host.used_idx = 0;
@@ -84,13 +98,20 @@ void alloc_ring(void)
84/* guest side */ 98/* guest side */
85int add_inbuf(unsigned len, void *buf, void *datap) 99int add_inbuf(unsigned len, void *buf, void *datap)
86{ 100{
87 unsigned head, avail; 101 unsigned head;
102#ifndef INORDER
103 unsigned avail;
104#endif
88 struct vring_desc *desc; 105 struct vring_desc *desc;
89 106
90 if (!guest.num_free) 107 if (!guest.num_free)
91 return -1; 108 return -1;
92 109
110#ifdef INORDER
111 head = (ring_size - 1) & (guest.avail_idx++);
112#else
93 head = guest.free_head; 113 head = guest.free_head;
114#endif
94 guest.num_free--; 115 guest.num_free--;
95 116
96 desc = ring.desc; 117 desc = ring.desc;
@@ -102,7 +123,9 @@ int add_inbuf(unsigned len, void *buf, void *datap)
102 * descriptors. 123 * descriptors.
103 */ 124 */
104 desc[head].flags &= ~VRING_DESC_F_NEXT; 125 desc[head].flags &= ~VRING_DESC_F_NEXT;
126#ifndef INORDER
105 guest.free_head = desc[head].next; 127 guest.free_head = desc[head].next;
128#endif
106 129
107 data[head].data = datap; 130 data[head].data = datap;
108 131
@@ -113,8 +136,12 @@ int add_inbuf(unsigned len, void *buf, void *datap)
113 ring.avail->ring[avail & (ring_size - 1)] = 136 ring.avail->ring[avail & (ring_size - 1)] =
114 (head | (avail & ~(ring_size - 1))) ^ 0x8000; 137 (head | (avail & ~(ring_size - 1))) ^ 0x8000;
115#else 138#else
139#ifndef INORDER
140 /* Barrier A (for pairing) */
141 smp_release();
116 avail = (ring_size - 1) & (guest.avail_idx++); 142 avail = (ring_size - 1) & (guest.avail_idx++);
117 ring.avail->ring[avail] = head; 143 ring.avail->ring[avail] = head;
144#endif
118 /* Barrier A (for pairing) */ 145 /* Barrier A (for pairing) */
119 smp_release(); 146 smp_release();
120#endif 147#endif
@@ -141,15 +168,27 @@ void *get_buf(unsigned *lenp, void **bufp)
141 return NULL; 168 return NULL;
142 /* Barrier B (for pairing) */ 169 /* Barrier B (for pairing) */
143 smp_acquire(); 170 smp_acquire();
171#ifdef INORDER
172 head = (ring_size - 1) & guest.last_used_idx;
173 index = head;
174#else
144 head = (ring_size - 1) & guest.last_used_idx; 175 head = (ring_size - 1) & guest.last_used_idx;
145 index = ring.used->ring[head].id; 176 index = ring.used->ring[head].id;
146#endif 177#endif
178
179#endif
180#ifdef INORDER
181 *lenp = ring.desc[index].len;
182#else
147 *lenp = ring.used->ring[head].len; 183 *lenp = ring.used->ring[head].len;
184#endif
148 datap = data[index].data; 185 datap = data[index].data;
149 *bufp = (void*)(unsigned long)ring.desc[index].addr; 186 *bufp = (void*)(unsigned long)ring.desc[index].addr;
150 data[index].data = NULL; 187 data[index].data = NULL;
188#ifndef INORDER
151 ring.desc[index].next = guest.free_head; 189 ring.desc[index].next = guest.free_head;
152 guest.free_head = index; 190 guest.free_head = index;
191#endif
153 guest.num_free++; 192 guest.num_free++;
154 guest.last_used_idx++; 193 guest.last_used_idx++;
155 return datap; 194 return datap;
@@ -283,16 +322,24 @@ bool use_buf(unsigned *lenp, void **bufp)
283 smp_acquire(); 322 smp_acquire();
284 323
285 used_idx &= ring_size - 1; 324 used_idx &= ring_size - 1;
325#ifdef INORDER
326 head = used_idx;
327#else
286 head = ring.avail->ring[used_idx]; 328 head = ring.avail->ring[used_idx];
329#endif
287 desc = &ring.desc[head]; 330 desc = &ring.desc[head];
288#endif 331#endif
289 332
290 *lenp = desc->len; 333 *lenp = desc->len;
291 *bufp = (void *)(unsigned long)desc->addr; 334 *bufp = (void *)(unsigned long)desc->addr;
292 335
336#ifdef INORDER
337 desc->len = desc->len - 1;
338#else
293 /* now update used ring */ 339 /* now update used ring */
294 ring.used->ring[used_idx].id = head; 340 ring.used->ring[used_idx].id = head;
295 ring.used->ring[used_idx].len = desc->len - 1; 341 ring.used->ring[used_idx].len = desc->len - 1;
342#endif
296 /* Barrier B (for pairing) */ 343 /* Barrier B (for pairing) */
297 smp_release(); 344 smp_release();
298 host.used_idx++; 345 host.used_idx++;
diff --git a/tools/virtio/ringtest/virtio_ring_inorder.c b/tools/virtio/ringtest/virtio_ring_inorder.c
new file mode 100644
index 000000000000..2438ca58a2ad
--- /dev/null
+++ b/tools/virtio/ringtest/virtio_ring_inorder.c
@@ -0,0 +1,2 @@
1#define INORDER 1
2#include "virtio_ring_0_9.c"