aboutsummaryrefslogtreecommitdiffstats
path: root/fs/nfsd/nfs4state.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/nfsd/nfs4state.c')
-rw-r--r--fs/nfsd/nfs4state.c49
1 files changed, 47 insertions, 2 deletions
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c
index 3b4d74cbb6c..596702e157c 100644
--- a/fs/nfsd/nfs4state.c
+++ b/fs/nfsd/nfs4state.c
@@ -658,13 +658,18 @@ static struct nfsd4_conn *alloc_conn(struct svc_rqst *rqstp)
658 return conn; 658 return conn;
659} 659}
660 660
661static void __nfsd4_hash_conn(struct nfsd4_conn *conn, struct nfsd4_session *ses)
662{
663 conn->cn_session = ses;
664 list_add(&conn->cn_persession, &ses->se_conns);
665}
666
661static void nfsd4_hash_conn(struct nfsd4_conn *conn, struct nfsd4_session *ses) 667static void nfsd4_hash_conn(struct nfsd4_conn *conn, struct nfsd4_session *ses)
662{ 668{
663 struct nfs4_client *clp = ses->se_client; 669 struct nfs4_client *clp = ses->se_client;
664 670
665 spin_lock(&clp->cl_lock); 671 spin_lock(&clp->cl_lock);
666 conn->cn_session = ses; 672 __nfsd4_hash_conn(conn, ses);
667 list_add(&conn->cn_persession, &ses->se_conns);
668 spin_unlock(&clp->cl_lock); 673 spin_unlock(&clp->cl_lock);
669} 674}
670 675
@@ -1612,6 +1617,44 @@ out:
1612 return status; 1617 return status;
1613} 1618}
1614 1619
1620static struct nfsd4_conn *__nfsd4_find_conn(struct svc_rqst *r, struct nfsd4_session *s)
1621{
1622 struct nfsd4_conn *c;
1623
1624 list_for_each_entry(c, &s->se_conns, cn_persession) {
1625 if (c->cn_xprt == r->rq_xprt) {
1626 return c;
1627 }
1628 }
1629 return NULL;
1630}
1631
1632static void nfsd4_sequence_check_conn(struct svc_rqst *rqstp, struct nfsd4_session *ses)
1633{
1634 struct nfs4_client *clp = ses->se_client;
1635 struct nfsd4_conn *c, *new = NULL;
1636
1637 spin_lock(&clp->cl_lock);
1638 c = __nfsd4_find_conn(rqstp, ses);
1639 spin_unlock(&clp->cl_lock);
1640 if (c)
1641 return;
1642
1643 new = alloc_conn(rqstp);
1644
1645 spin_lock(&clp->cl_lock);
1646 c = __nfsd4_find_conn(rqstp, ses);
1647 if (c) {
1648 spin_unlock(&clp->cl_lock);
1649 free_conn(new);
1650 return;
1651 }
1652 __nfsd4_hash_conn(new, ses);
1653 spin_unlock(&clp->cl_lock);
1654 nfsd4_register_conn(new);
1655 return;
1656}
1657
1615__be32 1658__be32
1616nfsd4_sequence(struct svc_rqst *rqstp, 1659nfsd4_sequence(struct svc_rqst *rqstp,
1617 struct nfsd4_compound_state *cstate, 1660 struct nfsd4_compound_state *cstate,
@@ -1656,6 +1699,8 @@ nfsd4_sequence(struct svc_rqst *rqstp,
1656 if (status) 1699 if (status)
1657 goto out; 1700 goto out;
1658 1701
1702 nfsd4_sequence_check_conn(rqstp, session);
1703
1659 /* Success! bump slot seqid */ 1704 /* Success! bump slot seqid */
1660 slot->sl_inuse = true; 1705 slot->sl_inuse = true;
1661 slot->sl_seqid = seq->seqid; 1706 slot->sl_seqid = seq->seqid;