Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * Fd transport layer.  Includes deprecated socket layer.
0004  *
0005  *  Copyright (C) 2006 by Russ Cox <rsc@swtch.com>
0006  *  Copyright (C) 2004-2005 by Latchesar Ionkov <lucho@ionkov.net>
0007  *  Copyright (C) 2004-2008 by Eric Van Hensbergen <ericvh@gmail.com>
0008  *  Copyright (C) 1997-2002 by Ron Minnich <rminnich@sarnoff.com>
0009  */
0010 
0011 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
0012 
0013 #include <linux/in.h>
0014 #include <linux/module.h>
0015 #include <linux/net.h>
0016 #include <linux/ipv6.h>
0017 #include <linux/kthread.h>
0018 #include <linux/errno.h>
0019 #include <linux/kernel.h>
0020 #include <linux/un.h>
0021 #include <linux/uaccess.h>
0022 #include <linux/inet.h>
0023 #include <linux/idr.h>
0024 #include <linux/file.h>
0025 #include <linux/parser.h>
0026 #include <linux/slab.h>
0027 #include <linux/seq_file.h>
0028 #include <net/9p/9p.h>
0029 #include <net/9p/client.h>
0030 #include <net/9p/transport.h>
0031 
0032 #include <linux/syscalls.h> /* killme */
0033 
0034 #define P9_PORT 564
0035 #define MAX_SOCK_BUF (1024*1024)
0036 #define MAXPOLLWADDR    2
0037 
0038 static struct p9_trans_module p9_tcp_trans;
0039 static struct p9_trans_module p9_fd_trans;
0040 
0041 /**
0042  * struct p9_fd_opts - per-transport options
0043  * @rfd: file descriptor for reading (trans=fd)
0044  * @wfd: file descriptor for writing (trans=fd)
0045  * @port: port to connect to (trans=tcp)
0046  * @privport: port is privileged
0047  */
0048 
0049 struct p9_fd_opts {
0050     int rfd;
0051     int wfd;
0052     u16 port;
0053     bool privport;
0054 };
0055 
0056 /*
0057   * Option Parsing (code inspired by NFS code)
0058   *  - a little lazy - parse all fd-transport options
0059   */
0060 
0061 enum {
0062     /* Options that take integer arguments */
0063     Opt_port, Opt_rfdno, Opt_wfdno, Opt_err,
0064     /* Options that take no arguments */
0065     Opt_privport,
0066 };
0067 
0068 static const match_table_t tokens = {
0069     {Opt_port, "port=%u"},
0070     {Opt_rfdno, "rfdno=%u"},
0071     {Opt_wfdno, "wfdno=%u"},
0072     {Opt_privport, "privport"},
0073     {Opt_err, NULL},
0074 };
0075 
0076 enum {
0077     Rworksched = 1,     /* read work scheduled or running */
0078     Rpending = 2,       /* can read */
0079     Wworksched = 4,     /* write work scheduled or running */
0080     Wpending = 8,       /* can write */
0081 };
0082 
0083 struct p9_poll_wait {
0084     struct p9_conn *conn;
0085     wait_queue_entry_t wait;
0086     wait_queue_head_t *wait_addr;
0087 };
0088 
0089 /**
0090  * struct p9_conn - fd mux connection state information
0091  * @mux_list: list link for mux to manage multiple connections (?)
0092  * @client: reference to client instance for this connection
0093  * @err: error state
0094  * @req_list: accounting for requests which have been sent
0095  * @unsent_req_list: accounting for requests that haven't been sent
0096  * @rreq: read request
0097  * @wreq: write request
0098  * @req: current request being processed (if any)
0099  * @tmp_buf: temporary buffer to read in header
0100  * @rc: temporary fcall for reading current frame
0101  * @wpos: write position for current frame
0102  * @wsize: amount of data to write for current frame
0103  * @wbuf: current write buffer
0104  * @poll_pending_link: pending links to be polled per conn
0105  * @poll_wait: array of wait_q's for various worker threads
0106  * @pt: poll state
0107  * @rq: current read work
0108  * @wq: current write work
0109  * @wsched: ????
0110  *
0111  */
0112 
0113 struct p9_conn {
0114     struct list_head mux_list;
0115     struct p9_client *client;
0116     int err;
0117     struct list_head req_list;
0118     struct list_head unsent_req_list;
0119     struct p9_req_t *rreq;
0120     struct p9_req_t *wreq;
0121     char tmp_buf[7];
0122     struct p9_fcall rc;
0123     int wpos;
0124     int wsize;
0125     char *wbuf;
0126     struct list_head poll_pending_link;
0127     struct p9_poll_wait poll_wait[MAXPOLLWADDR];
0128     poll_table pt;
0129     struct work_struct rq;
0130     struct work_struct wq;
0131     unsigned long wsched;
0132 };
0133 
0134 /**
0135  * struct p9_trans_fd - transport state
0136  * @rd: reference to file to read from
0137  * @wr: reference of file to write to
0138  * @conn: connection state reference
0139  *
0140  */
0141 
0142 struct p9_trans_fd {
0143     struct file *rd;
0144     struct file *wr;
0145     struct p9_conn conn;
0146 };
0147 
0148 static void p9_poll_workfn(struct work_struct *work);
0149 
0150 static DEFINE_SPINLOCK(p9_poll_lock);
0151 static LIST_HEAD(p9_poll_pending_list);
0152 static DECLARE_WORK(p9_poll_work, p9_poll_workfn);
0153 
0154 static unsigned int p9_ipport_resv_min = P9_DEF_MIN_RESVPORT;
0155 static unsigned int p9_ipport_resv_max = P9_DEF_MAX_RESVPORT;
0156 
0157 static void p9_mux_poll_stop(struct p9_conn *m)
0158 {
0159     unsigned long flags;
0160     int i;
0161 
0162     for (i = 0; i < ARRAY_SIZE(m->poll_wait); i++) {
0163         struct p9_poll_wait *pwait = &m->poll_wait[i];
0164 
0165         if (pwait->wait_addr) {
0166             remove_wait_queue(pwait->wait_addr, &pwait->wait);
0167             pwait->wait_addr = NULL;
0168         }
0169     }
0170 
0171     spin_lock_irqsave(&p9_poll_lock, flags);
0172     list_del_init(&m->poll_pending_link);
0173     spin_unlock_irqrestore(&p9_poll_lock, flags);
0174 
0175     flush_work(&p9_poll_work);
0176 }
0177 
0178 /**
0179  * p9_conn_cancel - cancel all pending requests with error
0180  * @m: mux data
0181  * @err: error code
0182  *
0183  */
0184 
0185 static void p9_conn_cancel(struct p9_conn *m, int err)
0186 {
0187     struct p9_req_t *req, *rtmp;
0188     LIST_HEAD(cancel_list);
0189 
0190     p9_debug(P9_DEBUG_ERROR, "mux %p err %d\n", m, err);
0191 
0192     spin_lock(&m->client->lock);
0193 
0194     if (m->err) {
0195         spin_unlock(&m->client->lock);
0196         return;
0197     }
0198 
0199     m->err = err;
0200 
0201     list_for_each_entry_safe(req, rtmp, &m->req_list, req_list) {
0202         list_move(&req->req_list, &cancel_list);
0203     }
0204     list_for_each_entry_safe(req, rtmp, &m->unsent_req_list, req_list) {
0205         list_move(&req->req_list, &cancel_list);
0206     }
0207 
0208     list_for_each_entry_safe(req, rtmp, &cancel_list, req_list) {
0209         p9_debug(P9_DEBUG_ERROR, "call back req %p\n", req);
0210         list_del(&req->req_list);
0211         if (!req->t_err)
0212             req->t_err = err;
0213         p9_client_cb(m->client, req, REQ_STATUS_ERROR);
0214     }
0215     spin_unlock(&m->client->lock);
0216 }
0217 
0218 static __poll_t
0219 p9_fd_poll(struct p9_client *client, struct poll_table_struct *pt, int *err)
0220 {
0221     __poll_t ret;
0222     struct p9_trans_fd *ts = NULL;
0223 
0224     if (client && client->status == Connected)
0225         ts = client->trans;
0226 
0227     if (!ts) {
0228         if (err)
0229             *err = -EREMOTEIO;
0230         return EPOLLERR;
0231     }
0232 
0233     ret = vfs_poll(ts->rd, pt);
0234     if (ts->rd != ts->wr)
0235         ret = (ret & ~EPOLLOUT) | (vfs_poll(ts->wr, pt) & ~EPOLLIN);
0236     return ret;
0237 }
0238 
0239 /**
0240  * p9_fd_read- read from a fd
0241  * @client: client instance
0242  * @v: buffer to receive data into
0243  * @len: size of receive buffer
0244  *
0245  */
0246 
0247 static int p9_fd_read(struct p9_client *client, void *v, int len)
0248 {
0249     int ret;
0250     struct p9_trans_fd *ts = NULL;
0251     loff_t pos;
0252 
0253     if (client && client->status != Disconnected)
0254         ts = client->trans;
0255 
0256     if (!ts)
0257         return -EREMOTEIO;
0258 
0259     if (!(ts->rd->f_flags & O_NONBLOCK))
0260         p9_debug(P9_DEBUG_ERROR, "blocking read ...\n");
0261 
0262     pos = ts->rd->f_pos;
0263     ret = kernel_read(ts->rd, v, len, &pos);
0264     if (ret <= 0 && ret != -ERESTARTSYS && ret != -EAGAIN)
0265         client->status = Disconnected;
0266     return ret;
0267 }
0268 
0269 /**
0270  * p9_read_work - called when there is some data to be read from a transport
0271  * @work: container of work to be done
0272  *
0273  */
0274 
0275 static void p9_read_work(struct work_struct *work)
0276 {
0277     __poll_t n;
0278     int err;
0279     struct p9_conn *m;
0280 
0281     m = container_of(work, struct p9_conn, rq);
0282 
0283     if (m->err < 0)
0284         return;
0285 
0286     p9_debug(P9_DEBUG_TRANS, "start mux %p pos %zd\n", m, m->rc.offset);
0287 
0288     if (!m->rc.sdata) {
0289         m->rc.sdata = m->tmp_buf;
0290         m->rc.offset = 0;
0291         m->rc.capacity = 7; /* start by reading header */
0292     }
0293 
0294     clear_bit(Rpending, &m->wsched);
0295     p9_debug(P9_DEBUG_TRANS, "read mux %p pos %zd size: %zd = %zd\n",
0296          m, m->rc.offset, m->rc.capacity,
0297          m->rc.capacity - m->rc.offset);
0298     err = p9_fd_read(m->client, m->rc.sdata + m->rc.offset,
0299              m->rc.capacity - m->rc.offset);
0300     p9_debug(P9_DEBUG_TRANS, "mux %p got %d bytes\n", m, err);
0301     if (err == -EAGAIN)
0302         goto end_clear;
0303 
0304     if (err <= 0)
0305         goto error;
0306 
0307     m->rc.offset += err;
0308 
0309     /* header read in */
0310     if ((!m->rreq) && (m->rc.offset == m->rc.capacity)) {
0311         p9_debug(P9_DEBUG_TRANS, "got new header\n");
0312 
0313         /* Header size */
0314         m->rc.size = 7;
0315         err = p9_parse_header(&m->rc, &m->rc.size, NULL, NULL, 0);
0316         if (err) {
0317             p9_debug(P9_DEBUG_ERROR,
0318                  "error parsing header: %d\n", err);
0319             goto error;
0320         }
0321 
0322         if (m->rc.size >= m->client->msize) {
0323             p9_debug(P9_DEBUG_ERROR,
0324                  "requested packet size too big: %d\n",
0325                  m->rc.size);
0326             err = -EIO;
0327             goto error;
0328         }
0329 
0330         p9_debug(P9_DEBUG_TRANS,
0331              "mux %p pkt: size: %d bytes tag: %d\n",
0332              m, m->rc.size, m->rc.tag);
0333 
0334         m->rreq = p9_tag_lookup(m->client, m->rc.tag);
0335         if (!m->rreq || (m->rreq->status != REQ_STATUS_SENT)) {
0336             p9_debug(P9_DEBUG_ERROR, "Unexpected packet tag %d\n",
0337                  m->rc.tag);
0338             err = -EIO;
0339             goto error;
0340         }
0341 
0342         if (!m->rreq->rc.sdata) {
0343             p9_debug(P9_DEBUG_ERROR,
0344                  "No recv fcall for tag %d (req %p), disconnecting!\n",
0345                  m->rc.tag, m->rreq);
0346             p9_req_put(m->client, m->rreq);
0347             m->rreq = NULL;
0348             err = -EIO;
0349             goto error;
0350         }
0351         m->rc.sdata = m->rreq->rc.sdata;
0352         memcpy(m->rc.sdata, m->tmp_buf, m->rc.capacity);
0353         m->rc.capacity = m->rc.size;
0354     }
0355 
0356     /* packet is read in
0357      * not an else because some packets (like clunk) have no payload
0358      */
0359     if ((m->rreq) && (m->rc.offset == m->rc.capacity)) {
0360         p9_debug(P9_DEBUG_TRANS, "got new packet\n");
0361         m->rreq->rc.size = m->rc.offset;
0362         spin_lock(&m->client->lock);
0363         if (m->rreq->status == REQ_STATUS_SENT) {
0364             list_del(&m->rreq->req_list);
0365             p9_client_cb(m->client, m->rreq, REQ_STATUS_RCVD);
0366         } else if (m->rreq->status == REQ_STATUS_FLSHD) {
0367             /* Ignore replies associated with a cancelled request. */
0368             p9_debug(P9_DEBUG_TRANS,
0369                  "Ignore replies associated with a cancelled request\n");
0370         } else {
0371             spin_unlock(&m->client->lock);
0372             p9_debug(P9_DEBUG_ERROR,
0373                  "Request tag %d errored out while we were reading the reply\n",
0374                  m->rc.tag);
0375             err = -EIO;
0376             goto error;
0377         }
0378         spin_unlock(&m->client->lock);
0379         m->rc.sdata = NULL;
0380         m->rc.offset = 0;
0381         m->rc.capacity = 0;
0382         p9_req_put(m->client, m->rreq);
0383         m->rreq = NULL;
0384     }
0385 
0386 end_clear:
0387     clear_bit(Rworksched, &m->wsched);
0388 
0389     if (!list_empty(&m->req_list)) {
0390         if (test_and_clear_bit(Rpending, &m->wsched))
0391             n = EPOLLIN;
0392         else
0393             n = p9_fd_poll(m->client, NULL, NULL);
0394 
0395         if ((n & EPOLLIN) && !test_and_set_bit(Rworksched, &m->wsched)) {
0396             p9_debug(P9_DEBUG_TRANS, "sched read work %p\n", m);
0397             schedule_work(&m->rq);
0398         }
0399     }
0400 
0401     return;
0402 error:
0403     p9_conn_cancel(m, err);
0404     clear_bit(Rworksched, &m->wsched);
0405 }
0406 
0407 /**
0408  * p9_fd_write - write to a socket
0409  * @client: client instance
0410  * @v: buffer to send data from
0411  * @len: size of send buffer
0412  *
0413  */
0414 
0415 static int p9_fd_write(struct p9_client *client, void *v, int len)
0416 {
0417     ssize_t ret;
0418     struct p9_trans_fd *ts = NULL;
0419 
0420     if (client && client->status != Disconnected)
0421         ts = client->trans;
0422 
0423     if (!ts)
0424         return -EREMOTEIO;
0425 
0426     if (!(ts->wr->f_flags & O_NONBLOCK))
0427         p9_debug(P9_DEBUG_ERROR, "blocking write ...\n");
0428 
0429     ret = kernel_write(ts->wr, v, len, &ts->wr->f_pos);
0430     if (ret <= 0 && ret != -ERESTARTSYS && ret != -EAGAIN)
0431         client->status = Disconnected;
0432     return ret;
0433 }
0434 
0435 /**
0436  * p9_write_work - called when a transport can send some data
0437  * @work: container for work to be done
0438  *
0439  */
0440 
0441 static void p9_write_work(struct work_struct *work)
0442 {
0443     __poll_t n;
0444     int err;
0445     struct p9_conn *m;
0446     struct p9_req_t *req;
0447 
0448     m = container_of(work, struct p9_conn, wq);
0449 
0450     if (m->err < 0) {
0451         clear_bit(Wworksched, &m->wsched);
0452         return;
0453     }
0454 
0455     if (!m->wsize) {
0456         spin_lock(&m->client->lock);
0457         if (list_empty(&m->unsent_req_list)) {
0458             clear_bit(Wworksched, &m->wsched);
0459             spin_unlock(&m->client->lock);
0460             return;
0461         }
0462 
0463         req = list_entry(m->unsent_req_list.next, struct p9_req_t,
0464                    req_list);
0465         req->status = REQ_STATUS_SENT;
0466         p9_debug(P9_DEBUG_TRANS, "move req %p\n", req);
0467         list_move_tail(&req->req_list, &m->req_list);
0468 
0469         m->wbuf = req->tc.sdata;
0470         m->wsize = req->tc.size;
0471         m->wpos = 0;
0472         p9_req_get(req);
0473         m->wreq = req;
0474         spin_unlock(&m->client->lock);
0475     }
0476 
0477     p9_debug(P9_DEBUG_TRANS, "mux %p pos %d size %d\n",
0478          m, m->wpos, m->wsize);
0479     clear_bit(Wpending, &m->wsched);
0480     err = p9_fd_write(m->client, m->wbuf + m->wpos, m->wsize - m->wpos);
0481     p9_debug(P9_DEBUG_TRANS, "mux %p sent %d bytes\n", m, err);
0482     if (err == -EAGAIN)
0483         goto end_clear;
0484 
0485 
0486     if (err < 0)
0487         goto error;
0488     else if (err == 0) {
0489         err = -EREMOTEIO;
0490         goto error;
0491     }
0492 
0493     m->wpos += err;
0494     if (m->wpos == m->wsize) {
0495         m->wpos = m->wsize = 0;
0496         p9_req_put(m->client, m->wreq);
0497         m->wreq = NULL;
0498     }
0499 
0500 end_clear:
0501     clear_bit(Wworksched, &m->wsched);
0502 
0503     if (m->wsize || !list_empty(&m->unsent_req_list)) {
0504         if (test_and_clear_bit(Wpending, &m->wsched))
0505             n = EPOLLOUT;
0506         else
0507             n = p9_fd_poll(m->client, NULL, NULL);
0508 
0509         if ((n & EPOLLOUT) &&
0510            !test_and_set_bit(Wworksched, &m->wsched)) {
0511             p9_debug(P9_DEBUG_TRANS, "sched write work %p\n", m);
0512             schedule_work(&m->wq);
0513         }
0514     }
0515 
0516     return;
0517 
0518 error:
0519     p9_conn_cancel(m, err);
0520     clear_bit(Wworksched, &m->wsched);
0521 }
0522 
0523 static int p9_pollwake(wait_queue_entry_t *wait, unsigned int mode, int sync, void *key)
0524 {
0525     struct p9_poll_wait *pwait =
0526         container_of(wait, struct p9_poll_wait, wait);
0527     struct p9_conn *m = pwait->conn;
0528     unsigned long flags;
0529 
0530     spin_lock_irqsave(&p9_poll_lock, flags);
0531     if (list_empty(&m->poll_pending_link))
0532         list_add_tail(&m->poll_pending_link, &p9_poll_pending_list);
0533     spin_unlock_irqrestore(&p9_poll_lock, flags);
0534 
0535     schedule_work(&p9_poll_work);
0536     return 1;
0537 }
0538 
0539 /**
0540  * p9_pollwait - add poll task to the wait queue
0541  * @filp: file pointer being polled
0542  * @wait_address: wait_q to block on
0543  * @p: poll state
0544  *
0545  * called by files poll operation to add v9fs-poll task to files wait queue
0546  */
0547 
0548 static void
0549 p9_pollwait(struct file *filp, wait_queue_head_t *wait_address, poll_table *p)
0550 {
0551     struct p9_conn *m = container_of(p, struct p9_conn, pt);
0552     struct p9_poll_wait *pwait = NULL;
0553     int i;
0554 
0555     for (i = 0; i < ARRAY_SIZE(m->poll_wait); i++) {
0556         if (m->poll_wait[i].wait_addr == NULL) {
0557             pwait = &m->poll_wait[i];
0558             break;
0559         }
0560     }
0561 
0562     if (!pwait) {
0563         p9_debug(P9_DEBUG_ERROR, "not enough wait_address slots\n");
0564         return;
0565     }
0566 
0567     pwait->conn = m;
0568     pwait->wait_addr = wait_address;
0569     init_waitqueue_func_entry(&pwait->wait, p9_pollwake);
0570     add_wait_queue(wait_address, &pwait->wait);
0571 }
0572 
0573 /**
0574  * p9_conn_create - initialize the per-session mux data
0575  * @client: client instance
0576  *
0577  * Note: Creates the polling task if this is the first session.
0578  */
0579 
0580 static void p9_conn_create(struct p9_client *client)
0581 {
0582     __poll_t n;
0583     struct p9_trans_fd *ts = client->trans;
0584     struct p9_conn *m = &ts->conn;
0585 
0586     p9_debug(P9_DEBUG_TRANS, "client %p msize %d\n", client, client->msize);
0587 
0588     INIT_LIST_HEAD(&m->mux_list);
0589     m->client = client;
0590 
0591     INIT_LIST_HEAD(&m->req_list);
0592     INIT_LIST_HEAD(&m->unsent_req_list);
0593     INIT_WORK(&m->rq, p9_read_work);
0594     INIT_WORK(&m->wq, p9_write_work);
0595     INIT_LIST_HEAD(&m->poll_pending_link);
0596     init_poll_funcptr(&m->pt, p9_pollwait);
0597 
0598     n = p9_fd_poll(client, &m->pt, NULL);
0599     if (n & EPOLLIN) {
0600         p9_debug(P9_DEBUG_TRANS, "mux %p can read\n", m);
0601         set_bit(Rpending, &m->wsched);
0602     }
0603 
0604     if (n & EPOLLOUT) {
0605         p9_debug(P9_DEBUG_TRANS, "mux %p can write\n", m);
0606         set_bit(Wpending, &m->wsched);
0607     }
0608 }
0609 
0610 /**
0611  * p9_poll_mux - polls a mux and schedules read or write works if necessary
0612  * @m: connection to poll
0613  *
0614  */
0615 
0616 static void p9_poll_mux(struct p9_conn *m)
0617 {
0618     __poll_t n;
0619     int err = -ECONNRESET;
0620 
0621     if (m->err < 0)
0622         return;
0623 
0624     n = p9_fd_poll(m->client, NULL, &err);
0625     if (n & (EPOLLERR | EPOLLHUP | EPOLLNVAL)) {
0626         p9_debug(P9_DEBUG_TRANS, "error mux %p err %d\n", m, n);
0627         p9_conn_cancel(m, err);
0628     }
0629 
0630     if (n & EPOLLIN) {
0631         set_bit(Rpending, &m->wsched);
0632         p9_debug(P9_DEBUG_TRANS, "mux %p can read\n", m);
0633         if (!test_and_set_bit(Rworksched, &m->wsched)) {
0634             p9_debug(P9_DEBUG_TRANS, "sched read work %p\n", m);
0635             schedule_work(&m->rq);
0636         }
0637     }
0638 
0639     if (n & EPOLLOUT) {
0640         set_bit(Wpending, &m->wsched);
0641         p9_debug(P9_DEBUG_TRANS, "mux %p can write\n", m);
0642         if ((m->wsize || !list_empty(&m->unsent_req_list)) &&
0643             !test_and_set_bit(Wworksched, &m->wsched)) {
0644             p9_debug(P9_DEBUG_TRANS, "sched write work %p\n", m);
0645             schedule_work(&m->wq);
0646         }
0647     }
0648 }
0649 
0650 /**
0651  * p9_fd_request - send 9P request
0652  * The function can sleep until the request is scheduled for sending.
0653  * The function can be interrupted. Return from the function is not
0654  * a guarantee that the request is sent successfully.
0655  *
0656  * @client: client instance
0657  * @req: request to be sent
0658  *
0659  */
0660 
0661 static int p9_fd_request(struct p9_client *client, struct p9_req_t *req)
0662 {
0663     __poll_t n;
0664     struct p9_trans_fd *ts = client->trans;
0665     struct p9_conn *m = &ts->conn;
0666 
0667     p9_debug(P9_DEBUG_TRANS, "mux %p task %p tcall %p id %d\n",
0668          m, current, &req->tc, req->tc.id);
0669     if (m->err < 0)
0670         return m->err;
0671 
0672     spin_lock(&client->lock);
0673     req->status = REQ_STATUS_UNSENT;
0674     list_add_tail(&req->req_list, &m->unsent_req_list);
0675     spin_unlock(&client->lock);
0676 
0677     if (test_and_clear_bit(Wpending, &m->wsched))
0678         n = EPOLLOUT;
0679     else
0680         n = p9_fd_poll(m->client, NULL, NULL);
0681 
0682     if (n & EPOLLOUT && !test_and_set_bit(Wworksched, &m->wsched))
0683         schedule_work(&m->wq);
0684 
0685     return 0;
0686 }
0687 
0688 static int p9_fd_cancel(struct p9_client *client, struct p9_req_t *req)
0689 {
0690     int ret = 1;
0691 
0692     p9_debug(P9_DEBUG_TRANS, "client %p req %p\n", client, req);
0693 
0694     spin_lock(&client->lock);
0695 
0696     if (req->status == REQ_STATUS_UNSENT) {
0697         list_del(&req->req_list);
0698         req->status = REQ_STATUS_FLSHD;
0699         p9_req_put(client, req);
0700         ret = 0;
0701     }
0702     spin_unlock(&client->lock);
0703 
0704     return ret;
0705 }
0706 
0707 static int p9_fd_cancelled(struct p9_client *client, struct p9_req_t *req)
0708 {
0709     p9_debug(P9_DEBUG_TRANS, "client %p req %p\n", client, req);
0710 
0711     spin_lock(&client->lock);
0712     /* Ignore cancelled request if message has been received
0713      * before lock.
0714      */
0715     if (req->status == REQ_STATUS_RCVD) {
0716         spin_unlock(&client->lock);
0717         return 0;
0718     }
0719 
0720     /* we haven't received a response for oldreq,
0721      * remove it from the list.
0722      */
0723     list_del(&req->req_list);
0724     req->status = REQ_STATUS_FLSHD;
0725     spin_unlock(&client->lock);
0726     p9_req_put(client, req);
0727 
0728     return 0;
0729 }
0730 
0731 static int p9_fd_show_options(struct seq_file *m, struct p9_client *clnt)
0732 {
0733     if (clnt->trans_mod == &p9_tcp_trans) {
0734         if (clnt->trans_opts.tcp.port != P9_PORT)
0735             seq_printf(m, ",port=%u", clnt->trans_opts.tcp.port);
0736     } else if (clnt->trans_mod == &p9_fd_trans) {
0737         if (clnt->trans_opts.fd.rfd != ~0)
0738             seq_printf(m, ",rfd=%u", clnt->trans_opts.fd.rfd);
0739         if (clnt->trans_opts.fd.wfd != ~0)
0740             seq_printf(m, ",wfd=%u", clnt->trans_opts.fd.wfd);
0741     }
0742     return 0;
0743 }
0744 
0745 /**
0746  * parse_opts - parse mount options into p9_fd_opts structure
0747  * @params: options string passed from mount
0748  * @opts: fd transport-specific structure to parse options into
0749  *
0750  * Returns 0 upon success, -ERRNO upon failure
0751  */
0752 
0753 static int parse_opts(char *params, struct p9_fd_opts *opts)
0754 {
0755     char *p;
0756     substring_t args[MAX_OPT_ARGS];
0757     int option;
0758     char *options, *tmp_options;
0759 
0760     opts->port = P9_PORT;
0761     opts->rfd = ~0;
0762     opts->wfd = ~0;
0763     opts->privport = false;
0764 
0765     if (!params)
0766         return 0;
0767 
0768     tmp_options = kstrdup(params, GFP_KERNEL);
0769     if (!tmp_options) {
0770         p9_debug(P9_DEBUG_ERROR,
0771              "failed to allocate copy of option string\n");
0772         return -ENOMEM;
0773     }
0774     options = tmp_options;
0775 
0776     while ((p = strsep(&options, ",")) != NULL) {
0777         int token;
0778         int r;
0779         if (!*p)
0780             continue;
0781         token = match_token(p, tokens, args);
0782         if ((token != Opt_err) && (token != Opt_privport)) {
0783             r = match_int(&args[0], &option);
0784             if (r < 0) {
0785                 p9_debug(P9_DEBUG_ERROR,
0786                      "integer field, but no integer?\n");
0787                 continue;
0788             }
0789         }
0790         switch (token) {
0791         case Opt_port:
0792             opts->port = option;
0793             break;
0794         case Opt_rfdno:
0795             opts->rfd = option;
0796             break;
0797         case Opt_wfdno:
0798             opts->wfd = option;
0799             break;
0800         case Opt_privport:
0801             opts->privport = true;
0802             break;
0803         default:
0804             continue;
0805         }
0806     }
0807 
0808     kfree(tmp_options);
0809     return 0;
0810 }
0811 
0812 static int p9_fd_open(struct p9_client *client, int rfd, int wfd)
0813 {
0814     struct p9_trans_fd *ts = kzalloc(sizeof(struct p9_trans_fd),
0815                        GFP_KERNEL);
0816     if (!ts)
0817         return -ENOMEM;
0818 
0819     ts->rd = fget(rfd);
0820     if (!ts->rd)
0821         goto out_free_ts;
0822     if (!(ts->rd->f_mode & FMODE_READ))
0823         goto out_put_rd;
0824     ts->wr = fget(wfd);
0825     if (!ts->wr)
0826         goto out_put_rd;
0827     if (!(ts->wr->f_mode & FMODE_WRITE))
0828         goto out_put_wr;
0829 
0830     client->trans = ts;
0831     client->status = Connected;
0832 
0833     return 0;
0834 
0835 out_put_wr:
0836     fput(ts->wr);
0837 out_put_rd:
0838     fput(ts->rd);
0839 out_free_ts:
0840     kfree(ts);
0841     return -EIO;
0842 }
0843 
0844 static int p9_socket_open(struct p9_client *client, struct socket *csocket)
0845 {
0846     struct p9_trans_fd *p;
0847     struct file *file;
0848 
0849     p = kzalloc(sizeof(struct p9_trans_fd), GFP_KERNEL);
0850     if (!p)
0851         return -ENOMEM;
0852 
0853     csocket->sk->sk_allocation = GFP_NOIO;
0854     file = sock_alloc_file(csocket, 0, NULL);
0855     if (IS_ERR(file)) {
0856         pr_err("%s (%d): failed to map fd\n",
0857                __func__, task_pid_nr(current));
0858         kfree(p);
0859         return PTR_ERR(file);
0860     }
0861 
0862     get_file(file);
0863     p->wr = p->rd = file;
0864     client->trans = p;
0865     client->status = Connected;
0866 
0867     p->rd->f_flags |= O_NONBLOCK;
0868 
0869     p9_conn_create(client);
0870     return 0;
0871 }
0872 
0873 /**
0874  * p9_conn_destroy - cancels all pending requests of mux
0875  * @m: mux to destroy
0876  *
0877  */
0878 
0879 static void p9_conn_destroy(struct p9_conn *m)
0880 {
0881     p9_debug(P9_DEBUG_TRANS, "mux %p prev %p next %p\n",
0882          m, m->mux_list.prev, m->mux_list.next);
0883 
0884     p9_mux_poll_stop(m);
0885     cancel_work_sync(&m->rq);
0886     if (m->rreq) {
0887         p9_req_put(m->client, m->rreq);
0888         m->rreq = NULL;
0889     }
0890     cancel_work_sync(&m->wq);
0891     if (m->wreq) {
0892         p9_req_put(m->client, m->wreq);
0893         m->wreq = NULL;
0894     }
0895 
0896     p9_conn_cancel(m, -ECONNRESET);
0897 
0898     m->client = NULL;
0899 }
0900 
0901 /**
0902  * p9_fd_close - shutdown file descriptor transport
0903  * @client: client instance
0904  *
0905  */
0906 
0907 static void p9_fd_close(struct p9_client *client)
0908 {
0909     struct p9_trans_fd *ts;
0910 
0911     if (!client)
0912         return;
0913 
0914     ts = client->trans;
0915     if (!ts)
0916         return;
0917 
0918     client->status = Disconnected;
0919 
0920     p9_conn_destroy(&ts->conn);
0921 
0922     if (ts->rd)
0923         fput(ts->rd);
0924     if (ts->wr)
0925         fput(ts->wr);
0926 
0927     kfree(ts);
0928 }
0929 
0930 /*
0931  * stolen from NFS - maybe should be made a generic function?
0932  */
0933 static inline int valid_ipaddr4(const char *buf)
0934 {
0935     int rc, count, in[4];
0936 
0937     rc = sscanf(buf, "%d.%d.%d.%d", &in[0], &in[1], &in[2], &in[3]);
0938     if (rc != 4)
0939         return -EINVAL;
0940     for (count = 0; count < 4; count++) {
0941         if (in[count] > 255)
0942             return -EINVAL;
0943     }
0944     return 0;
0945 }
0946 
0947 static int p9_bind_privport(struct socket *sock)
0948 {
0949     struct sockaddr_in cl;
0950     int port, err = -EINVAL;
0951 
0952     memset(&cl, 0, sizeof(cl));
0953     cl.sin_family = AF_INET;
0954     cl.sin_addr.s_addr = htonl(INADDR_ANY);
0955     for (port = p9_ipport_resv_max; port >= p9_ipport_resv_min; port--) {
0956         cl.sin_port = htons((ushort)port);
0957         err = kernel_bind(sock, (struct sockaddr *)&cl, sizeof(cl));
0958         if (err != -EADDRINUSE)
0959             break;
0960     }
0961     return err;
0962 }
0963 
0964 
0965 static int
0966 p9_fd_create_tcp(struct p9_client *client, const char *addr, char *args)
0967 {
0968     int err;
0969     struct socket *csocket;
0970     struct sockaddr_in sin_server;
0971     struct p9_fd_opts opts;
0972 
0973     err = parse_opts(args, &opts);
0974     if (err < 0)
0975         return err;
0976 
0977     if (addr == NULL || valid_ipaddr4(addr) < 0)
0978         return -EINVAL;
0979 
0980     csocket = NULL;
0981 
0982     client->trans_opts.tcp.port = opts.port;
0983     client->trans_opts.tcp.privport = opts.privport;
0984     sin_server.sin_family = AF_INET;
0985     sin_server.sin_addr.s_addr = in_aton(addr);
0986     sin_server.sin_port = htons(opts.port);
0987     err = __sock_create(current->nsproxy->net_ns, PF_INET,
0988                 SOCK_STREAM, IPPROTO_TCP, &csocket, 1);
0989     if (err) {
0990         pr_err("%s (%d): problem creating socket\n",
0991                __func__, task_pid_nr(current));
0992         return err;
0993     }
0994 
0995     if (opts.privport) {
0996         err = p9_bind_privport(csocket);
0997         if (err < 0) {
0998             pr_err("%s (%d): problem binding to privport\n",
0999                    __func__, task_pid_nr(current));
1000             sock_release(csocket);
1001             return err;
1002         }
1003     }
1004 
1005     err = csocket->ops->connect(csocket,
1006                     (struct sockaddr *)&sin_server,
1007                     sizeof(struct sockaddr_in), 0);
1008     if (err < 0) {
1009         pr_err("%s (%d): problem connecting socket to %s\n",
1010                __func__, task_pid_nr(current), addr);
1011         sock_release(csocket);
1012         return err;
1013     }
1014 
1015     return p9_socket_open(client, csocket);
1016 }
1017 
1018 static int
1019 p9_fd_create_unix(struct p9_client *client, const char *addr, char *args)
1020 {
1021     int err;
1022     struct socket *csocket;
1023     struct sockaddr_un sun_server;
1024 
1025     csocket = NULL;
1026 
1027     if (!addr || !strlen(addr))
1028         return -EINVAL;
1029 
1030     if (strlen(addr) >= UNIX_PATH_MAX) {
1031         pr_err("%s (%d): address too long: %s\n",
1032                __func__, task_pid_nr(current), addr);
1033         return -ENAMETOOLONG;
1034     }
1035 
1036     sun_server.sun_family = PF_UNIX;
1037     strcpy(sun_server.sun_path, addr);
1038     err = __sock_create(current->nsproxy->net_ns, PF_UNIX,
1039                 SOCK_STREAM, 0, &csocket, 1);
1040     if (err < 0) {
1041         pr_err("%s (%d): problem creating socket\n",
1042                __func__, task_pid_nr(current));
1043 
1044         return err;
1045     }
1046     err = csocket->ops->connect(csocket, (struct sockaddr *)&sun_server,
1047             sizeof(struct sockaddr_un) - 1, 0);
1048     if (err < 0) {
1049         pr_err("%s (%d): problem connecting socket: %s: %d\n",
1050                __func__, task_pid_nr(current), addr, err);
1051         sock_release(csocket);
1052         return err;
1053     }
1054 
1055     return p9_socket_open(client, csocket);
1056 }
1057 
1058 static int
1059 p9_fd_create(struct p9_client *client, const char *addr, char *args)
1060 {
1061     int err;
1062     struct p9_fd_opts opts;
1063 
1064     parse_opts(args, &opts);
1065     client->trans_opts.fd.rfd = opts.rfd;
1066     client->trans_opts.fd.wfd = opts.wfd;
1067 
1068     if (opts.rfd == ~0 || opts.wfd == ~0) {
1069         pr_err("Insufficient options for proto=fd\n");
1070         return -ENOPROTOOPT;
1071     }
1072 
1073     err = p9_fd_open(client, opts.rfd, opts.wfd);
1074     if (err < 0)
1075         return err;
1076 
1077     p9_conn_create(client);
1078 
1079     return 0;
1080 }
1081 
1082 static struct p9_trans_module p9_tcp_trans = {
1083     .name = "tcp",
1084     .maxsize = MAX_SOCK_BUF,
1085     .def = 0,
1086     .create = p9_fd_create_tcp,
1087     .close = p9_fd_close,
1088     .request = p9_fd_request,
1089     .cancel = p9_fd_cancel,
1090     .cancelled = p9_fd_cancelled,
1091     .show_options = p9_fd_show_options,
1092     .owner = THIS_MODULE,
1093 };
1094 MODULE_ALIAS_9P("tcp");
1095 
1096 static struct p9_trans_module p9_unix_trans = {
1097     .name = "unix",
1098     .maxsize = MAX_SOCK_BUF,
1099     .def = 0,
1100     .create = p9_fd_create_unix,
1101     .close = p9_fd_close,
1102     .request = p9_fd_request,
1103     .cancel = p9_fd_cancel,
1104     .cancelled = p9_fd_cancelled,
1105     .show_options = p9_fd_show_options,
1106     .owner = THIS_MODULE,
1107 };
1108 MODULE_ALIAS_9P("unix");
1109 
1110 static struct p9_trans_module p9_fd_trans = {
1111     .name = "fd",
1112     .maxsize = MAX_SOCK_BUF,
1113     .def = 0,
1114     .create = p9_fd_create,
1115     .close = p9_fd_close,
1116     .request = p9_fd_request,
1117     .cancel = p9_fd_cancel,
1118     .cancelled = p9_fd_cancelled,
1119     .show_options = p9_fd_show_options,
1120     .owner = THIS_MODULE,
1121 };
1122 MODULE_ALIAS_9P("fd");
1123 
1124 /**
1125  * p9_poll_workfn - poll worker thread
1126  * @work: work queue
1127  *
1128  * polls all v9fs transports for new events and queues the appropriate
1129  * work to the work queue
1130  *
1131  */
1132 
1133 static void p9_poll_workfn(struct work_struct *work)
1134 {
1135     unsigned long flags;
1136 
1137     p9_debug(P9_DEBUG_TRANS, "start %p\n", current);
1138 
1139     spin_lock_irqsave(&p9_poll_lock, flags);
1140     while (!list_empty(&p9_poll_pending_list)) {
1141         struct p9_conn *conn = list_first_entry(&p9_poll_pending_list,
1142                             struct p9_conn,
1143                             poll_pending_link);
1144         list_del_init(&conn->poll_pending_link);
1145         spin_unlock_irqrestore(&p9_poll_lock, flags);
1146 
1147         p9_poll_mux(conn);
1148 
1149         spin_lock_irqsave(&p9_poll_lock, flags);
1150     }
1151     spin_unlock_irqrestore(&p9_poll_lock, flags);
1152 
1153     p9_debug(P9_DEBUG_TRANS, "finish\n");
1154 }
1155 
1156 static int __init p9_trans_fd_init(void)
1157 {
1158     v9fs_register_trans(&p9_tcp_trans);
1159     v9fs_register_trans(&p9_unix_trans);
1160     v9fs_register_trans(&p9_fd_trans);
1161 
1162     return 0;
1163 }
1164 
1165 static void __exit p9_trans_fd_exit(void)
1166 {
1167     flush_work(&p9_poll_work);
1168     v9fs_unregister_trans(&p9_tcp_trans);
1169     v9fs_unregister_trans(&p9_unix_trans);
1170     v9fs_unregister_trans(&p9_fd_trans);
1171 }
1172 
1173 module_init(p9_trans_fd_init);
1174 module_exit(p9_trans_fd_exit);
1175 
1176 MODULE_AUTHOR("Eric Van Hensbergen <ericvh@gmail.com>");
1177 MODULE_DESCRIPTION("Filedescriptor Transport for 9P");
1178 MODULE_LICENSE("GPL");