of: MSI: Simplify irqdomain lookup
[linux/fpc-iii.git] / net / vmw_vsock / vmci_transport_notify_qstate.c
blobdc9c7929a2f959f533e198c6e0c178571f2abd9d
1 /*
2 * VMware vSockets Driver
4 * Copyright (C) 2009-2013 VMware, Inc. All rights reserved.
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the Free
8 * Software Foundation version 2 and no later version.
10 * This program is distributed in the hope that it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
16 #include <linux/types.h>
17 #include <linux/socket.h>
18 #include <linux/stddef.h>
19 #include <net/sock.h>
21 #include "vmci_transport_notify.h"
23 #define PKT_FIELD(vsk, field_name) \
24 (vmci_trans(vsk)->notify.pkt_q_state.field_name)
26 static bool vmci_transport_notify_waiting_write(struct vsock_sock *vsk)
28 bool retval;
29 u64 notify_limit;
31 if (!PKT_FIELD(vsk, peer_waiting_write))
32 return false;
34 /* When the sender blocks, we take that as a sign that the sender is
35 * faster than the receiver. To reduce the transmit rate of the sender,
36 * we delay the sending of the read notification by decreasing the
37 * write_notify_window. The notification is delayed until the number of
38 * bytes used in the queue drops below the write_notify_window.
41 if (!PKT_FIELD(vsk, peer_waiting_write_detected)) {
42 PKT_FIELD(vsk, peer_waiting_write_detected) = true;
43 if (PKT_FIELD(vsk, write_notify_window) < PAGE_SIZE) {
44 PKT_FIELD(vsk, write_notify_window) =
45 PKT_FIELD(vsk, write_notify_min_window);
46 } else {
47 PKT_FIELD(vsk, write_notify_window) -= PAGE_SIZE;
48 if (PKT_FIELD(vsk, write_notify_window) <
49 PKT_FIELD(vsk, write_notify_min_window))
50 PKT_FIELD(vsk, write_notify_window) =
51 PKT_FIELD(vsk, write_notify_min_window);
55 notify_limit = vmci_trans(vsk)->consume_size -
56 PKT_FIELD(vsk, write_notify_window);
58 /* The notify_limit is used to delay notifications in the case where
59 * flow control is enabled. Below the test is expressed in terms of
60 * free space in the queue: if free_space > ConsumeSize -
61 * write_notify_window then notify An alternate way of expressing this
62 * is to rewrite the expression to use the data ready in the receive
63 * queue: if write_notify_window > bufferReady then notify as
64 * free_space == ConsumeSize - bufferReady.
67 retval = vmci_qpair_consume_free_space(vmci_trans(vsk)->qpair) >
68 notify_limit;
70 if (retval) {
71 /* Once we notify the peer, we reset the detected flag so the
72 * next wait will again cause a decrease in the window size.
75 PKT_FIELD(vsk, peer_waiting_write_detected) = false;
77 return retval;
80 static void
81 vmci_transport_handle_read(struct sock *sk,
82 struct vmci_transport_packet *pkt,
83 bool bottom_half,
84 struct sockaddr_vm *dst, struct sockaddr_vm *src)
86 sk->sk_write_space(sk);
89 static void
90 vmci_transport_handle_wrote(struct sock *sk,
91 struct vmci_transport_packet *pkt,
92 bool bottom_half,
93 struct sockaddr_vm *dst, struct sockaddr_vm *src)
95 sk->sk_data_ready(sk);
98 static void vsock_block_update_write_window(struct sock *sk)
100 struct vsock_sock *vsk = vsock_sk(sk);
102 if (PKT_FIELD(vsk, write_notify_window) < vmci_trans(vsk)->consume_size)
103 PKT_FIELD(vsk, write_notify_window) =
104 min(PKT_FIELD(vsk, write_notify_window) + PAGE_SIZE,
105 vmci_trans(vsk)->consume_size);
108 static int vmci_transport_send_read_notification(struct sock *sk)
110 struct vsock_sock *vsk;
111 bool sent_read;
112 unsigned int retries;
113 int err;
115 vsk = vsock_sk(sk);
116 sent_read = false;
117 retries = 0;
118 err = 0;
120 if (vmci_transport_notify_waiting_write(vsk)) {
121 /* Notify the peer that we have read, retrying the send on
122 * failure up to our maximum value. XXX For now we just log
123 * the failure, but later we should schedule a work item to
124 * handle the resend until it succeeds. That would require
125 * keeping track of work items in the vsk and cleaning them up
126 * upon socket close.
128 while (!(vsk->peer_shutdown & RCV_SHUTDOWN) &&
129 !sent_read &&
130 retries < VMCI_TRANSPORT_MAX_DGRAM_RESENDS) {
131 err = vmci_transport_send_read(sk);
132 if (err >= 0)
133 sent_read = true;
135 retries++;
138 if (retries >= VMCI_TRANSPORT_MAX_DGRAM_RESENDS && !sent_read)
139 pr_err("%p unable to send read notification to peer\n",
140 sk);
141 else
142 PKT_FIELD(vsk, peer_waiting_write) = false;
145 return err;
148 static void vmci_transport_notify_pkt_socket_init(struct sock *sk)
150 struct vsock_sock *vsk = vsock_sk(sk);
152 PKT_FIELD(vsk, write_notify_window) = PAGE_SIZE;
153 PKT_FIELD(vsk, write_notify_min_window) = PAGE_SIZE;
154 PKT_FIELD(vsk, peer_waiting_write) = false;
155 PKT_FIELD(vsk, peer_waiting_write_detected) = false;
158 static void vmci_transport_notify_pkt_socket_destruct(struct vsock_sock *vsk)
160 PKT_FIELD(vsk, write_notify_window) = PAGE_SIZE;
161 PKT_FIELD(vsk, write_notify_min_window) = PAGE_SIZE;
162 PKT_FIELD(vsk, peer_waiting_write) = false;
163 PKT_FIELD(vsk, peer_waiting_write_detected) = false;
166 static int
167 vmci_transport_notify_pkt_poll_in(struct sock *sk,
168 size_t target, bool *data_ready_now)
170 struct vsock_sock *vsk = vsock_sk(sk);
172 if (vsock_stream_has_data(vsk)) {
173 *data_ready_now = true;
174 } else {
175 /* We can't read right now because there is nothing in the
176 * queue. Ask for notifications when there is something to
177 * read.
179 if (sk->sk_state == SS_CONNECTED)
180 vsock_block_update_write_window(sk);
181 *data_ready_now = false;
184 return 0;
187 static int
188 vmci_transport_notify_pkt_poll_out(struct sock *sk,
189 size_t target, bool *space_avail_now)
191 s64 produce_q_free_space;
192 struct vsock_sock *vsk = vsock_sk(sk);
194 produce_q_free_space = vsock_stream_has_space(vsk);
195 if (produce_q_free_space > 0) {
196 *space_avail_now = true;
197 return 0;
198 } else if (produce_q_free_space == 0) {
199 /* This is a connected socket but we can't currently send data.
200 * Nothing else to do.
202 *space_avail_now = false;
205 return 0;
208 static int
209 vmci_transport_notify_pkt_recv_init(
210 struct sock *sk,
211 size_t target,
212 struct vmci_transport_recv_notify_data *data)
214 struct vsock_sock *vsk = vsock_sk(sk);
216 data->consume_head = 0;
217 data->produce_tail = 0;
218 data->notify_on_block = false;
220 if (PKT_FIELD(vsk, write_notify_min_window) < target + 1) {
221 PKT_FIELD(vsk, write_notify_min_window) = target + 1;
222 if (PKT_FIELD(vsk, write_notify_window) <
223 PKT_FIELD(vsk, write_notify_min_window)) {
224 /* If the current window is smaller than the new
225 * minimal window size, we need to reevaluate whether
226 * we need to notify the sender. If the number of ready
227 * bytes are smaller than the new window, we need to
228 * send a notification to the sender before we block.
231 PKT_FIELD(vsk, write_notify_window) =
232 PKT_FIELD(vsk, write_notify_min_window);
233 data->notify_on_block = true;
237 return 0;
240 static int
241 vmci_transport_notify_pkt_recv_pre_block(
242 struct sock *sk,
243 size_t target,
244 struct vmci_transport_recv_notify_data *data)
246 int err = 0;
248 vsock_block_update_write_window(sk);
250 if (data->notify_on_block) {
251 err = vmci_transport_send_read_notification(sk);
252 if (err < 0)
253 return err;
254 data->notify_on_block = false;
257 return err;
260 static int
261 vmci_transport_notify_pkt_recv_post_dequeue(
262 struct sock *sk,
263 size_t target,
264 ssize_t copied,
265 bool data_read,
266 struct vmci_transport_recv_notify_data *data)
268 struct vsock_sock *vsk;
269 int err;
270 bool was_full = false;
271 u64 free_space;
273 vsk = vsock_sk(sk);
274 err = 0;
276 if (data_read) {
277 smp_mb();
279 free_space =
280 vmci_qpair_consume_free_space(vmci_trans(vsk)->qpair);
281 was_full = free_space == copied;
283 if (was_full)
284 PKT_FIELD(vsk, peer_waiting_write) = true;
286 err = vmci_transport_send_read_notification(sk);
287 if (err < 0)
288 return err;
290 /* See the comment in
291 * vmci_transport_notify_pkt_send_post_enqueue().
293 sk->sk_data_ready(sk);
296 return err;
299 static int
300 vmci_transport_notify_pkt_send_init(
301 struct sock *sk,
302 struct vmci_transport_send_notify_data *data)
304 data->consume_head = 0;
305 data->produce_tail = 0;
307 return 0;
310 static int
311 vmci_transport_notify_pkt_send_post_enqueue(
312 struct sock *sk,
313 ssize_t written,
314 struct vmci_transport_send_notify_data *data)
316 int err = 0;
317 struct vsock_sock *vsk;
318 bool sent_wrote = false;
319 bool was_empty;
320 int retries = 0;
322 vsk = vsock_sk(sk);
324 smp_mb();
326 was_empty =
327 vmci_qpair_produce_buf_ready(vmci_trans(vsk)->qpair) == written;
328 if (was_empty) {
329 while (!(vsk->peer_shutdown & RCV_SHUTDOWN) &&
330 !sent_wrote &&
331 retries < VMCI_TRANSPORT_MAX_DGRAM_RESENDS) {
332 err = vmci_transport_send_wrote(sk);
333 if (err >= 0)
334 sent_wrote = true;
336 retries++;
340 if (retries >= VMCI_TRANSPORT_MAX_DGRAM_RESENDS && !sent_wrote) {
341 pr_err("%p unable to send wrote notification to peer\n",
342 sk);
343 return err;
346 return err;
349 static void
350 vmci_transport_notify_pkt_handle_pkt(
351 struct sock *sk,
352 struct vmci_transport_packet *pkt,
353 bool bottom_half,
354 struct sockaddr_vm *dst,
355 struct sockaddr_vm *src, bool *pkt_processed)
357 bool processed = false;
359 switch (pkt->type) {
360 case VMCI_TRANSPORT_PACKET_TYPE_WROTE:
361 vmci_transport_handle_wrote(sk, pkt, bottom_half, dst, src);
362 processed = true;
363 break;
364 case VMCI_TRANSPORT_PACKET_TYPE_READ:
365 vmci_transport_handle_read(sk, pkt, bottom_half, dst, src);
366 processed = true;
367 break;
370 if (pkt_processed)
371 *pkt_processed = processed;
374 static void vmci_transport_notify_pkt_process_request(struct sock *sk)
376 struct vsock_sock *vsk = vsock_sk(sk);
378 PKT_FIELD(vsk, write_notify_window) = vmci_trans(vsk)->consume_size;
379 if (vmci_trans(vsk)->consume_size <
380 PKT_FIELD(vsk, write_notify_min_window))
381 PKT_FIELD(vsk, write_notify_min_window) =
382 vmci_trans(vsk)->consume_size;
385 static void vmci_transport_notify_pkt_process_negotiate(struct sock *sk)
387 struct vsock_sock *vsk = vsock_sk(sk);
389 PKT_FIELD(vsk, write_notify_window) = vmci_trans(vsk)->consume_size;
390 if (vmci_trans(vsk)->consume_size <
391 PKT_FIELD(vsk, write_notify_min_window))
392 PKT_FIELD(vsk, write_notify_min_window) =
393 vmci_trans(vsk)->consume_size;
396 static int
397 vmci_transport_notify_pkt_recv_pre_dequeue(
398 struct sock *sk,
399 size_t target,
400 struct vmci_transport_recv_notify_data *data)
402 return 0; /* NOP for QState. */
405 static int
406 vmci_transport_notify_pkt_send_pre_block(
407 struct sock *sk,
408 struct vmci_transport_send_notify_data *data)
410 return 0; /* NOP for QState. */
413 static int
414 vmci_transport_notify_pkt_send_pre_enqueue(
415 struct sock *sk,
416 struct vmci_transport_send_notify_data *data)
418 return 0; /* NOP for QState. */
421 /* Socket always on control packet based operations. */
422 struct vmci_transport_notify_ops vmci_transport_notify_pkt_q_state_ops = {
423 vmci_transport_notify_pkt_socket_init,
424 vmci_transport_notify_pkt_socket_destruct,
425 vmci_transport_notify_pkt_poll_in,
426 vmci_transport_notify_pkt_poll_out,
427 vmci_transport_notify_pkt_handle_pkt,
428 vmci_transport_notify_pkt_recv_init,
429 vmci_transport_notify_pkt_recv_pre_block,
430 vmci_transport_notify_pkt_recv_pre_dequeue,
431 vmci_transport_notify_pkt_recv_post_dequeue,
432 vmci_transport_notify_pkt_send_init,
433 vmci_transport_notify_pkt_send_pre_block,
434 vmci_transport_notify_pkt_send_pre_enqueue,
435 vmci_transport_notify_pkt_send_post_enqueue,
436 vmci_transport_notify_pkt_process_request,
437 vmci_transport_notify_pkt_process_negotiate,