Date: Sun, 11 Oct 2015 20:58:00 +0000 (UTC) From: "Conrad E. Meyer" <cem@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r289153 - head/sys/dev/ntb/if_ntb Message-ID: <201510112058.t9BKw0N0086915@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: cem Date: Sun Oct 11 20:58:00 2015 New Revision: 289153 URL: https://svnweb.freebsd.org/changeset/base/289153 Log: NTB: MFV 113fc505: Handle 64bit BAR sizes 64bit BAR sizes are permissible with an NTB device. To support them various modifications and clean-ups were required, most significantly using 2 32bit scratch pad registers for each BAR. Also, modify the driver to allow more than 2 Memory Windows. Authored by: Jon Mason Obtained from: Linux Sponsored by: EMC / Isilon Storage Division Modified: head/sys/dev/ntb/if_ntb/if_ntb.c Modified: head/sys/dev/ntb/if_ntb/if_ntb.c ============================================================================== --- head/sys/dev/ntb/if_ntb/if_ntb.c Sun Oct 11 20:57:09 2015 (r289152) +++ head/sys/dev/ntb/if_ntb/if_ntb.c Sun Oct 11 20:58:00 2015 (r289153) @@ -194,11 +194,22 @@ struct ntb_payload_header { }; enum { + /* + * The order of this enum is part of the if_ntb remote protocol. Do + * not reorder without bumping protocol version (and it's probably best + * to keep the protocol in lock-step with the Linux NTB driver. + */ IF_NTB_VERSION = 0, - IF_NTB_MW0_SZ, - IF_NTB_MW1_SZ, - IF_NTB_NUM_QPS, IF_NTB_QP_LINKS, + IF_NTB_NUM_QPS, + IF_NTB_NUM_MWS, + /* + * N.B.: transport_link_work assumes MW1 enums = MW0 + 2. + */ + IF_NTB_MW0_SZ_HIGH, + IF_NTB_MW0_SZ_LOW, + IF_NTB_MW1_SZ_HIGH, + IF_NTB_MW1_SZ_LOW, IF_NTB_MAX_SPAD, }; @@ -242,6 +253,7 @@ static void ntb_rx_completion_task(void static void ntb_transport_event_callback(void *data, enum ntb_hw_event event); static void ntb_transport_link_work(void *arg); static int ntb_set_mw(struct ntb_netdev *nt, int num_mw, unsigned int size); +static void ntb_free_mw(struct ntb_netdev *nt, int num_mw); static void ntb_transport_setup_qp_mw(struct ntb_netdev *nt, unsigned int qp_num); static void ntb_qp_link_work(void *arg); @@ -514,9 +526,7 @@ ntb_transport_free(void *transport) ntb_unregister_event_callback(ntb); for (i = 0; i < NTB_NUM_MW; i++) - if (nt->mw[i].virt_addr != NULL) - contigfree(nt->mw[i].virt_addr, nt->mw[i].size, - M_NTB_IF); + ntb_free_mw(nt, i); free(nt->qps, M_NTB_IF); ntb_unregister_transport(ntb); @@ -1019,19 +1029,24 @@ ntb_transport_link_work(void *arg) struct ntb_netdev *nt = arg; struct ntb_softc *ntb = nt->ntb; struct ntb_transport_qp *qp; + uint64_t val64; uint32_t val; int rc, i; - /* send the local info */ - rc = ntb_write_remote_spad(ntb, IF_NTB_VERSION, NTB_TRANSPORT_VERSION); - if (rc != 0) - goto out; - - rc = ntb_write_remote_spad(ntb, IF_NTB_MW0_SZ, ntb_get_mw_size(ntb, 0)); - if (rc != 0) - goto out; + /* send the local info, in the opposite order of the way we read it */ + for (i = 0; i < NTB_NUM_MW; i++) { + rc = ntb_write_remote_spad(ntb, IF_NTB_MW0_SZ_HIGH + (i * 2), + ntb_get_mw_size(ntb, i) >> 32); + if (rc != 0) + goto out; + + rc = ntb_write_remote_spad(ntb, IF_NTB_MW0_SZ_LOW + (i * 2), + (uint32_t)ntb_get_mw_size(ntb, i)); + if (rc != 0) + goto out; + } - rc = ntb_write_remote_spad(ntb, IF_NTB_MW1_SZ, ntb_get_mw_size(ntb, 1)); + rc = ntb_write_remote_spad(ntb, IF_NTB_NUM_MWS, NTB_NUM_MW); if (rc != 0) goto out; @@ -1039,11 +1054,7 @@ ntb_transport_link_work(void *arg) if (rc != 0) goto out; - rc = ntb_read_remote_spad(ntb, IF_NTB_QP_LINKS, &val); - if (rc != 0) - goto out; - - rc = ntb_write_remote_spad(ntb, IF_NTB_QP_LINKS, val); + rc = ntb_write_remote_spad(ntb, IF_NTB_VERSION, NTB_TRANSPORT_VERSION); if (rc != 0) goto out; @@ -1062,27 +1073,32 @@ ntb_transport_link_work(void *arg) if (val != nt->max_qps) goto out; - rc = ntb_read_local_spad(ntb, IF_NTB_MW0_SZ, &val); - if (rc != 0) - goto out; - - if (val == 0) - goto out; - - rc = ntb_set_mw(nt, 0, val); - if (rc != 0) - return; - - rc = ntb_read_local_spad(ntb, IF_NTB_MW1_SZ, &val); + rc = ntb_read_local_spad(ntb, IF_NTB_NUM_MWS, &val); if (rc != 0) goto out; - if (val == 0) + if (val != NTB_NUM_MW) goto out; - rc = ntb_set_mw(nt, 1, val); - if (rc != 0) - return; + for (i = 0; i < NTB_NUM_MW; i++) { + rc = ntb_read_local_spad(ntb, IF_NTB_MW0_SZ_HIGH + (i * 2), + &val); + if (rc != 0) + goto free_mws; + + val64 = (uint64_t)val << 32; + + rc = ntb_read_local_spad(ntb, IF_NTB_MW0_SZ_LOW + (i * 2), + &val); + if (rc != 0) + goto free_mws; + + val64 |= val; + + rc = ntb_set_mw(nt, i, val64); + if (rc != 0) + goto free_mws; + } nt->transport_link = NTB_LINK_UP; if (bootverbose) @@ -1099,10 +1115,13 @@ ntb_transport_link_work(void *arg) return; +free_mws: + for (i = 0; i < NTB_NUM_MW; i++) + ntb_free_mw(nt, i); out: if (ntb_query_link_status(ntb)) callout_reset(&nt->link_work, - NTB_LINK_DOWN_TIMEOUT * hz / 1000, ntb_transport_link_work, nt); + NTB_LINK_DOWN_TIMEOUT * hz / 1000, ntb_transport_link_work, nt); } static int @@ -1130,6 +1149,18 @@ ntb_set_mw(struct ntb_netdev *nt, int nu } static void +ntb_free_mw(struct ntb_netdev *nt, int num_mw) +{ + struct ntb_transport_mw *mw = &nt->mw[num_mw]; + + if (mw->virt_addr == NULL) + return; + + contigfree(mw->virt_addr, mw->size, M_NTB_IF); + mw->virt_addr = NULL; +} + +static void ntb_transport_setup_qp_mw(struct ntb_netdev *nt, unsigned int qp_num) { struct ntb_transport_qp *qp = &nt->qps[qp_num];
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201510112058.t9BKw0N0086915>