summaryrefslogtreecommitdiff
path: root/net/strparser
diff options
context:
space:
mode:
Diffstat (limited to 'net/strparser')
-rw-r--r--net/strparser/strparser.c48
1 files changed, 29 insertions, 19 deletions
diff --git a/net/strparser/strparser.c b/net/strparser/strparser.c
index 4ecfc10cbe6d..5c7549b5b92c 100644
--- a/net/strparser/strparser.c
+++ b/net/strparser/strparser.c
@@ -26,7 +26,6 @@
#include <net/strparser.h>
#include <net/netns/generic.h>
#include <net/sock.h>
-#include <net/tcp.h>
static struct workqueue_struct *strp_wq;
@@ -80,9 +79,16 @@ static void strp_parser_err(struct strparser *strp, int err,
strp->cb.abort_parser(strp, err);
}
+static inline int strp_peek_len(struct strparser *strp)
+{
+ struct socket *sock = strp->sk->sk_socket;
+
+ return sock->ops->peek_len(sock);
+}
+
/* Lower socket lock held */
-static int strp_tcp_recv(read_descriptor_t *desc, struct sk_buff *orig_skb,
- unsigned int orig_offset, size_t orig_len)
+static int strp_recv(read_descriptor_t *desc, struct sk_buff *orig_skb,
+ unsigned int orig_offset, size_t orig_len)
{
struct strparser *strp = (struct strparser *)desc->arg.data;
struct _strp_rx_msg *rxm;
@@ -266,12 +272,12 @@ static int strp_tcp_recv(read_descriptor_t *desc, struct sk_buff *orig_skb,
if (extra < 0) {
/* Message not complete yet. */
if (rxm->strp.full_len - rxm->accum_len >
- tcp_inq(strp->sk)) {
+ strp_peek_len(strp)) {
/* Don't have the whole messages in the socket
* buffer. Set strp->rx_need_bytes to wait for
* the rest of the message. Also, set "early
* eaten" since we've already buffered the skb
- * but don't consume yet per tcp_read_sock.
+ * but don't consume yet per strp_read_sock.
*/
if (!rxm->accum_len) {
@@ -329,16 +335,17 @@ static int default_read_sock_done(struct strparser *strp, int err)
}
/* Called with lock held on lower socket */
-static int strp_tcp_read_sock(struct strparser *strp)
+static int strp_read_sock(struct strparser *strp)
{
+ struct socket *sock = strp->sk->sk_socket;
read_descriptor_t desc;
desc.arg.data = strp;
desc.error = 0;
desc.count = 1; /* give more than one skb per call */
- /* sk should be locked here, so okay to do tcp_read_sock */
- tcp_read_sock(strp->sk, &desc, strp_tcp_recv);
+ /* sk should be locked here, so okay to do read_sock */
+ sock->ops->read_sock(strp->sk, &desc, strp_recv);
desc.error = strp->cb.read_sock_done(strp, desc.error);
@@ -346,10 +353,8 @@ static int strp_tcp_read_sock(struct strparser *strp)
}
/* Lower sock lock held */
-void strp_tcp_data_ready(struct strparser *strp)
+void strp_data_ready(struct strparser *strp)
{
- struct sock *csk = strp->sk;
-
if (unlikely(strp->rx_stopped))
return;
@@ -360,7 +365,7 @@ void strp_tcp_data_ready(struct strparser *strp)
* allows a thread in BH context to safely check if the process
* lock is held. In this case, if the lock is held, queue work.
*/
- if (sock_owned_by_user(csk)) {
+ if (sock_owned_by_user(strp->sk)) {
queue_work(strp_wq, &strp->rx_work);
return;
}
@@ -369,24 +374,24 @@ void strp_tcp_data_ready(struct strparser *strp)
return;
if (strp->rx_need_bytes) {
- if (tcp_inq(csk) >= strp->rx_need_bytes)
+ if (strp_peek_len(strp) >= strp->rx_need_bytes)
strp->rx_need_bytes = 0;
else
return;
}
- if (strp_tcp_read_sock(strp) == -ENOMEM)
+ if (strp_read_sock(strp) == -ENOMEM)
queue_work(strp_wq, &strp->rx_work);
}
-EXPORT_SYMBOL_GPL(strp_tcp_data_ready);
+EXPORT_SYMBOL_GPL(strp_data_ready);
static void do_strp_rx_work(struct strparser *strp)
{
read_descriptor_t rd_desc;
struct sock *csk = strp->sk;
- /* We need the read lock to synchronize with strp_tcp_data_ready. We
- * need the socket lock for calling tcp_read_sock.
+ /* We need the read lock to synchronize with strp_data_ready. We
+ * need the socket lock for calling strp_read_sock.
*/
lock_sock(csk);
@@ -398,7 +403,7 @@ static void do_strp_rx_work(struct strparser *strp)
rd_desc.arg.data = strp;
- if (strp_tcp_read_sock(strp) == -ENOMEM)
+ if (strp_read_sock(strp) == -ENOMEM)
queue_work(strp_wq, &strp->rx_work);
out:
@@ -424,9 +429,14 @@ static void strp_rx_msg_timeout(unsigned long arg)
int strp_init(struct strparser *strp, struct sock *csk,
struct strp_callbacks *cb)
{
+ struct socket *sock = csk->sk_socket;
+
if (!cb || !cb->rcv_msg || !cb->parse_msg)
return -EINVAL;
+ if (!sock->ops->read_sock || !sock->ops->peek_len)
+ return -EAFNOSUPPORT;
+
memset(strp, 0, sizeof(*strp));
strp->sk = csk;
@@ -456,7 +466,7 @@ void strp_unpause(struct strparser *strp)
}
EXPORT_SYMBOL_GPL(strp_unpause);
-/* strp must already be stopped so that strp_tcp_recv will no longer be called.
+/* strp must already be stopped so that strp_recv will no longer be called.
* Note that strp_done is not called with the lower socket held.
*/
void strp_done(struct strparser *strp)