summaryrefslogtreecommitdiff
path: root/fs/afs/rxrpc.c
diff options
context:
space:
mode:
authorDavid Howells <dhowells@redhat.com>2017-11-02 18:27:48 +0300
committerDavid Howells <dhowells@redhat.com>2017-11-13 18:38:17 +0300
commit33cd7f2b76717ac8dda566d8b4f518e803ae2618 (patch)
treede1ca2aba2b026759a89ed343271ccf1268093cc /fs/afs/rxrpc.c
parent97e3043ad82c93b7c2e3c4bfc518f7401f175821 (diff)
downloadlinux-33cd7f2b76717ac8dda566d8b4f518e803ae2618.tar.xz
afs: Potentially return call->reply[0] from afs_make_call()
If call->ret_reply0 is set, return call->reply[0] on success. Change the return type of afs_make_call() to long so that this can be passed back without bit loss and then cast to a pointer if required. Signed-off-by: David Howells <dhowells@redhat.com>
Diffstat (limited to 'fs/afs/rxrpc.c')
-rw-r--r--fs/afs/rxrpc.c26
1 files changed, 16 insertions, 10 deletions
diff --git a/fs/afs/rxrpc.c b/fs/afs/rxrpc.c
index fc49193e12c4..d57f09b5d27b 100644
--- a/fs/afs/rxrpc.c
+++ b/fs/afs/rxrpc.c
@@ -20,7 +20,7 @@
struct workqueue_struct *afs_async_calls;
static void afs_wake_up_call_waiter(struct sock *, struct rxrpc_call *, unsigned long);
-static int afs_wait_for_call_to_complete(struct afs_call *);
+static long afs_wait_for_call_to_complete(struct afs_call *);
static void afs_wake_up_async_call(struct sock *, struct rxrpc_call *, unsigned long);
static void afs_process_async_call(struct work_struct *);
static void afs_rx_new_call(struct sock *, struct rxrpc_call *, unsigned long);
@@ -320,8 +320,8 @@ static int afs_send_pages(struct afs_call *call, struct msghdr *msg)
/*
* initiate a call
*/
-int afs_make_call(struct sockaddr_rxrpc *srx, struct afs_call *call,
- gfp_t gfp, bool async)
+long afs_make_call(struct sockaddr_rxrpc *srx, struct afs_call *call,
+ gfp_t gfp, bool async)
{
struct rxrpc_call *rxcall;
struct msghdr msg;
@@ -415,9 +415,9 @@ error_do_abort:
abort_code = 0;
offset = 0;
rxrpc_kernel_recv_data(call->net->socket, rxcall, NULL,
- 0, &offset, false, &abort_code,
+ 0, &offset, false, &call->abort_code,
&call->service_id);
- ret = afs_abort_to_error(abort_code);
+ ret = afs_abort_to_error(call->abort_code);
}
error_kill_call:
afs_put_call(call);
@@ -468,7 +468,7 @@ static void afs_deliver_to_call(struct afs_call *call)
case -EAGAIN:
goto out;
case -ECONNABORTED:
- goto call_complete;
+ goto save_error;
case -ENOTCONN:
abort_code = RX_CALL_DEAD;
rxrpc_kernel_abort_call(call->net->socket, call->rxcall,
@@ -501,7 +501,6 @@ out:
save_error:
call->error = ret;
-call_complete:
call->state = AFS_CALL_COMPLETE;
goto done;
}
@@ -509,10 +508,10 @@ call_complete:
/*
* wait synchronously for a call to complete
*/
-static int afs_wait_for_call_to_complete(struct afs_call *call)
+static long afs_wait_for_call_to_complete(struct afs_call *call)
{
signed long rtt2, timeout;
- int ret;
+ long ret;
u64 rtt;
u32 life, last_life;
@@ -567,9 +566,16 @@ static int afs_wait_for_call_to_complete(struct afs_call *call)
}
ret = call->error;
+ if (ret < 0) {
+ ret = afs_abort_to_error(call->abort_code);
+ } else if (ret == 0 && call->ret_reply0) {
+ ret = (long)call->reply[0];
+ call->reply[0] = NULL;
+ }
+
_debug("call complete");
afs_put_call(call);
- _leave(" = %d", ret);
+ _leave(" = %p", (void *)ret);
return ret;
}