hyperv/hn: Avoid the hv_device
This paves way to nuke the hv_device, which is actually an unncessary indirection. MFC after: 1 week Sponsored by: Microsoft OSTC Differential Revision: https://reviews.freebsd.org/D7033
This commit is contained in:
parent
0159c1e4b5
commit
4f58713202
@ -58,31 +58,30 @@ MALLOC_DEFINE(M_NETVSC, "netvsc", "Hyper-V netvsc driver");
|
||||
* Forward declarations
|
||||
*/
|
||||
static void hv_nv_on_channel_callback(void *xchan);
|
||||
static int hv_nv_init_send_buffer_with_net_vsp(struct hv_device *device);
|
||||
static int hv_nv_init_rx_buffer_with_net_vsp(struct hv_device *device);
|
||||
static int hv_nv_init_send_buffer_with_net_vsp(struct hn_softc *sc);
|
||||
static int hv_nv_init_rx_buffer_with_net_vsp(struct hn_softc *);
|
||||
static int hv_nv_destroy_send_buffer(netvsc_dev *net_dev);
|
||||
static int hv_nv_destroy_rx_buffer(netvsc_dev *net_dev);
|
||||
static int hv_nv_connect_to_vsp(struct hv_device *device);
|
||||
static int hv_nv_connect_to_vsp(struct hn_softc *sc);
|
||||
static void hv_nv_on_send_completion(netvsc_dev *net_dev,
|
||||
struct hv_device *device, struct hv_vmbus_channel *, hv_vm_packet_descriptor *pkt);
|
||||
struct hv_vmbus_channel *, hv_vm_packet_descriptor *pkt);
|
||||
static void hv_nv_on_receive_completion(struct hv_vmbus_channel *chan,
|
||||
uint64_t tid, uint32_t status);
|
||||
static void hv_nv_on_receive(netvsc_dev *net_dev,
|
||||
struct hv_device *device, struct hv_vmbus_channel *chan,
|
||||
struct hn_softc *sc, struct hv_vmbus_channel *chan,
|
||||
hv_vm_packet_descriptor *pkt);
|
||||
|
||||
/*
|
||||
*
|
||||
*/
|
||||
static inline netvsc_dev *
|
||||
hv_nv_alloc_net_device(struct hv_device *device)
|
||||
hv_nv_alloc_net_device(struct hn_softc *sc)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
|
||||
net_dev = malloc(sizeof(netvsc_dev), M_NETVSC, M_WAITOK | M_ZERO);
|
||||
|
||||
net_dev->dev = device;
|
||||
net_dev->sc = sc;
|
||||
net_dev->destroy = FALSE;
|
||||
sc->net_dev = net_dev;
|
||||
|
||||
@ -90,43 +89,21 @@ hv_nv_alloc_net_device(struct hv_device *device)
|
||||
}
|
||||
|
||||
/*
|
||||
*
|
||||
* XXX unnecessary; nuke it.
|
||||
*/
|
||||
static inline netvsc_dev *
|
||||
hv_nv_get_outbound_net_device(struct hv_device *device)
|
||||
hv_nv_get_outbound_net_device(struct hn_softc *sc)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;;
|
||||
|
||||
if ((net_dev != NULL) && net_dev->destroy) {
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
return (net_dev);
|
||||
return sc->net_dev;
|
||||
}
|
||||
|
||||
/*
|
||||
*
|
||||
* XXX unnecessary; nuke it.
|
||||
*/
|
||||
static inline netvsc_dev *
|
||||
hv_nv_get_inbound_net_device(struct hv_device *device)
|
||||
hv_nv_get_inbound_net_device(struct hn_softc *sc)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;;
|
||||
|
||||
if (net_dev == NULL) {
|
||||
return (net_dev);
|
||||
}
|
||||
/*
|
||||
* When the device is being destroyed; we only
|
||||
* permit incoming packets if and only if there
|
||||
* are outstanding sends.
|
||||
*/
|
||||
if (net_dev->destroy) {
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
return (net_dev);
|
||||
return sc->net_dev;
|
||||
}
|
||||
|
||||
int
|
||||
@ -164,13 +141,13 @@ hv_nv_get_next_send_section(netvsc_dev *net_dev)
|
||||
* Hyper-V extensible switch and the synthetic data path.
|
||||
*/
|
||||
static int
|
||||
hv_nv_init_rx_buffer_with_net_vsp(struct hv_device *device)
|
||||
hv_nv_init_rx_buffer_with_net_vsp(struct hn_softc *sc)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
nvsp_msg *init_pkt;
|
||||
int ret = 0;
|
||||
|
||||
net_dev = hv_nv_get_outbound_net_device(device);
|
||||
net_dev = hv_nv_get_outbound_net_device(sc);
|
||||
if (!net_dev) {
|
||||
return (ENODEV);
|
||||
}
|
||||
@ -185,7 +162,7 @@ hv_nv_init_rx_buffer_with_net_vsp(struct hv_device *device)
|
||||
* GPADL: Guest physical address descriptor list.
|
||||
*/
|
||||
ret = hv_vmbus_channel_establish_gpadl(
|
||||
device->channel, net_dev->rx_buf,
|
||||
sc->hn_prichan, net_dev->rx_buf,
|
||||
net_dev->rx_buf_size, &net_dev->rx_buf_gpadl_handle);
|
||||
if (ret != 0) {
|
||||
goto cleanup;
|
||||
@ -206,7 +183,7 @@ hv_nv_init_rx_buffer_with_net_vsp(struct hv_device *device)
|
||||
|
||||
/* Send the gpadl notification request */
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)(uintptr_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND,
|
||||
HV_VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
|
||||
@ -256,13 +233,13 @@ hv_nv_init_rx_buffer_with_net_vsp(struct hv_device *device)
|
||||
* Net VSC initialize send buffer with net VSP
|
||||
*/
|
||||
static int
|
||||
hv_nv_init_send_buffer_with_net_vsp(struct hv_device *device)
|
||||
hv_nv_init_send_buffer_with_net_vsp(struct hn_softc *sc)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
nvsp_msg *init_pkt;
|
||||
int ret = 0;
|
||||
|
||||
net_dev = hv_nv_get_outbound_net_device(device);
|
||||
net_dev = hv_nv_get_outbound_net_device(sc);
|
||||
if (!net_dev) {
|
||||
return (ENODEV);
|
||||
}
|
||||
@ -279,7 +256,7 @@ hv_nv_init_send_buffer_with_net_vsp(struct hv_device *device)
|
||||
* Note: This call uses the vmbus connection rather than the
|
||||
* channel to establish the gpadl handle.
|
||||
*/
|
||||
ret = hv_vmbus_channel_establish_gpadl(device->channel,
|
||||
ret = hv_vmbus_channel_establish_gpadl(sc->hn_prichan,
|
||||
net_dev->send_buf, net_dev->send_buf_size,
|
||||
&net_dev->send_buf_gpadl_handle);
|
||||
if (ret != 0) {
|
||||
@ -300,7 +277,7 @@ hv_nv_init_send_buffer_with_net_vsp(struct hv_device *device)
|
||||
|
||||
/* Send the gpadl notification request */
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND,
|
||||
HV_VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
|
||||
@ -360,7 +337,7 @@ hv_nv_destroy_rx_buffer(netvsc_dev *net_dev)
|
||||
revoke_pkt->msgs.vers_1_msgs.revoke_rx_buf.id =
|
||||
NETVSC_RECEIVE_BUFFER_ID;
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(net_dev->dev->channel,
|
||||
ret = hv_vmbus_channel_send_packet(net_dev->sc->hn_prichan,
|
||||
revoke_pkt, sizeof(nvsp_msg),
|
||||
(uint64_t)(uintptr_t)revoke_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND, 0);
|
||||
@ -376,7 +353,7 @@ hv_nv_destroy_rx_buffer(netvsc_dev *net_dev)
|
||||
|
||||
/* Tear down the gpadl on the vsp end */
|
||||
if (net_dev->rx_buf_gpadl_handle) {
|
||||
ret = hv_vmbus_channel_teardown_gpdal(net_dev->dev->channel,
|
||||
ret = hv_vmbus_channel_teardown_gpdal(net_dev->sc->hn_prichan,
|
||||
net_dev->rx_buf_gpadl_handle);
|
||||
/*
|
||||
* If we failed here, we might as well return and have a leak
|
||||
@ -428,7 +405,7 @@ hv_nv_destroy_send_buffer(netvsc_dev *net_dev)
|
||||
revoke_pkt->msgs.vers_1_msgs.revoke_send_buf.id =
|
||||
NETVSC_SEND_BUFFER_ID;
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(net_dev->dev->channel,
|
||||
ret = hv_vmbus_channel_send_packet(net_dev->sc->hn_prichan,
|
||||
revoke_pkt, sizeof(nvsp_msg),
|
||||
(uint64_t)(uintptr_t)revoke_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND, 0);
|
||||
@ -443,7 +420,7 @@ hv_nv_destroy_send_buffer(netvsc_dev *net_dev)
|
||||
|
||||
/* Tear down the gpadl on the vsp end */
|
||||
if (net_dev->send_buf_gpadl_handle) {
|
||||
ret = hv_vmbus_channel_teardown_gpdal(net_dev->dev->channel,
|
||||
ret = hv_vmbus_channel_teardown_gpdal(net_dev->sc->hn_prichan,
|
||||
net_dev->send_buf_gpadl_handle);
|
||||
|
||||
/*
|
||||
@ -478,7 +455,7 @@ hv_nv_destroy_send_buffer(netvsc_dev *net_dev)
|
||||
* to the negotiated version, so we cannot rely on that.
|
||||
*/
|
||||
static int
|
||||
hv_nv_negotiate_nvsp_protocol(struct hv_device *device, netvsc_dev *net_dev,
|
||||
hv_nv_negotiate_nvsp_protocol(struct hn_softc *sc, netvsc_dev *net_dev,
|
||||
uint32_t nvsp_ver)
|
||||
{
|
||||
nvsp_msg *init_pkt;
|
||||
@ -495,7 +472,7 @@ hv_nv_negotiate_nvsp_protocol(struct hv_device *device, netvsc_dev *net_dev,
|
||||
init_pkt->msgs.init_msgs.init.protocol_version_2 = nvsp_ver;
|
||||
|
||||
/* Send the init request */
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)(uintptr_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND,
|
||||
HV_VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
|
||||
@ -516,13 +493,13 @@ hv_nv_negotiate_nvsp_protocol(struct hv_device *device, netvsc_dev *net_dev,
|
||||
* Not valid for NDIS version 1.
|
||||
*/
|
||||
static int
|
||||
hv_nv_send_ndis_config(struct hv_device *device, uint32_t mtu)
|
||||
hv_nv_send_ndis_config(struct hn_softc *sc, uint32_t mtu)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
nvsp_msg *init_pkt;
|
||||
int ret;
|
||||
|
||||
net_dev = hv_nv_get_outbound_net_device(device);
|
||||
net_dev = hv_nv_get_outbound_net_device(sc);
|
||||
if (!net_dev)
|
||||
return (-ENODEV);
|
||||
|
||||
@ -539,7 +516,7 @@ hv_nv_send_ndis_config(struct hv_device *device, uint32_t mtu)
|
||||
= 1;
|
||||
|
||||
/* Send the configuration packet */
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)(uintptr_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND, 0);
|
||||
if (ret != 0)
|
||||
@ -552,7 +529,7 @@ hv_nv_send_ndis_config(struct hv_device *device, uint32_t mtu)
|
||||
* Net VSC connect to VSP
|
||||
*/
|
||||
static int
|
||||
hv_nv_connect_to_vsp(struct hv_device *device)
|
||||
hv_nv_connect_to_vsp(struct hn_softc *sc)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
nvsp_msg *init_pkt;
|
||||
@ -564,20 +541,16 @@ hv_nv_connect_to_vsp(struct hv_device *device)
|
||||
int i;
|
||||
int protocol_number = nitems(protocol_list);
|
||||
int ret = 0;
|
||||
device_t dev = device->device;
|
||||
hn_softc_t *sc = device_get_softc(dev);
|
||||
device_t dev = sc->hn_dev;
|
||||
struct ifnet *ifp = sc->hn_ifp;
|
||||
|
||||
net_dev = hv_nv_get_outbound_net_device(device);
|
||||
if (!net_dev) {
|
||||
return (ENODEV);
|
||||
}
|
||||
net_dev = hv_nv_get_outbound_net_device(sc);
|
||||
|
||||
/*
|
||||
* Negotiate the NVSP version. Try the latest NVSP first.
|
||||
*/
|
||||
for (i = protocol_number - 1; i >= 0; i--) {
|
||||
if (hv_nv_negotiate_nvsp_protocol(device, net_dev,
|
||||
if (hv_nv_negotiate_nvsp_protocol(sc, net_dev,
|
||||
protocol_list[i]) == 0) {
|
||||
net_dev->nvsp_version = protocol_list[i];
|
||||
if (bootverbose)
|
||||
@ -599,7 +572,7 @@ hv_nv_connect_to_vsp(struct hv_device *device)
|
||||
* This needs to be right after the NVSP init message per Haiyang
|
||||
*/
|
||||
if (net_dev->nvsp_version >= NVSP_PROTOCOL_VERSION_2)
|
||||
ret = hv_nv_send_ndis_config(device, ifp->if_mtu);
|
||||
ret = hv_nv_send_ndis_config(sc, ifp->if_mtu);
|
||||
|
||||
/*
|
||||
* Send the NDIS version
|
||||
@ -622,7 +595,7 @@ hv_nv_connect_to_vsp(struct hv_device *device)
|
||||
|
||||
/* Send the init request */
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)(uintptr_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND, 0);
|
||||
if (ret != 0) {
|
||||
@ -643,9 +616,9 @@ hv_nv_connect_to_vsp(struct hv_device *device)
|
||||
net_dev->rx_buf_size = NETVSC_RECEIVE_BUFFER_SIZE;
|
||||
net_dev->send_buf_size = NETVSC_SEND_BUFFER_SIZE;
|
||||
|
||||
ret = hv_nv_init_rx_buffer_with_net_vsp(device);
|
||||
ret = hv_nv_init_rx_buffer_with_net_vsp(sc);
|
||||
if (ret == 0)
|
||||
ret = hv_nv_init_send_buffer_with_net_vsp(device);
|
||||
ret = hv_nv_init_send_buffer_with_net_vsp(sc);
|
||||
|
||||
cleanup:
|
||||
return (ret);
|
||||
@ -677,13 +650,13 @@ hv_nv_subchan_attach(struct hv_vmbus_channel *chan)
|
||||
* Callback when the device belonging to this driver is added
|
||||
*/
|
||||
netvsc_dev *
|
||||
hv_nv_on_device_add(struct hv_device *device, void *additional_info)
|
||||
hv_nv_on_device_add(struct hn_softc *sc, void *additional_info)
|
||||
{
|
||||
struct hv_vmbus_channel *chan = device->channel;
|
||||
struct hv_vmbus_channel *chan = sc->hn_prichan;
|
||||
netvsc_dev *net_dev;
|
||||
int ret = 0;
|
||||
|
||||
net_dev = hv_nv_alloc_net_device(device);
|
||||
net_dev = hv_nv_alloc_net_device(sc);
|
||||
if (net_dev == NULL)
|
||||
return NULL;
|
||||
|
||||
@ -707,7 +680,7 @@ hv_nv_on_device_add(struct hv_device *device, void *additional_info)
|
||||
/*
|
||||
* Connect with the NetVsp
|
||||
*/
|
||||
ret = hv_nv_connect_to_vsp(device);
|
||||
ret = hv_nv_connect_to_vsp(sc);
|
||||
if (ret != 0)
|
||||
goto close;
|
||||
|
||||
@ -733,9 +706,8 @@ hv_nv_on_device_add(struct hv_device *device, void *additional_info)
|
||||
* Net VSC on device remove
|
||||
*/
|
||||
int
|
||||
hv_nv_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
hv_nv_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;;
|
||||
|
||||
/* Stop outbound traffic ie sends and receives completions */
|
||||
@ -748,12 +720,12 @@ hv_nv_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
/* Now, we can close the channel safely */
|
||||
|
||||
if (!destroy_channel) {
|
||||
device->channel->state =
|
||||
sc->hn_prichan->state =
|
||||
HV_CHANNEL_CLOSING_NONDESTRUCTIVE_STATE;
|
||||
}
|
||||
|
||||
free(device->channel->hv_chan_rdbuf, M_NETVSC);
|
||||
hv_vmbus_channel_close(device->channel);
|
||||
free(sc->hn_prichan->hv_chan_rdbuf, M_NETVSC);
|
||||
hv_vmbus_channel_close(sc->hn_prichan);
|
||||
|
||||
sema_destroy(&net_dev->channel_init_sema);
|
||||
free(net_dev, M_NETVSC);
|
||||
@ -765,8 +737,7 @@ hv_nv_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
* Net VSC on send completion
|
||||
*/
|
||||
static void
|
||||
hv_nv_on_send_completion(netvsc_dev *net_dev,
|
||||
struct hv_device *device, struct hv_vmbus_channel *chan,
|
||||
hv_nv_on_send_completion(netvsc_dev *net_dev, struct hv_vmbus_channel *chan,
|
||||
hv_vm_packet_descriptor *pkt)
|
||||
{
|
||||
nvsp_msg *nvsp_msg_pkt;
|
||||
@ -871,14 +842,14 @@ hv_nv_on_send(struct hv_vmbus_channel *chan, netvsc_packet *pkt)
|
||||
* with virtual addresses.
|
||||
*/
|
||||
static void
|
||||
hv_nv_on_receive(netvsc_dev *net_dev, struct hv_device *device,
|
||||
hv_nv_on_receive(netvsc_dev *net_dev, struct hn_softc *sc,
|
||||
struct hv_vmbus_channel *chan, hv_vm_packet_descriptor *pkt)
|
||||
{
|
||||
hv_vm_transfer_page_packet_header *vm_xfer_page_pkt;
|
||||
nvsp_msg *nvsp_msg_pkt;
|
||||
netvsc_packet vsc_pkt;
|
||||
netvsc_packet *net_vsc_pkt = &vsc_pkt;
|
||||
device_t dev = device->device;
|
||||
device_t dev = sc->hn_dev;
|
||||
int count = 0;
|
||||
int i = 0;
|
||||
int status = nvsp_status_success;
|
||||
@ -912,7 +883,6 @@ hv_nv_on_receive(netvsc_dev *net_dev, struct hv_device *device,
|
||||
}
|
||||
|
||||
count = vm_xfer_page_pkt->range_count;
|
||||
net_vsc_pkt->device = device;
|
||||
|
||||
/* Each range represents 1 RNDIS pkt that contains 1 Ethernet frame */
|
||||
for (i = 0; i < count; i++) {
|
||||
@ -922,7 +892,7 @@ hv_nv_on_receive(netvsc_dev *net_dev, struct hv_device *device,
|
||||
net_vsc_pkt->tot_data_buf_len =
|
||||
vm_xfer_page_pkt->ranges[i].byte_count;
|
||||
|
||||
hv_rf_on_receive(net_dev, device, chan, net_vsc_pkt);
|
||||
hv_rf_on_receive(net_dev, chan, net_vsc_pkt);
|
||||
if (net_vsc_pkt->status != nvsp_status_success) {
|
||||
status = nvsp_status_failure;
|
||||
}
|
||||
@ -978,14 +948,14 @@ hv_nv_on_receive_completion(struct hv_vmbus_channel *chan, uint64_t tid,
|
||||
* Net VSC receiving vRSS send table from VSP
|
||||
*/
|
||||
static void
|
||||
hv_nv_send_table(struct hv_device *device, hv_vm_packet_descriptor *pkt)
|
||||
hv_nv_send_table(struct hn_softc *sc, hv_vm_packet_descriptor *pkt)
|
||||
{
|
||||
netvsc_dev *net_dev;
|
||||
nvsp_msg *nvsp_msg_pkt;
|
||||
int i;
|
||||
uint32_t count, *table;
|
||||
|
||||
net_dev = hv_nv_get_inbound_net_device(device);
|
||||
net_dev = hv_nv_get_inbound_net_device(sc);
|
||||
if (!net_dev)
|
||||
return;
|
||||
|
||||
@ -1021,9 +991,9 @@ static void
|
||||
hv_nv_on_channel_callback(void *xchan)
|
||||
{
|
||||
struct hv_vmbus_channel *chan = xchan;
|
||||
struct hv_device *device = chan->device;
|
||||
device_t dev = chan->ch_dev;
|
||||
struct hn_softc *sc = device_get_softc(dev);
|
||||
netvsc_dev *net_dev;
|
||||
device_t dev = device->device;
|
||||
uint32_t bytes_rxed;
|
||||
uint64_t request_id;
|
||||
hv_vm_packet_descriptor *desc;
|
||||
@ -1031,7 +1001,7 @@ hv_nv_on_channel_callback(void *xchan)
|
||||
int bufferlen = NETVSC_PACKET_SIZE;
|
||||
int ret = 0;
|
||||
|
||||
net_dev = hv_nv_get_inbound_net_device(device);
|
||||
net_dev = hv_nv_get_inbound_net_device(sc);
|
||||
if (net_dev == NULL)
|
||||
return;
|
||||
|
||||
@ -1045,14 +1015,14 @@ hv_nv_on_channel_callback(void *xchan)
|
||||
desc = (hv_vm_packet_descriptor *)buffer;
|
||||
switch (desc->type) {
|
||||
case HV_VMBUS_PACKET_TYPE_COMPLETION:
|
||||
hv_nv_on_send_completion(net_dev, device,
|
||||
chan, desc);
|
||||
hv_nv_on_send_completion(net_dev, chan,
|
||||
desc);
|
||||
break;
|
||||
case HV_VMBUS_PACKET_TYPE_DATA_USING_TRANSFER_PAGES:
|
||||
hv_nv_on_receive(net_dev, device, chan, desc);
|
||||
hv_nv_on_receive(net_dev, sc, chan, desc);
|
||||
break;
|
||||
case HV_VMBUS_PACKET_TYPE_DATA_IN_BAND:
|
||||
hv_nv_send_table(device, desc);
|
||||
hv_nv_send_table(sc, desc);
|
||||
break;
|
||||
default:
|
||||
device_printf(dev,
|
||||
|
@ -1040,7 +1040,7 @@ typedef struct nvsp_msg_ {
|
||||
* Per netvsc channel-specific
|
||||
*/
|
||||
typedef struct netvsc_dev_ {
|
||||
struct hv_device *dev;
|
||||
struct hn_softc *sc;
|
||||
|
||||
/* Send buffer allocated by us but manages by NetVSP */
|
||||
void *send_buf;
|
||||
@ -1107,7 +1107,6 @@ typedef void (*pfn_on_send_rx_completion)(struct hv_vmbus_channel *, void *);
|
||||
#endif
|
||||
|
||||
typedef struct netvsc_packet_ {
|
||||
struct hv_device *device;
|
||||
hv_bool_uint8_t is_data_pkt; /* One byte */
|
||||
uint16_t vlan_tci;
|
||||
uint32_t status;
|
||||
@ -1239,8 +1238,8 @@ typedef struct hn_softc {
|
||||
int hn_initdone;
|
||||
/* See hv_netvsc_drv_freebsd.c for rules on how to use */
|
||||
int temp_unusable;
|
||||
struct hv_device *hn_dev_obj;
|
||||
netvsc_dev *net_dev;
|
||||
struct hv_vmbus_channel *hn_prichan;
|
||||
|
||||
int hn_rx_ring_cnt;
|
||||
int hn_rx_ring_inuse;
|
||||
@ -1262,10 +1261,10 @@ typedef struct hn_softc {
|
||||
*/
|
||||
extern int hv_promisc_mode;
|
||||
|
||||
void netvsc_linkstatus_callback(struct hv_device *device_obj, uint32_t status);
|
||||
netvsc_dev *hv_nv_on_device_add(struct hv_device *device,
|
||||
void netvsc_linkstatus_callback(struct hn_softc *sc, uint32_t status);
|
||||
netvsc_dev *hv_nv_on_device_add(struct hn_softc *sc,
|
||||
void *additional_info);
|
||||
int hv_nv_on_device_remove(struct hv_device *device,
|
||||
int hv_nv_on_device_remove(struct hn_softc *sc,
|
||||
boolean_t destroy_channel);
|
||||
int hv_nv_on_send(struct hv_vmbus_channel *chan, netvsc_packet *pkt);
|
||||
int hv_nv_get_next_send_section(netvsc_dev *net_dev);
|
||||
|
@ -428,8 +428,6 @@ netvsc_probe(device_t dev)
|
||||
static int
|
||||
netvsc_attach(device_t dev)
|
||||
{
|
||||
struct hv_device *device_ctx = vmbus_get_devctx(dev);
|
||||
struct hv_vmbus_channel *pri_chan;
|
||||
netvsc_device_info device_info;
|
||||
hn_softc_t *sc;
|
||||
int unit = device_get_unit(dev);
|
||||
@ -443,6 +441,7 @@ netvsc_attach(device_t dev)
|
||||
|
||||
sc->hn_unit = unit;
|
||||
sc->hn_dev = dev;
|
||||
sc->hn_prichan = vmbus_get_channel(dev);
|
||||
|
||||
if (hn_tx_taskq == NULL) {
|
||||
sc->hn_tx_taskq = taskqueue_create("hn_tx", M_WAITOK,
|
||||
@ -466,8 +465,6 @@ netvsc_attach(device_t dev)
|
||||
}
|
||||
NV_LOCK_INIT(sc, "NetVSCLock");
|
||||
|
||||
sc->hn_dev_obj = device_ctx;
|
||||
|
||||
ifp = sc->hn_ifp = if_alloc(IFT_ETHER);
|
||||
ifp->if_softc = sc;
|
||||
if_initname(ifp, device_get_name(dev), device_get_unit(dev));
|
||||
@ -510,12 +507,7 @@ netvsc_attach(device_t dev)
|
||||
/*
|
||||
* Associate the first TX/RX ring w/ the primary channel.
|
||||
*/
|
||||
pri_chan = device_ctx->channel;
|
||||
KASSERT(HV_VMBUS_CHAN_ISPRIMARY(pri_chan), ("not primary channel"));
|
||||
KASSERT(pri_chan->ch_subidx == 0,
|
||||
("primary channel subidx %u",
|
||||
pri_chan->ch_subidx));
|
||||
hn_channel_attach(sc, pri_chan);
|
||||
hn_channel_attach(sc, sc->hn_prichan);
|
||||
|
||||
ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
|
||||
ifp->if_ioctl = hn_ioctl;
|
||||
@ -552,7 +544,7 @@ netvsc_attach(device_t dev)
|
||||
IFCAP_LRO;
|
||||
ifp->if_hwassist = sc->hn_tx_ring[0].hn_csum_assist | CSUM_TSO;
|
||||
|
||||
error = hv_rf_on_device_add(device_ctx, &device_info, ring_cnt);
|
||||
error = hv_rf_on_device_add(sc, &device_info, ring_cnt);
|
||||
if (error)
|
||||
goto failed;
|
||||
KASSERT(sc->net_dev->num_channel > 0 &&
|
||||
@ -626,7 +618,6 @@ static int
|
||||
netvsc_detach(device_t dev)
|
||||
{
|
||||
struct hn_softc *sc = device_get_softc(dev);
|
||||
struct hv_device *hv_device = vmbus_get_devctx(dev);
|
||||
|
||||
if (bootverbose)
|
||||
printf("netvsc_detach\n");
|
||||
@ -642,7 +633,7 @@ netvsc_detach(device_t dev)
|
||||
* the netdevice.
|
||||
*/
|
||||
|
||||
hv_rf_on_device_remove(hv_device, HV_RF_NV_DESTROY_CHANNEL);
|
||||
hv_rf_on_device_remove(sc, HV_RF_NV_DESTROY_CHANNEL);
|
||||
|
||||
hn_stop_tx_tasks(sc);
|
||||
|
||||
@ -1201,10 +1192,8 @@ hn_start_locked(struct hn_tx_ring *txr, int len)
|
||||
* Link up/down notification
|
||||
*/
|
||||
void
|
||||
netvsc_linkstatus_callback(struct hv_device *device_obj, uint32_t status)
|
||||
netvsc_linkstatus_callback(struct hn_softc *sc, uint32_t status)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device_obj->device);
|
||||
|
||||
if (status == 1) {
|
||||
sc->hn_carrier = 1;
|
||||
} else {
|
||||
@ -1525,7 +1514,6 @@ hn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
struct ifaddr *ifa = (struct ifaddr *)data;
|
||||
#endif
|
||||
netvsc_device_info device_info;
|
||||
struct hv_device *hn_dev;
|
||||
int mask, error = 0;
|
||||
int retry_cnt = 500;
|
||||
|
||||
@ -1543,8 +1531,6 @@ hn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
error = ether_ioctl(ifp, cmd, data);
|
||||
break;
|
||||
case SIOCSIFMTU:
|
||||
hn_dev = vmbus_get_devctx(sc->hn_dev);
|
||||
|
||||
/* Check MTU value change */
|
||||
if (ifp->if_mtu == ifr->ifr_mtu)
|
||||
break;
|
||||
@ -1591,7 +1577,7 @@ hn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
* MTU to take effect. This includes tearing down, but not
|
||||
* deleting the channel, then bringing it back up.
|
||||
*/
|
||||
error = hv_rf_on_device_remove(hn_dev, HV_RF_NV_RETAIN_CHANNEL);
|
||||
error = hv_rf_on_device_remove(sc, HV_RF_NV_RETAIN_CHANNEL);
|
||||
if (error) {
|
||||
NV_LOCK(sc);
|
||||
sc->temp_unusable = FALSE;
|
||||
@ -1600,9 +1586,9 @@ hn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
}
|
||||
|
||||
/* Wait for subchannels to be destroyed */
|
||||
vmbus_drain_subchan(hn_dev->channel);
|
||||
vmbus_drain_subchan(sc->hn_prichan);
|
||||
|
||||
error = hv_rf_on_device_add(hn_dev, &device_info,
|
||||
error = hv_rf_on_device_add(sc, &device_info,
|
||||
sc->hn_rx_ring_inuse);
|
||||
if (error) {
|
||||
NV_LOCK(sc);
|
||||
@ -1767,7 +1753,6 @@ hn_stop(hn_softc_t *sc)
|
||||
{
|
||||
struct ifnet *ifp;
|
||||
int ret, i;
|
||||
struct hv_device *device_ctx = vmbus_get_devctx(sc->hn_dev);
|
||||
|
||||
ifp = sc->hn_ifp;
|
||||
|
||||
@ -1782,7 +1767,7 @@ hn_stop(hn_softc_t *sc)
|
||||
if_link_state_change(ifp, LINK_STATE_DOWN);
|
||||
sc->hn_initdone = 0;
|
||||
|
||||
ret = hv_rf_on_close(device_ctx);
|
||||
ret = hv_rf_on_close(sc);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1850,7 +1835,6 @@ static void
|
||||
hn_ifinit_locked(hn_softc_t *sc)
|
||||
{
|
||||
struct ifnet *ifp;
|
||||
struct hv_device *device_ctx = vmbus_get_devctx(sc->hn_dev);
|
||||
int ret, i;
|
||||
|
||||
ifp = sc->hn_ifp;
|
||||
@ -1861,7 +1845,7 @@ hn_ifinit_locked(hn_softc_t *sc)
|
||||
|
||||
hv_promisc_mode = 1;
|
||||
|
||||
ret = hv_rf_on_open(device_ctx);
|
||||
ret = hv_rf_on_open(sc);
|
||||
if (ret != 0) {
|
||||
return;
|
||||
} else {
|
||||
@ -2984,13 +2968,12 @@ hn_subchan_attach(struct hn_softc *sc, struct hv_vmbus_channel *chan)
|
||||
static void
|
||||
hn_subchan_setup(struct hn_softc *sc)
|
||||
{
|
||||
struct hv_device *device_ctx = vmbus_get_devctx(sc->hn_dev);
|
||||
struct hv_vmbus_channel **subchan;
|
||||
int subchan_cnt = sc->net_dev->num_channel - 1;
|
||||
int i;
|
||||
|
||||
/* Wait for sub-channels setup to complete. */
|
||||
subchan = vmbus_get_subchan(device_ctx->channel, subchan_cnt);
|
||||
subchan = vmbus_get_subchan(sc->hn_prichan, subchan_cnt);
|
||||
|
||||
/* Attach the sub-channels. */
|
||||
for (i = 0; i < subchan_cnt; ++i) {
|
||||
|
@ -88,7 +88,7 @@ static int hv_rf_close_device(rndis_device *device);
|
||||
static void hv_rf_on_send_request_completion(struct hv_vmbus_channel *, void *context);
|
||||
static void hv_rf_on_send_request_halt_completion(struct hv_vmbus_channel *, void *context);
|
||||
int
|
||||
hv_rf_send_offload_request(struct hv_device *device,
|
||||
hv_rf_send_offload_request(struct hn_softc *sc,
|
||||
rndis_offload_params *offloads);
|
||||
/*
|
||||
* Set the Per-Packet-Info with the specified type
|
||||
@ -298,7 +298,7 @@ hv_rf_send_request(rndis_device *device, rndis_request *request,
|
||||
packet->send_buf_section_size = 0;
|
||||
|
||||
sendit:
|
||||
ret = hv_nv_on_send(device->net_dev->dev->channel, packet);
|
||||
ret = hv_nv_on_send(device->net_dev->sc->hn_prichan, packet);
|
||||
|
||||
return (ret);
|
||||
}
|
||||
@ -350,7 +350,7 @@ hv_rf_receive_response(rndis_device *device, rndis_msg *response)
|
||||
}
|
||||
|
||||
int
|
||||
hv_rf_send_offload_request(struct hv_device *device,
|
||||
hv_rf_send_offload_request(struct hn_softc *sc,
|
||||
rndis_offload_params *offloads)
|
||||
{
|
||||
rndis_request *request;
|
||||
@ -358,8 +358,7 @@ hv_rf_send_offload_request(struct hv_device *device,
|
||||
rndis_offload_params *offload_req;
|
||||
rndis_set_complete *set_complete;
|
||||
rndis_device *rndis_dev;
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
device_t dev = device->device;
|
||||
device_t dev = sc->hn_dev;
|
||||
netvsc_dev *net_dev = sc->net_dev;
|
||||
uint32_t vsp_version = net_dev->nvsp_version;
|
||||
uint32_t extlen = sizeof(rndis_offload_params);
|
||||
@ -436,14 +435,14 @@ hv_rf_receive_indicate_status(rndis_device *device, rndis_msg *response)
|
||||
|
||||
switch(indicate->status) {
|
||||
case RNDIS_STATUS_MEDIA_CONNECT:
|
||||
netvsc_linkstatus_callback(device->net_dev->dev, 1);
|
||||
netvsc_linkstatus_callback(device->net_dev->sc, 1);
|
||||
break;
|
||||
case RNDIS_STATUS_MEDIA_DISCONNECT:
|
||||
netvsc_linkstatus_callback(device->net_dev->dev, 0);
|
||||
netvsc_linkstatus_callback(device->net_dev->sc, 0);
|
||||
break;
|
||||
default:
|
||||
/* TODO: */
|
||||
device_printf(device->net_dev->dev->device,
|
||||
device_printf(device->net_dev->sc->hn_dev,
|
||||
"unknown status %d received\n", indicate->status);
|
||||
break;
|
||||
}
|
||||
@ -536,7 +535,7 @@ hv_rf_receive_data(rndis_device *device, rndis_msg *message,
|
||||
{
|
||||
rndis_packet *rndis_pkt;
|
||||
uint32_t data_offset;
|
||||
device_t dev = device->net_dev->dev->device;
|
||||
device_t dev = device->net_dev->sc->hn_dev;
|
||||
struct hv_rf_recvinfo info;
|
||||
|
||||
rndis_pkt = &message->msg.packet;
|
||||
@ -579,7 +578,7 @@ hv_rf_receive_data(rndis_device *device, rndis_msg *message,
|
||||
* RNDIS filter on receive
|
||||
*/
|
||||
int
|
||||
hv_rf_on_receive(netvsc_dev *net_dev, struct hv_device *device,
|
||||
hv_rf_on_receive(netvsc_dev *net_dev,
|
||||
struct hv_vmbus_channel *chan, netvsc_packet *pkt)
|
||||
{
|
||||
rndis_device *rndis_dev;
|
||||
@ -1061,7 +1060,7 @@ hv_rf_close_device(rndis_device *device)
|
||||
* RNDIS filter on device add
|
||||
*/
|
||||
int
|
||||
hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
hv_rf_on_device_add(struct hn_softc *sc, void *additl_info,
|
||||
int nchan)
|
||||
{
|
||||
int ret;
|
||||
@ -1072,7 +1071,7 @@ hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
struct rndis_recv_scale_cap rsscaps;
|
||||
uint32_t rsscaps_size = sizeof(struct rndis_recv_scale_cap);
|
||||
netvsc_device_info *dev_info = (netvsc_device_info *)additl_info;
|
||||
device_t dev = device->device;
|
||||
device_t dev = sc->hn_dev;
|
||||
|
||||
rndis_dev = hv_get_rndis_device();
|
||||
if (rndis_dev == NULL) {
|
||||
@ -1085,7 +1084,7 @@ hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
* (hv_rf_on_receive()) before this call is completed.
|
||||
* Note: Earlier code used a function pointer here.
|
||||
*/
|
||||
net_dev = hv_nv_on_device_add(device, additl_info);
|
||||
net_dev = hv_nv_on_device_add(sc, additl_info);
|
||||
if (!net_dev) {
|
||||
hv_put_rndis_device(rndis_dev);
|
||||
|
||||
@ -1123,7 +1122,7 @@ hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
offloads.udp_ipv6_csum = RNDIS_OFFLOAD_PARAMETERS_TX_RX_ENABLED;
|
||||
offloads.lso_v2_ipv4 = RNDIS_OFFLOAD_PARAMETERS_LSOV2_ENABLED;
|
||||
|
||||
ret = hv_rf_send_offload_request(device, &offloads);
|
||||
ret = hv_rf_send_offload_request(sc, &offloads);
|
||||
if (ret != 0) {
|
||||
/* TODO: shut down rndis device and the channel */
|
||||
device_printf(dev,
|
||||
@ -1170,7 +1169,7 @@ hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
init_pkt->msgs.vers_5_msgs.subchannel_request.num_subchannels =
|
||||
net_dev->num_channel - 1;
|
||||
|
||||
ret = hv_vmbus_channel_send_packet(device->channel, init_pkt,
|
||||
ret = hv_vmbus_channel_send_packet(sc->hn_prichan, init_pkt,
|
||||
sizeof(nvsp_msg), (uint64_t)(uintptr_t)init_pkt,
|
||||
HV_VMBUS_PACKET_TYPE_DATA_IN_BAND,
|
||||
HV_VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
|
||||
@ -1204,9 +1203,8 @@ hv_rf_on_device_add(struct hv_device *device, void *additl_info,
|
||||
* RNDIS filter on device remove
|
||||
*/
|
||||
int
|
||||
hv_rf_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;
|
||||
rndis_device *rndis_dev = (rndis_device *)net_dev->extension;
|
||||
int ret;
|
||||
@ -1218,7 +1216,7 @@ hv_rf_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
net_dev->extension = NULL;
|
||||
|
||||
/* Pass control to inner driver to remove the device */
|
||||
ret |= hv_nv_on_device_remove(device, destroy_channel);
|
||||
ret |= hv_nv_on_device_remove(sc, destroy_channel);
|
||||
|
||||
return (ret);
|
||||
}
|
||||
@ -1227,9 +1225,8 @@ hv_rf_on_device_remove(struct hv_device *device, boolean_t destroy_channel)
|
||||
* RNDIS filter on open
|
||||
*/
|
||||
int
|
||||
hv_rf_on_open(struct hv_device *device)
|
||||
hv_rf_on_open(struct hn_softc *sc)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;
|
||||
|
||||
return (hv_rf_open_device((rndis_device *)net_dev->extension));
|
||||
@ -1239,9 +1236,8 @@ hv_rf_on_open(struct hv_device *device)
|
||||
* RNDIS filter on close
|
||||
*/
|
||||
int
|
||||
hv_rf_on_close(struct hv_device *device)
|
||||
hv_rf_on_close(struct hn_softc *sc)
|
||||
{
|
||||
hn_softc_t *sc = device_get_softc(device->device);
|
||||
netvsc_dev *net_dev = sc->net_dev;
|
||||
|
||||
return (hv_rf_close_device((rndis_device *)net_dev->extension));
|
||||
|
@ -111,15 +111,16 @@ typedef struct rndis_device_ {
|
||||
* Externs
|
||||
*/
|
||||
struct hv_vmbus_channel;
|
||||
struct hn_softc;
|
||||
|
||||
int hv_rf_on_receive(netvsc_dev *net_dev, struct hv_device *device,
|
||||
int hv_rf_on_receive(netvsc_dev *net_dev,
|
||||
struct hv_vmbus_channel *chan, netvsc_packet *pkt);
|
||||
void hv_rf_receive_rollup(netvsc_dev *net_dev);
|
||||
void hv_rf_channel_rollup(struct hv_vmbus_channel *chan);
|
||||
int hv_rf_on_device_add(struct hv_device *device, void *additl_info, int nchan);
|
||||
int hv_rf_on_device_remove(struct hv_device *device, boolean_t destroy_channel);
|
||||
int hv_rf_on_open(struct hv_device *device);
|
||||
int hv_rf_on_close(struct hv_device *device);
|
||||
int hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, int nchan);
|
||||
int hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel);
|
||||
int hv_rf_on_open(struct hn_softc *sc);
|
||||
int hv_rf_on_close(struct hn_softc *sc);
|
||||
|
||||
#endif /* __HV_RNDIS_FILTER_H__ */
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user