From ca534f38f59a6dbed158232056255427dac8442d Mon Sep 17 00:00:00 2001 From: eeb Date: Thu, 29 Sep 2005 00:11:36 +0000 Subject: [PATCH] * Changed LNetGet() LNetPut() to include a source nid parameter Set this to LNET_NID_ANY to have the source nid set automatically, otherwise it checks that the destination is reachable from the given source NID and sends using that. This ensures the source NID is deterministic in the presence of equivalent routes. * Changed LNetDist() to return the count of networks traversed rather than routers (i.e. 0 == local, 1 == local net, 2 == via 1 router etc). It also returns a source NID (== NID of local LNET interface that will send). * Changed LNet() completion events to include the target process ID so the app can tell which NID the sender sent to. * Removed the 'implicit_loopback' lnet module parameter. You have to use 0@lo explicitly if you want loopback. * Changed lustre to remember the source NID returned by LNetDist() to ensure client requests always arrive with a consistent initiator NID. * Changed lustre to remember the target NID of incoming requests to ensure server replies are always sent with the same source NID that the client sent her requests to. * Changed lustre to use a NID of 0@lo if the distance to the target NID is 0 (i.e use the loopback LNET interface when talking to local servers). --- lnet/include/lnet/api.h | 8 +- lnet/include/lnet/lib-lnet.h | 16 ++- lnet/include/lnet/types.h | 1 + lnet/klnds/iiblnd/iiblnd_cb.c | 2 + lnet/klnds/openiblnd/openiblnd.c | 2 +- lnet/klnds/openiblnd/openiblnd_cb.c | 8 +- lnet/klnds/qswlnd/qswlnd_cb.c | 2 + lnet/klnds/ralnd/ralnd_cb.c | 7 ++ lnet/klnds/viblnd/viblnd_cb.c | 3 +- lnet/lnet/api-ni.c | 95 ++++++++-------- lnet/lnet/config.c | 6 +- lnet/lnet/lib-move.c | 209 ++++++++++++++++++++++++------------ lnet/lnet/lib-msg.c | 4 +- lnet/lnet/router.c | 34 +----- lnet/tests/ping_cli.c | 3 +- lnet/tests/ping_srv.c | 3 +- lnet/tests/sping_cli.c | 2 +- lnet/tests/sping_srv.c | 3 +- lnet/tests/ut_cli.c | 2 + 19 files changed, 244 insertions(+), 166 deletions(-) diff --git a/lnet/include/lnet/api.h b/lnet/include/lnet/api.h index d5a7a01..5065ad2 100644 --- a/lnet/include/lnet/api.h +++ b/lnet/include/lnet/api.h @@ -10,7 +10,7 @@ int LNetNIInit(lnet_pid_t requested_pid); int LNetNIFini(void); int LNetGetId(unsigned int index, lnet_process_id_t *id); -int LNetDist(lnet_nid_t nid, int *order); +int LNetDist(lnet_nid_t nid, lnet_nid_t *srcnid, int *order); int LNetCtl(unsigned int cmd, void *arg); void LNetSnprintHandle (char *str, int str_len, lnet_handle_any_t handle); @@ -75,7 +75,8 @@ int LNetEQPoll(lnet_handle_eq_t *eventqs_in, /* * Data movement */ -int LNetPut(lnet_handle_md_t md_in, +int LNetPut(lnet_nid_t self, + lnet_handle_md_t md_in, lnet_ack_req_t ack_req_in, lnet_process_id_t target_in, unsigned int portal_in, @@ -83,7 +84,8 @@ int LNetPut(lnet_handle_md_t md_in, unsigned int offset_in, __u64 hdr_data_in); -int LNetGet(lnet_handle_md_t md_in, +int LNetGet(lnet_nid_t self, + lnet_handle_md_t md_in, lnet_process_id_t target_in, unsigned int portal_in, __u64 match_bits_in, diff --git a/lnet/include/lnet/lib-lnet.h b/lnet/include/lnet/lib-lnet.h index 46164b4..ae8eb3b 100644 --- a/lnet/include/lnet/lib-lnet.h +++ b/lnet/include/lnet/lib-lnet.h @@ -435,9 +435,19 @@ lnet_ptlcompat_matchnid(lnet_nid_t lnet_nid, lnet_nid_t ptl_nid) return ((ptl_nid == lnet_nid) || (the_lnet.ln_ptlcompat > 0 && PTL_NIDNET(ptl_nid) == 0 && + PTL_NETTYP(PTL_NIDNET(lnet_nid)) != LOLND && PTL_NIDADDR(ptl_nid) == PTL_NIDADDR(lnet_nid))); } +static inline int +lnet_ptlcompat_matchnet(__u32 lnet_net, __u32 ptl_net) +{ + return ((ptl_net == lnet_net) || + (the_lnet.ln_ptlcompat > 0 && + ptl_net == 0 && + PTL_NETTYP(lnet_net) != LOLND)); +} + static inline struct list_head * lnet_nid2peerhash (lnet_nid_t nid) { @@ -458,6 +468,7 @@ do { \ } while (0) #endif +extern lnet_ni_t *lnet_nid2ni_locked (lnet_nid_t nid); extern lnet_ni_t *lnet_net2ni_locked (__u32 net); static inline lnet_ni_t * lnet_net2ni (__u32 net) @@ -472,7 +483,6 @@ lnet_net2ni (__u32 net) } int lnet_notify(lnet_ni_t *ni, lnet_nid_t peer, int alive, time_t when); -int lnet_distance(lnet_nid_t nid, int *order); int lnet_add_route(__u32 net, unsigned int hops, lnet_nid_t gateway_nid); int lnet_check_routes(void); int lnet_del_route(__u32 net, lnet_nid_t gw_nid); @@ -487,12 +497,12 @@ void lnet_free_rtrpools(void); lnet_remotenet_t *lnet_find_net_locked (__u32 net); int lnet_islocalnid(lnet_nid_t nid); -int lnet_islocalnet(__u32 net, int *orderp); +int lnet_islocalnet(__u32 net); void lnet_enq_event_locked(lnet_eq_t *eq, lnet_event_t *ev); void lnet_prep_send(lnet_msg_t *msg, int type, lnet_process_id_t target, unsigned int offset, unsigned int len); -int lnet_send(lnet_ni_t *ni, lnet_msg_t *msg); +int lnet_send(lnet_nid_t nid, lnet_msg_t *msg); void lnet_return_credits_locked (lnet_msg_t *msg); int lnet_parse (lnet_ni_t *ni, lnet_hdr_t *hdr, lnet_nid_t fromnid, void *private); diff --git a/lnet/include/lnet/types.h b/lnet/include/lnet/types.h index de2ca2d..c681638 100644 --- a/lnet/include/lnet/types.h +++ b/lnet/include/lnet/types.h @@ -108,6 +108,7 @@ typedef unsigned LNET_SEQ_BASETYPE lnet_seq_t; #endif typedef struct { lnet_event_kind_t type; + lnet_process_id_t target; lnet_process_id_t initiator; unsigned int pt_index; __u64 match_bits; diff --git a/lnet/klnds/iiblnd/iiblnd_cb.c b/lnet/klnds/iiblnd/iiblnd_cb.c index 21bd3bc..3779c91 100644 --- a/lnet/klnds/iiblnd/iiblnd_cb.c +++ b/lnet/klnds/iiblnd/iiblnd_cb.c @@ -172,6 +172,8 @@ kibnal_complete_passive_rdma(kib_conn_t *conn, __u64 cookie, int status) CDEBUG(D_NET, "Complete %p "LPD64": %d\n", tx, cookie, status); + /* XXX Set mlength of REPLY here */ + tx->tx_status = status; tx->tx_passive_rdma_wait = 0; idle = (tx->tx_sending == 0); diff --git a/lnet/klnds/openiblnd/openiblnd.c b/lnet/klnds/openiblnd/openiblnd.c index c2d89df..1fc30c5 100644 --- a/lnet/klnds/openiblnd/openiblnd.c +++ b/lnet/klnds/openiblnd/openiblnd.c @@ -278,7 +278,7 @@ kibnal_make_svcqry (kib_conn_t *conn) goto out; } - if (msg->ibm_srcnid != peer->ibp_nid) { + if (!lnet_ptlcompat_matchnid(peer->ibp_nid, msg->ibm_srcnid)) { CERROR("Unexpected src NID %s from %s at %u.%u.%u.%u/%d\n", libcfs_nid2str(msg->ibm_srcnid), libcfs_nid2str(peer->ibp_nid), diff --git a/lnet/klnds/openiblnd/openiblnd_cb.c b/lnet/klnds/openiblnd/openiblnd_cb.c index 067ab2b..1bd9d36 100644 --- a/lnet/klnds/openiblnd/openiblnd_cb.c +++ b/lnet/klnds/openiblnd/openiblnd_cb.c @@ -172,6 +172,8 @@ kibnal_complete_passive_rdma(kib_conn_t *conn, __u64 cookie, int status) CDEBUG(D_NET, "Complete %p "LPD64": %d\n", tx, cookie, status); + /* XXX Set mlength of reply here */ + tx->tx_status = status; tx->tx_passive_rdma_wait = 0; idle = (tx->tx_sending == 0); @@ -289,7 +291,8 @@ kibnal_rx_callback (struct ib_cq_entry *e) goto failed; } - if (msg->ibm_srcnid != conn->ibc_peer->ibp_nid || + if (!lnet_ptlcompat_matchnid(conn->ibc_peer->ibp_nid, + msg->ibm_srcnid) || !lnet_ptlcompat_matchnid(kibnal_data.kib_ni->ni_nid, msg->ibm_dstnid) || msg->ibm_srcstamp != conn->ibc_incarnation || @@ -1958,7 +1961,8 @@ kibnal_active_conn_callback (tTS_IB_CM_EVENT event, return TS_IB_CM_CALLBACK_ABORT; } - if (msg->ibm_srcnid != conn->ibc_peer->ibp_nid || + if (!lnet_ptlcompat_matchnid(conn->ibc_peer->ibp_nid, + msg->ibm_srcnid) || !lnet_ptlcompat_matchnid(kibnal_data.kib_ni->ni_nid, msg->ibm_dstnid) || msg->ibm_srcstamp != conn->ibc_incarnation || diff --git a/lnet/klnds/qswlnd/qswlnd_cb.c b/lnet/klnds/qswlnd/qswlnd_cb.c index fc8a93c..4b14815 100644 --- a/lnet/klnds/qswlnd/qswlnd_cb.c +++ b/lnet/klnds/qswlnd/qswlnd_cb.c @@ -732,6 +732,8 @@ kqswnal_rdma_store_complete (EP_RXD *rxd) LASSERT (krx->krx_rxd == rxd); LASSERT (krx->krx_rpc_reply_needed); + /* XXX Set REPLY mlength here */ + krx->krx_rpc_reply_needed = 0; kqswnal_rx_decref (krx); diff --git a/lnet/klnds/ralnd/ralnd_cb.c b/lnet/klnds/ralnd/ralnd_cb.c index 1e79640..7be86cc 100644 --- a/lnet/klnds/ralnd/ralnd_cb.c +++ b/lnet/klnds/ralnd/ralnd_cb.c @@ -1815,6 +1815,13 @@ kranal_check_fma_rx (kra_conn_t *conn) LASSERT (tx->tx_buftype == RANAL_BUF_PHYS_MAPPED || tx->tx_buftype == RANAL_BUF_VIRT_MAPPED); +#if 0 + /* completion message should send rdma length if we ever allow + * GET truncation */ + LASSERT (tx->tx_lntmsg[1] != NULL); + LASSERT (tx->tx_lntmsg[1]->msg_ev.type == LNET_EVENT_REPLY); + tx->tx_lntmsg[1]->msg_ev.mlength = ???; +#endif kranal_tx_done(tx, 0); break; } diff --git a/lnet/klnds/viblnd/viblnd_cb.c b/lnet/klnds/viblnd/viblnd_cb.c index 948f235..310f047 100644 --- a/lnet/klnds/viblnd/viblnd_cb.c +++ b/lnet/klnds/viblnd/viblnd_cb.c @@ -434,7 +434,8 @@ kibnal_rx_complete (kib_rx_t *rx, vv_comp_status_t vvrc, int nob, __u64 rxseq) rx->rx_nob = nob; /* Can trust 'nob' now */ - if (msg->ibm_srcnid != conn->ibc_peer->ibp_nid || + if (!lnet_ptlcompat_matchnid(conn->ibc_peer->ibp_nid, + msg->ibm_srcnid) || !lnet_ptlcompat_matchnid(kibnal_data.kib_ni->ni_nid, msg->ibm_dstnid) || msg->ibm_srcstamp != conn->ibc_incarnation || diff --git a/lnet/lnet/api-ni.c b/lnet/lnet/api-ni.c index bdd327b..a346953 100644 --- a/lnet/lnet/api-ni.c +++ b/lnet/lnet/api-ni.c @@ -675,10 +675,7 @@ lnet_net2ni_locked (__u32 net) list_for_each (tmp, &the_lnet.ln_nis) { ni = list_entry(tmp, lnet_ni_t, ni_list); - if (PTL_NIDNET(ni->ni_nid) == net || - (the_lnet.ln_ptlcompat > 0 && - net == 0 && - PTL_NETTYP(PTL_NIDNET(ni->ni_nid)) != LOLND)) { + if (lnet_ptlcompat_matchnet(PTL_NIDNET(ni->ni_nid), net)) { lnet_ni_addref_locked(ni); return ni; } @@ -688,81 +685,79 @@ lnet_net2ni_locked (__u32 net) } int -lnet_count_acceptor_nis (lnet_ni_t **first_ni) +lnet_islocalnet (__u32 net) { - /* Return the # of NIs that need the acceptor. Return the first one in - * *first_ni so the acceptor can pass it connections "blind" to retain - * binary compatibility. */ - int count = 0; -#ifdef __KERNEL__ - struct list_head *tmp; - lnet_ni_t *ni; - - LNET_LOCK(); - list_for_each (tmp, &the_lnet.ln_nis) { - ni = list_entry(tmp, lnet_ni_t, ni_list); - - if (ni->ni_lnd->lnd_accept != NULL) { - /* This LND uses the acceptor */ - if (count == 0 && first_ni != NULL) { - lnet_ni_addref_locked(ni); - *first_ni = ni; - } - count++; - } - } + lnet_ni_t *ni; + LNET_LOCK(); + ni = lnet_net2ni_locked(net); + if (ni != NULL) + lnet_ni_decref_locked(ni); LNET_UNLOCK(); -#endif - return count; + + return ni != NULL; } -int -lnet_islocalnid (lnet_nid_t nid) +lnet_ni_t * +lnet_nid2ni_locked (lnet_nid_t nid) { struct list_head *tmp; lnet_ni_t *ni; - int islocal = 0; - - LNET_LOCK(); list_for_each (tmp, &the_lnet.ln_nis) { ni = list_entry(tmp, lnet_ni_t, ni_list); - if (ni->ni_nid == nid) { - islocal = 1; - break; + if (lnet_ptlcompat_matchnid(ni->ni_nid, nid)) { + lnet_ni_addref_locked(ni); + return ni; } } + return NULL; +} + +int +lnet_islocalnid (lnet_nid_t nid) +{ + lnet_ni_t *ni; + + LNET_LOCK(); + ni = lnet_nid2ni_locked(nid); + if (ni != NULL) + lnet_ni_decref_locked(ni); LNET_UNLOCK(); - return islocal; + + return ni != NULL; } int -lnet_islocalnet (__u32 net, int *orderp) +lnet_count_acceptor_nis (lnet_ni_t **first_ni) { - struct list_head *tmp; - lnet_ni_t *ni; - int order = 0; - int islocal = 0; + /* Return the # of NIs that need the acceptor. Return the first one in + * *first_ni so the acceptor can pass it connections "blind" to retain + * binary compatibility. */ + int count = 0; +#ifdef __KERNEL__ + struct list_head *tmp; + lnet_ni_t *ni; LNET_LOCK(); - list_for_each (tmp, &the_lnet.ln_nis) { ni = list_entry(tmp, lnet_ni_t, ni_list); - if (PTL_NIDNET(ni->ni_nid) == net) { - islocal = 1; - if (orderp != NULL) - *orderp = order; - break; + if (ni->ni_lnd->lnd_accept != NULL) { + /* This LND uses the acceptor */ + if (count == 0 && first_ni != NULL) { + lnet_ni_addref_locked(ni); + *first_ni = ni; + } + count++; } - order++; } LNET_UNLOCK(); - return islocal; +#endif + return count; } void diff --git a/lnet/lnet/config.c b/lnet/lnet/config.c index 4306233..b1863f2 100644 --- a/lnet/lnet/config.c +++ b/lnet/lnet/config.c @@ -623,11 +623,13 @@ lnet_parse_route (char *str, int *im_a_router) if (ntokens == 1) { net = libcfs_str2net(ptb->ptb_text); - if (net == PTL_NIDNET(LNET_NID_ANY)) + if (net == PTL_NIDNET(LNET_NID_ANY) || + PTL_NETTYP(net) == LOLND) goto token_error; } else { nid = libcfs_str2nid(ptb->ptb_text); - if (nid == LNET_NID_ANY) + if (nid == LNET_NID_ANY || + PTL_NETTYP(PTL_NIDNET(nid)) == LOLND) goto token_error; } } diff --git a/lnet/lnet/lib-move.c b/lnet/lnet/lib-move.c index 1910051..1ce53e6 100644 --- a/lnet/lnet/lib-move.c +++ b/lnet/lnet/lib-move.c @@ -26,10 +26,6 @@ #include -static int implicit_loopback = 1; -CFS_MODULE_PARM(implicit_loopback, "i", int, 0644, - "Boolean: substitute 0@lo when sending to any local NID"); - /* forward ref */ static void lnet_commit_md (lnet_libmd_t *md, lnet_msg_t *msg); @@ -789,7 +785,8 @@ lnet_prep_send(lnet_msg_t *msg, int type, lnet_process_id_t target, msg->msg_hdr.type = cpu_to_le32(type); msg->msg_hdr.dest_nid = cpu_to_le64(target.nid); msg->msg_hdr.dest_pid = cpu_to_le32(target.pid); - /* src not set yet */ + /* src_nid will be set later */ + msg->msg_hdr.src_pid = cpu_to_le32(the_lnet.ln_pid); msg->msg_hdr.payload_length = cpu_to_le32(len); } @@ -1144,14 +1141,14 @@ lnet_return_credits_locked (lnet_msg_t *msg) } int -lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) +lnet_send(lnet_nid_t src_nid, lnet_msg_t *msg) { lnet_nid_t dst_nid = msg->msg_target.nid; - lnet_ni_t *src_ni = NULL; - lnet_remotenet_t *rnet = NULL; + lnet_ni_t *src_ni; + lnet_ni_t *local_ni; + lnet_remotenet_t *rnet; lnet_route_t *route; struct list_head *tmp; - lnet_nid_t src_nid; lnet_peer_t *lp; lnet_peer_t *lp2; int rc; @@ -1159,7 +1156,6 @@ lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) LASSERT (msg->msg_txpeer == NULL); LASSERT (!msg->msg_sending); LASSERT (!msg->msg_target_is_router); - LASSERT (!msg->msg_routing || ni == NULL); msg->msg_sending = 1; @@ -1172,42 +1168,50 @@ lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) return -ESHUTDOWN; } - /* Is this for someone on a local network? */ - src_ni = lnet_net2ni_locked(PTL_NIDNET(dst_nid)); - if (src_ni != NULL) { + if (src_nid == LNET_NID_ANY) { + src_ni = NULL; + } else { + src_ni = lnet_nid2ni_locked(src_nid); + if (src_ni == NULL) { + LNET_UNLOCK(); + CERROR("Can't send to %s: src %s is not a local nid\n", + libcfs_nid2str(dst_nid), libcfs_nid2str(src_nid)); + return -EINVAL; + } + LASSERT (!msg->msg_routing); + } + + /* Is this for someone on a local network? */ + local_ni = lnet_net2ni_locked(PTL_NIDNET(dst_nid)); + + if (local_ni != NULL) { + if (src_ni == NULL) { + src_ni = local_ni; + src_nid = src_ni->ni_nid; + } else if (src_ni == local_ni) { + lnet_ni_decref_locked(local_ni); + } else { + lnet_ni_decref_locked(local_ni); + lnet_ni_decref_locked(src_ni); + LNET_UNLOCK(); + CERROR("no route to %s via from %s\n", + libcfs_nid2str(dst_nid), libcfs_nid2str(src_nid)); + return -EINVAL; + } + + LASSERT (src_nid != LNET_NID_ANY); + if (!msg->msg_routing) { - /* I'm the original message source and I'm sending to - * someone local. Set msg_hdr.src_nid/pid from the NI - * I'm sending from and see if I should actually use - * the loopback NI. */ - - src_nid = lnet_ptlcompat_srcnid(src_ni->ni_nid, dst_nid); + src_nid = lnet_ptlcompat_srcnid(src_nid, dst_nid); msg->msg_hdr.src_nid = cpu_to_le64(src_nid); - msg->msg_hdr.src_pid = cpu_to_le32(the_lnet.ln_pid); + } - /* send via lo0? */ - if (implicit_loopback && - the_lnet.ln_loni != NULL && - lnet_ptlcompat_matchnid(src_ni->ni_nid, dst_nid)) { - lnet_ni_decref_locked(src_ni); - src_ni = the_lnet.ln_loni; - lnet_ni_addref_locked(src_ni); - } - - if (src_ni == the_lnet.ln_loni) { - /* No send credit hassles with LOLND */ - LNET_UNLOCK(); - - if (ni != NULL && ni != src_ni) { - /* a different LND expects a response */ - rc = -EPROTO; - } else { - rc = 0; - lnet_ni_send(src_ni, msg); - } - lnet_ni_decref(src_ni); - return rc; - } + if (src_ni == the_lnet.ln_loni) { + /* No send credit hassles with LOLND */ + LNET_UNLOCK(); + lnet_ni_send(src_ni, msg); + lnet_ni_decref(src_ni); + return 0; } rc = lnet_nid2peer_locked(&lp, dst_nid); @@ -1219,10 +1223,13 @@ lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) /* ENOMEM or shutting down */ return rc; } + LASSERT (lp->lp_ni == src_ni); } else { /* sending to a remote network */ rnet = lnet_find_net_locked(PTL_NIDNET(dst_nid)); if (rnet == NULL) { + if (src_ni != NULL) + lnet_ni_decref_locked(src_ni); LNET_UNLOCK(); CERROR("No route to %s\n", libcfs_id2str(msg->msg_target)); return -EHOSTUNREACH; @@ -1235,25 +1242,37 @@ lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) lp2 = route->lr_gateway; if (lp2->lp_alive && + (src_ni == NULL || lp2->lp_ni == src_ni) && (lp == NULL || lnet_compare_routers(lp2, lp))) lp = lp2; } if (lp == NULL) { + if (src_ni == NULL) + lnet_ni_decref_locked(src_ni); LNET_UNLOCK(); CERROR("No route to %s (all routers down)\n", libcfs_id2str(msg->msg_target)); return -EHOSTUNREACH; } + if (src_ni == NULL) { + src_ni = lp->lp_ni; + src_nid = src_ni->ni_nid; + } else { + LASSERT (src_ni == lp->lp_ni); + lnet_ni_decref_locked(src_ni); + } + lnet_peer_addref_locked(lp); src_ni = lp->lp_ni; + LASSERT (src_nid != LNET_NID_ANY); + if (!msg->msg_routing) { /* I'm the source and now I know which NI to send on */ - src_nid = lnet_ptlcompat_srcnid(src_ni->ni_nid, dst_nid); + src_nid = lnet_ptlcompat_srcnid(src_nid, dst_nid); msg->msg_hdr.src_nid = cpu_to_le64(src_nid); - msg->msg_hdr.src_pid = cpu_to_le32(the_lnet.ln_pid); } msg->msg_target_is_router = 1; @@ -1262,21 +1281,10 @@ lnet_send(lnet_ni_t *ni, lnet_msg_t *msg) } /* 'lp' is our best choice of peer */ - LASSERT (lp->lp_ni == src_ni); - if (ni != NULL && ni != src_ni) { - /* A different LND expects a response */ - lnet_peer_decref_locked(lp); - LNET_UNLOCK(); - CERROR("NI mismatch: dest %s expected %s\n", - libcfs_nid2str(dst_nid), - libcfs_net2str(PTL_NIDNET(ni->ni_nid))); - return -EPROTO; - } - - LASSERT (msg->msg_txpeer == NULL); LASSERT (!msg->msg_peertxcredit); LASSERT (!msg->msg_txcredit); + LASSERT (msg->msg_txpeer == NULL); msg->msg_txpeer = lp; /* msg takes my ref on lp */ @@ -1376,6 +1384,8 @@ lnet_parse_put(lnet_ni_t *ni, lnet_msg_t *msg) lnet_setpayloadbuffer(msg); msg->msg_ev.type = LNET_EVENT_PUT; + msg->msg_ev.target.pid = hdr->dest_pid; + msg->msg_ev.target.nid = hdr->dest_nid; msg->msg_ev.hdr_data = hdr->msg.put.hdr_data; /* Must I ACK? If so I'll grab the ack_wmd out of the header and put @@ -1428,6 +1438,8 @@ lnet_parse_get(lnet_ni_t *ni, lnet_msg_t *msg) msg->msg_hdr.msg.reply.dst_wmd = reply_wmd; msg->msg_ev.type = LNET_EVENT_GET; + msg->msg_ev.target.pid = hdr->dest_pid; + msg->msg_ev.target.nid = hdr->dest_nid; msg->msg_ev.hdr_data = 0; /* set msg_recvaftersend so the incoming message is consumed (by @@ -1437,7 +1449,7 @@ lnet_parse_get(lnet_ni_t *ni, lnet_msg_t *msg) * valid. */ msg->msg_recvaftersend = 1; - rc = lnet_send(ni, msg); + rc = lnet_send(ni->ni_nid, msg); if (rc < 0) { /* didn't get as far as lnet_ni_send() */ CERROR("%s: Unable to send REPLY for GET from %s: %d\n", @@ -1507,6 +1519,8 @@ lnet_parse_reply(lnet_ni_t *ni, lnet_msg_t *msg) lnet_setpayloadbuffer(msg); msg->msg_ev.type = LNET_EVENT_REPLY; + msg->msg_ev.target.pid = hdr->dest_pid; + msg->msg_ev.target.nid = hdr->dest_nid; msg->msg_ev.initiator = src; msg->msg_ev.rlength = rlength; msg->msg_ev.mlength = mlength; @@ -1560,6 +1574,8 @@ lnet_parse_ack(lnet_ni_t *ni, lnet_msg_t *msg) lnet_commit_md(md, msg); msg->msg_ev.type = LNET_EVENT_ACK; + msg->msg_ev.target.pid = hdr->dest_pid; + msg->msg_ev.target.nid = hdr->dest_nid; msg->msg_ev.initiator = src; msg->msg_ev.mlength = hdr->msg.ack.mlength; msg->msg_ev.match_bits = hdr->msg.ack.match_bits; @@ -1707,9 +1723,7 @@ lnet_parse(lnet_ni_t *ni, lnet_hdr_t *hdr, lnet_nid_t from_nid, void *private) * know what they're doing; if they don't they're misconfigured, buggy * or malicious so we chop them off at the knees :) */ - for_me = (PTL_NETTYP(PTL_NIDNET(ni->ni_nid)) == LOLND || - lnet_ptlcompat_matchnid(ni->ni_nid, dest_nid)); - + for_me = lnet_ptlcompat_matchnid(ni->ni_nid, dest_nid); if (!for_me) { if (the_lnet.ln_ptlcompat > 0) { /* portals compatibility is single-network */ @@ -1866,7 +1880,7 @@ lnet_parse(lnet_ni_t *ni, lnet_hdr_t *hdr, lnet_nid_t from_nid, void *private) } int -LNetPut(lnet_handle_md_t mdh, lnet_ack_req_t ack, +LNetPut(lnet_nid_t self, lnet_handle_md_t mdh, lnet_ack_req_t ack, lnet_process_id_t target, unsigned int portal, __u64 match_bits, unsigned int offset, __u64 hdr_data) @@ -1944,7 +1958,7 @@ LNetPut(lnet_handle_md_t mdh, lnet_ack_req_t ack, LNET_UNLOCK(); - rc = lnet_send(NULL, msg); + rc = lnet_send(self, msg); if (rc != 0) { CERROR("Error sending PUT to %s: %d\n", libcfs_id2str(target), rc); @@ -2024,7 +2038,7 @@ lnet_create_reply_msg (lnet_ni_t *ni, lnet_msg_t *getmsg) } int -LNetGet(lnet_handle_md_t mdh, +LNetGet(lnet_nid_t self, lnet_handle_md_t mdh, lnet_process_id_t target, unsigned int portal, __u64 match_bits, unsigned int offset) { @@ -2096,7 +2110,7 @@ LNetGet(lnet_handle_md_t mdh, LNET_UNLOCK(); - rc = lnet_send(NULL, msg); + rc = lnet_send(self, msg); if (rc < 0) { CERROR("error sending GET to %s: %d\n", libcfs_id2str(target), rc); @@ -2108,10 +2122,71 @@ LNetGet(lnet_handle_md_t mdh, } int -LNetDist (lnet_nid_t nid, int *order) +LNetDist (lnet_nid_t dstnid, lnet_nid_t *srcnidp, int *orderp) { + struct list_head *e; + lnet_ni_t *ni; + lnet_route_t *route; + lnet_remotenet_t *rnet; + __u32 dstnet = PTL_NIDNET(dstnid); + int hops; + int order = 0; + LASSERT (the_lnet.ln_init); LASSERT (the_lnet.ln_refcount > 0); + + LNET_LOCK(); - return lnet_distance(nid, order); + list_for_each (e, &the_lnet.ln_nis) { + ni = list_entry(e, lnet_ni_t, ni_list); + + if (ni->ni_nid == dstnid || + (the_lnet.ln_ptlcompat > 0 && + PTL_NIDNET(dstnid) == 0 && + PTL_NIDADDR(dstnid) == PTL_NIDADDR(ni->ni_nid) && + PTL_NETTYP(PTL_NIDNET(ni->ni_nid)) != LOLND)) { + if (srcnidp != NULL) + *srcnidp = dstnid; + if (orderp != NULL) + *orderp = 0; + LNET_UNLOCK(); + return 0; + } + + if (PTL_NIDNET(ni->ni_nid) == dstnet || + (the_lnet.ln_ptlcompat > 0 && + dstnet == 0 && + PTL_NETTYP(PTL_NIDNET(ni->ni_nid)) != LOLND)) { + if (srcnidp != NULL) + *srcnidp = ni->ni_nid; + if (orderp != NULL) + *orderp = order; + LNET_UNLOCK(); + return 1; + } + + order++; + } + + list_for_each (e, &the_lnet.ln_remote_nets) { + rnet = list_entry(e, lnet_remotenet_t, lrn_list); + + if (rnet->lrn_net == dstnet) { + LASSERT (!list_empty(&rnet->lrn_routes)); + route = list_entry(rnet->lrn_routes.next, + lnet_route_t, lr_list); + hops = rnet->lrn_hops; + if (srcnidp != NULL) + *srcnidp = route->lr_gateway->lp_ni->ni_nid; + if (orderp != NULL) + *orderp = order; + LNET_UNLOCK(); + return hops + 1; + } + order++; + } + + LNET_UNLOCK(); + return -EHOSTUNREACH; } + diff --git a/lnet/lnet/lib-msg.c b/lnet/lnet/lib-msg.c index c95464f..c7ac4e2 100644 --- a/lnet/lnet/lib-msg.c +++ b/lnet/lnet/lib-msg.c @@ -149,7 +149,7 @@ lnet_finalize (lnet_ni_t *ni, lnet_msg_t *msg, int status) msg->msg_hdr.msg.ack.mlength = cpu_to_le32(msg->msg_ev.mlength); LASSERT(!in_interrupt()); - rc = lnet_send(ni, msg); + rc = lnet_send(ni->ni_nid, msg); LASSERT(!in_interrupt()); if (rc == 0) return; @@ -164,7 +164,7 @@ lnet_finalize (lnet_ni_t *ni, lnet_msg_t *msg, int status) LNET_UNLOCK(); LASSERT(!in_interrupt()); - rc = lnet_send(NULL, msg); + rc = lnet_send(LNET_NID_ANY, msg); LASSERT(!in_interrupt()); if (rc == 0) return; diff --git a/lnet/lnet/router.c b/lnet/lnet/router.c index 863d60b..85b88a7 100644 --- a/lnet/lnet/router.c +++ b/lnet/lnet/router.c @@ -206,36 +206,6 @@ lnet_find_net_locked (__u32 net) } int -lnet_distance (lnet_nid_t nid, int *orderp) -{ - struct list_head *e; - lnet_remotenet_t *rnet; - __u32 net = PTL_NIDNET(nid); - int dist = -ENETUNREACH; - int order = 0; - - if (lnet_islocalnet(net, orderp)) - return 0; - - LNET_LOCK(); - - list_for_each (e, &the_lnet.ln_remote_nets) { - rnet = list_entry(e, lnet_remotenet_t, lrn_list); - - if (rnet->lrn_net == net) { - dist = rnet->lrn_hops; - if (orderp != NULL) - *orderp = order; - break; - } - order++; - } - - LNET_UNLOCK(); - return dist; -} - -int lnet_add_route (__u32 net, unsigned int hops, lnet_nid_t gateway) { struct list_head zombies; @@ -251,12 +221,14 @@ lnet_add_route (__u32 net, unsigned int hops, lnet_nid_t gateway) libcfs_net2str(net), hops, libcfs_nid2str(gateway)); if (gateway == LNET_NID_ANY || + PTL_NETTYP(PTL_NIDNET(gateway)) == LOLND || net == PTL_NIDNET(LNET_NID_ANY) || + PTL_NETTYP(net) == LOLND || PTL_NIDNET(gateway) == net || hops < 1 || hops > 255) return (-EINVAL); - if (lnet_islocalnet(net, NULL)) /* it's a local network */ + if (lnet_islocalnet(net)) /* it's a local network */ return 0; /* ignore the route entry */ /* Assume net, route, all new */ diff --git a/lnet/tests/ping_cli.c b/lnet/tests/ping_cli.c index 181900b..c9ed801 100644 --- a/lnet/tests/ping_cli.c +++ b/lnet/tests/ping_cli.c @@ -230,7 +230,8 @@ pingcli_start(struct portal_ioctl_data *args) memcpy(client->outbuf+sizeof(unsigned)+sizeof(unsigned),&tv1, sizeof(struct timeval)); - if((rc = LNetPut (client->md_out_head_h, LNET_NOACK_REQ, + if((rc = LNetPut (LNET_NID_ANY, client->md_out_head_h, + LNET_NOACK_REQ, client->id_remote, PTL_PING_SERVER, 0, 0, 0))) { PDEBUG ("LNetPut (header)", rc); diff --git a/lnet/tests/ping_srv.c b/lnet/tests/ping_srv.c index 90e11c5..0646d9f 100644 --- a/lnet/tests/ping_srv.c +++ b/lnet/tests/ping_srv.c @@ -137,7 +137,8 @@ int pingsrv_thread(void *arg) CDEBUG (D_OTHER, "ping server resources allocated\n"); } - if ((rc = LNetPut (server->mdout_h, LNET_NOACK_REQ, + if ((rc = LNetPut (server->evnt.target.nid, server->mdout_h, + LNET_NOACK_REQ, server->evnt.initiator, PTL_PING_CLIENT, 0, 0, 0))) PDEBUG ("LNetPut", rc); diff --git a/lnet/tests/sping_cli.c b/lnet/tests/sping_cli.c index d21cf65..a4923d7 100644 --- a/lnet/tests/sping_cli.c +++ b/lnet/tests/sping_cli.c @@ -211,7 +211,7 @@ pingcli_start(struct portal_ioctl_data *args) return; } /* Put the ping packet */ - if((rc = LNetPut (client->md_out_head_h, LNET_NOACK_REQ, + if((rc = LNetPut (LNET_NID_ANY, client->md_out_head_h, LNET_NOACK_REQ, client->id_remote, PTL_PING_SERVER, 0, 0, 0))) { PDEBUG ("LNetPut (header)", rc); diff --git a/lnet/tests/sping_srv.c b/lnet/tests/sping_srv.c index e22eea5..d9d8321 100644 --- a/lnet/tests/sping_srv.c +++ b/lnet/tests/sping_srv.c @@ -146,7 +146,8 @@ int pingsrv_thread(void *arg) CDEBUG (D_OTHER, "ping server resources allocated\n"); } - if ((rc = LNetPut (server->mdout_h, LNET_NOACK_REQ, + if ((rc = LNetPut (server->evnt.target.nid, + server->mdout_h, LNET_NOACK_REQ, server->evnt.initiator, PTL_PING_CLIENT, 0, 0, 0))) PDEBUG ("LNetPut", rc); diff --git a/lnet/tests/ut_cli.c b/lnet/tests/ut_cli.c index 33088c7..a6e2650 100644 --- a/lnet/tests/ut_cli.c +++ b/lnet/tests/ut_cli.c @@ -108,6 +108,7 @@ static int __init utcli_init(void) if(get){ PJK_UT_MSG("LNetGet()\n"); if((rc = LNetGet ( + LNET_ID_ANY, mdh, target, /* peer "address" */ UT_PORTAL, /* portal */ @@ -121,6 +122,7 @@ static int __init utcli_init(void) PJK_UT_MSG("LNetPut()\n"); if((rc = LNetPut ( + LNET_ID_ANY, mdh, LNET_ACK_REQ, /* we want ack */ target, /* peer "address" */ -- 1.8.3.1