Bug 998895 - Could not ping Win7-64 guest successfully after changing e1000 MTU
Could not ping Win7-64 guest successfully after changing e1000 MTU
Status: CLOSED NOTABUG
Product: Red Hat Enterprise Linux 7
Classification: Red Hat
Component: qemu-kvm (Show other bugs)
7.0
Unspecified Unspecified
medium Severity medium
: rc
: ---
Assigned To: Amos Kong
Virtualization Bugs
:
Depends On: 998890
Blocks:
  Show dependency treegraph
 
Reported: 2013-08-20 06:04 EDT by CongLi
Modified: 2015-05-24 20:07 EDT (History)
18 users (show)

See Also:
Fixed In Version:
Doc Type: Bug Fix
Doc Text:
Story Points: ---
Clone Of: 998890
Environment:
Last Closed: 2013-11-27 06:40:31 EST
Type: Bug
Regression: ---
Mount Type: ---
Documentation: ---
CRM:
Verified Versions:
Category: ---
oVirt Team: ---
RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: ---


Attachments (Terms of Use)
enable e1000 jumbo-packet option in win7 (76.14 KB, image/png)
2013-11-27 06:38 EST, Amos Kong
no flags Details

  None (edit)
Description CongLi 2013-08-20 06:04:48 EDT
Tested the case on RHEL7, this bug can be reproduced.

kernel-3.10.0-9.el7.x86_64
qemu-kvm-1.5.2-3.el7.x86_64

+++ This bug was initially created as a clone of Bug #998890 +++

Description of problem:
Could not ping Win7-64 guest successfully after changing e1000 MTU

Version-Release number of selected component (if applicable):
kernel-2.6.32-411.el6.x86_64
qemu-kvm-rhev-tools-0.12.1.2-2.389.el6.x86_64

How reproducible:
100%

Steps to Reproduce:
1. Boot a Win7-64 guest w/ e1000 nic

2. In guest:
   1) wmic nic where macaddress="$guest_macaddress" get netconnectionid  
   2) wmic nic where netconnectionid="Ethernet" get index
   3) reg add HKLM\SYSTEM\CurrentControlSet\Control\Class\{4D36E972-E325-11CE-BFC1-08002BE10318}\0001 /v mtu /d 16128 /f 
   4) netsh interface set interface name="Ethernet" admin=DISABLED
   5) netsh interface set interface name="Ethernet" admin=ENABLED 

3. In host:
   1) ifconfig $tap mtu 16128
   2) arp -s $guest_ip $guest_macaddress -i $tap
   3) ping $guest_ip -c 1 -I $tap -s 16100 -M do

Actual results:
Could not ping guest successfully

Expected results:
Ping guest successfully

Additional info:
1. Tested w/ nic rtl8139 & virtio_net successfully.

2. After changing MTU, disable the e1000 driver in guest, then enable it can ping successfully.

3. Qemu CML:
/home/staf-kvm-devel/autotest-devel/client/tests/virt/qemu/qemu \
    -S \
    -name 'virt-tests-vm1' \
    -nodefaults \
    -chardev socket,id=qmp_id_qmpmonitor1,path=/tmp/monitor-qmpmonitor1-20130815-152836-Ih7kA0vX,server,nowait \
    -mon chardev=qmp_id_qmpmonitor1,mode=control \
    -chardev socket,id=serial_id_serial1,path=/tmp/serial-serial1-20130815-152836-Ih7kA0vX,server,nowait \
    -device isa-serial,chardev=serial_id_serial1 \
    -chardev socket,id=seabioslog_id_20130815-152836-Ih7kA0vX,path=/tmp/seabios-20130815-152836-Ih7kA0vX,server,nowait \
    -device isa-debugcon,chardev=seabioslog_id_20130815-152836-Ih7kA0vX,iobase=0x402 \
    -device ich9-usb-uhci1,id=usb1,bus=pci.0,addr=0x4 \
    -drive file='/home/staf-kvm-devel/autotest-devel/client/tests/virt/shared/data/images/win7-64.qcow2',index=0,if=none,id=drive-ide0-0-0,media=disk,cache=none,snapshot=off,format=qcow2,aio=native \
    -device ide-drive,bus=ide.0,unit=0,drive=drive-ide0-0-0 \
    -device e1000,netdev=idAhvj4X,mac='9a:c0:c1:c2:c3:c4',bus=pci.0,addr=0x3,id='idsiWq2u' \
    -netdev tap,id=idAhvj4X,fd=18 \
    -m 4096 \
    -smp 2,maxcpus=2,cores=1,threads=1,sockets=2 \
    -cpu 'SandyBridge',,+sep \
    -M rhel6.5.0 \
    -drive file='/home/staf-kvm-devel/autotest-devel/client/tests/virt/shared/data/isos/windows/winutils.iso',index=1,if=none,id=drive-ide0-0-1,media=cdrom,format=raw \
    -device ide-drive,bus=ide.0,unit=1,drive=drive-ide0-0-1 \
    -device AC97,addr=0x5 \
    -device usb-tablet,id=usb-tablet1,bus=usb1.0,port=1 \
    -vnc :0 \
    -vga std \
    -rtc base=localtime,clock=host,driftfix=slew  \
    -boot order=cdn,once=c,menu=off  \
    -enable-kvm

4. cpuinfo:
processor	: 3
vendor_id	: GenuineIntel
cpu family	: 6
model		: 42
model name	: Intel(R) Xeon(R) CPU E31225 @ 3.10GHz
stepping	: 7
cpu MHz		: 1600.000
cache size	: 6144 KB
physical id	: 0
siblings	: 4
core id		: 3
cpu cores	: 4
apicid		: 6
initial apicid	: 6
fpu		: yes
fpu_exception	: yes
cpuid level	: 13
wp		: yes
flags		: fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe syscall nx rdtscp lm constant_tsc arch_perfmon pebs bts xtopology nonstop_tsc aperfmperf pni pclmulqdq dtes64 monitor ds_cpl vmx smx est tm2 ssse3 cx16 xtpr pdcm pcid sse4_1 sse4_2 x2apic popcnt tsc_deadline_timer aes xsave avx lahf_lm ida arat epb xsaveopt pln pts dts tpr_shadow vnmi flexpriority ept vpid
bogomips	: 6184.25
clflush size	: 64
cache_alignment	: 64
address sizes	: 36 bits physical, 48 bits virtual
power management:
Comment 2 Amos Kong 2013-11-05 18:46:34 EST
We don't test/support e1000 virt nic of Windows for the driver licence , right?
Comment 3 Amos Kong 2013-11-05 19:26:40 EST
There is a old bug (https://bugzilla.redhat.com/show_bug.cgi?id=602205), it used linux guest.

In linux e1000 driver: static int e1000_change_mtu(...)
|
|	if (netif_running(netdev))
|		e1000_up(adapter);
|	else
|		e1000_reset(adapter);

It means e1000 interface will be auto enabled/reset after mtu changing in linux.

Windows driver is not so smart, manually enable opt is needed?
did you test with other MTU / other Windows guest?

----- 
Cong, can you try this saved setup? let's see if ping works after rebooting.

http://networking.nitecruzr.net/2007/11/setting-mtu-in-windows-vista.html
Comment 5 Amos Kong 2013-11-18 06:25:02 EST
Hi Cong,

I know you touched some new problem in testing this bug.
Let's clear something here.

Based on your description in Comment #1, I infer that:
 1) test passed with Linux guests, all kinds of nics
 2) test passed with Win7, e1000/rtl8139
 3) problem only exists with Win7, virtio-net
    (don't disable&re-enable the nic after changing MTU)
 4) if disable & enable the nic after MTU change, problem in 3) disappears.

It seems not a bug, so I asked you to re-test (re-confirm) the 4 inferences.

So just list all your test result and problem here.
Comment 6 CongLi 2013-11-20 23:57:11 EST
(In reply to Amos Kong from comment #5)
> Hi Cong,
> 
> I know you touched some new problem in testing this bug.
> Let's clear something here.
> 
> Based on your description in Comment #1, I infer that:
>  1) test passed with Linux guests, all kinds of nics
      
      Tested with RHEL.7 guest, all kinds of nics  --> pass

>  2) test passed with Win7, e1000/rtl8139

      <1> virtio-net: ping $guest_ip -c 1 -I $tap -s 16100 -M do  --> pass
      <2> rtl8139:    the max size is 1500
                      ping $guest_ip -c 1 -I $tap -s 1472 -M do  --> pass

>  3) problem only exists with Win7, virtio-net
>     (don't disable&re-enable the nic after changing MTU)

      Tested with Win7-64 guest after changing mtu to 16128:
      e1000:      ping $guest_ip -c 1 -I $tap -s 16100 -M do  --> fail

>  4) if disable & enable the nic after MTU change, problem in 3) disappears.

      e1000:
      Ping 16100 bytes packet failed, then ping 100 bytes packet will failed.
      Disable & enable the nic, can ping 100 bytes packet, but can't ping 16100 bytes.

      e1000:   ping $guest_ip -c 1 -I $tap -s 16100 -M do  --> fail
               ping $guest_ip -c 1 -I $tap -s 100 -M do    --> fail
               disable & enable the nic in guest           --> ok
               ping $guest_ip -c 1 -I $tap -s 100 -M do    --> ok
               ping $guest_ip -c 1 -I $tap -s 16100 -M do  --> fail

> 
> It seems not a bug, so I asked you to re-test (re-confirm) the 4 inferences.
> 
> So just list all your test result and problem here.
Comment 7 Amos Kong 2013-11-27 02:50:18 EST
1) C:\>netsh interface ipv4 set subinterface "Local Area Connection 3" mtu=16110
   (disable & enable is not needed)
2) arp -s 192.168.58.89 52:54:00:12:34:56 -i tap0
3) ping 192.168.58.89  -I tap0 -c 1 -s 16100

ping successfully, request packet is split to many small packets.
But there is only one reply packet, its size is 16088, it means guest can process Jumbo packet in tx.


15:44:06.385763 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: ICMP echo request, id 9037, seq 1, length 1480
15:44:06.385773 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385775 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385776 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385778 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385780 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385781 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385783 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385785 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385786 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1514: amosk.info > 192.168.58.89: icmp
15:44:06.385787 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 1342: amosk.info > 192.168.58.89: icmp
15:44:06.386128 52:54:00:12:34:56 (oui Unknown) > 16:d2:42:8d:bf:a3 (oui Unknown), ethertype IPv4 (0x0800), length 16122: 192.168.58.89 > amosk.info: ICMP echo reply, id 9037, seq 1, length 16088
15:44:06.386175 52:54:00:12:34:56 (oui Unknown) > 16:d2:42:8d:bf:a3 (oui Unknown), ethertype IPv4 (0x0800), length 54: 192.168.58.89 > amosk.info: icmp
Comment 8 Amos Kong 2013-11-27 03:06:27 EST
1) C:\>netsh interface ipv4 set subinterface "Local Area Connection 3" mtu=16110
   (disable & enable is not needed)
2) ifconfig tap0 mtu 16110
3) arp -s 192.168.58.89 52:54:00:12:34:56 -i tap0
4) ping 192.168.58.89  -I tap0 -c 1 -s 16000 -M do

ping failed.  This test also changes the mtu of tap0 to 16110.
The size of request packet is 16008, it means guest can't process the Jumbo packet in RX.  

# tcpdump -i tap0 -e

15:55:44.326146 16:d2:42:8d:bf:a3 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 16042: amosk.info > 192.168.58.89: ICMP echo request, id 10056, seq 1, length 16008
Comment 9 Amos Kong 2013-11-27 03:19:19 EST
Btw, I can set the max MTU of e1000 to more than 16110.
I found the max MTU of e1000 in Win7 is 4,294,967,295
This is the driver implementation difference between linux & windows, not a problem. 

The max MTU of tap0 is 65521.

Maybe we can set the MTU of tap0 and e1000 (in guest) to 65521 for Jumbo testing (only windows).
Comment 10 Amos Kong 2013-11-27 03:29:14 EST
Cong,

Can you test with real hardware (e1000: 82540EM)?

1. found a win7 host, which has e1000 nic
2. found a linux host with e1000 nic
3. connect two compute back-to-back (To avoid that the packet's split by switch)
4. try to ping win7 host from linux host with default mtu (1500)

5. set e1000 mtu to 16110 in Linux(eth0) and Window7 (Local Are Connection ..)
6. add arp entry in linux os
7. ping win7 host from linux host

If the ping failed, try to using tcpdump/wireshark to capture the ICMP packet, it can help to know the fault point.

Thanks, Amos
Comment 11 Amos Kong 2013-11-27 05:49:21 EST
Currently QEMU will drop the packet if SBP is not set && LPE is not set && size > vlan_size 1522.

qemu: hw/net/e1000.c: e1000_receive_iov() {

    ....

    /* Discard oversized packets if !LPE and !SBP. */
    if ((size > MAXIMUM_ETHERNET_LPE_SIZE ||
        (size > MAXIMUM_ETHERNET_VLAN_SIZE
        && !(s->mac_reg[RCTL] & E1000_RCTL_LPE)))
        && !(s->mac_reg[RCTL] & E1000_RCTL_SBP)) {
        return size;
    }
    ....
}

In linux we clearly set the LPE to 1, when the MTU is larger than 1500.
So the Jumbo testing passes with Linux guest.

linux: drivers/net/ethernet/intel/e1000/e1000_main.c:
static void e1000_setup_rctl(struct e1000_adapter *adapter)
{
        ....

        if (adapter->netdev->mtu <= ETH_DATA_LEN)
                rctl &= ~E1000_RCTL_LPE;
        else
                rctl |= E1000_RCTL_LPE;

    ....
}


I will check the e1000 specification to know why Windows doesn't set the LPE.

============
* linux, change mtu more than 1500:
e1000: RCTL: 13, mac_reg[RCTL] = 0x8000
e1000: RCTL: 13, mac_reg[RCTL] = 0x0
e1000: RCTL: 0, mac_reg[RCTL] = 0x0
e1000: RCTL: 0, mac_reg[RCTL] = 0x8020   <------------ 0x20 bit is set
e1000: RCTL: 0, mac_reg[RCTL] = 0x8020
e1000: RCTL: 0, mac_reg[RCTL] = 0x8022

* linux, change mtu <= 1500:
e1000: RCTL: 32, mac_reg[RCTL] = 0x8000
e1000: RCTL: 32, mac_reg[RCTL] = 0x0
e1000: RCTL: 0, mac_reg[RCTL] = 0x0
e1000: RCTL: 0, mac_reg[RCTL] = 0x8000  <-----------0x20 bit is not set
e1000: RCTL: 0, mac_reg[RCTL] = 0x8000
e1000: RCTL: 0, mac_reg[RCTL] = 0x8002

* windows: change mtu to any value:
Receive ctrl (RCTL) register is not changed, no debug message
Comment 12 Amos Kong 2013-11-27 06:38:41 EST
Created attachment 829645 [details]
enable e1000 jumbo-packet option in win7

(In reply to Amos Kong from comment #11)
>
...
> * windows: change mtu to any value:
> Receive ctrl (RCTL) register is not changed, no debug message

In e1000 driver of Windows, there is a "Jumbo Packet" option, it's
used to enable LPE, after enabled Jumbo packet, I can ping guest with
large packet (>1500)

So it's not a bug, the testcase should update.
  "enable jumbo-packet option (16128 bytes) for windows e1000 nic"
Comment 13 Amos Kong 2013-11-27 06:40:31 EST
close this bug as NOTABUG according comment #12
Comment 14 CongLi 2013-11-27 21:26:27 EST
(In reply to Amos Kong from comment #12)
> Created attachment 829645 [details]
> enable e1000 jumbo-packet option in win7
> 
> (In reply to Amos Kong from comment #11)
> >
> ...
> > * windows: change mtu to any value:
> > Receive ctrl (RCTL) register is not changed, no debug message
> 
> In e1000 driver of Windows, there is a "Jumbo Packet" option, it's
> used to enable LPE, after enabled Jumbo packet, I can ping guest with
> large packet (>1500)
>
> So it's not a bug, the testcase should update.
>   "enable jumbo-packet option (16128 bytes) for windows e1000 nic"

Hi akong,

1. After changing mtu=16128 via 'Jumbo Packet'in guest, can ping 16000, but can't ping 16100 (16128-28).

1) jumbo=16000:
# ping 10.66.107.198 -c 1 -I tap0 -s 16000 -M do
ping: Warning: source address might be selected on device other than tap0.
PING 10.66.107.198 (10.66.107.198) from 10.66.106.30 tap0: 16000(16028) bytes of data.
16008 bytes from 10.66.107.198: icmp_seq=1 ttl=128 time=0.506 ms

--- 10.66.107.198 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 0ms
rtt min/avg/max/mdev = 0.506/0.506/0.506/0.000 ms

2) jumbo=16100:
# ping 10.66.107.198 -c 1 -I tap0 -s 16100 -M do
ping: Warning: source address might be selected on device other than tap0.
PING 10.66.107.198 (10.66.107.198) from 10.66.106.30 tap0: 16100(16128) bytes of data.
^C
--- 10.66.107.198 ping statistics ---
1 packets transmitted, 0 received, 100% packet loss, time 0ms


2. Can't ping a small packet after ping a jumbo=16100.

# ping 10.66.107.198 -c 1 -I tap0 -s 16100 -M do
ping: Warning: source address might be selected on device other than tap0.
PING 10.66.107.198 (10.66.107.198) from 10.66.106.30 tap0: 16100(16128) bytes of data.
^C
--- 10.66.107.198 ping statistics ---
1 packets transmitted, 0 received, 100% packet loss, time 0ms

# ping 10.66.107.198 -c 1 -I tap0 -s 100 -M do
ping: Warning: source address might be selected on device other than tap0.
PING 10.66.107.198 (10.66.107.198) from 10.66.106.30 tap0: 100(128) bytes of data.
^C
--- 10.66.107.198 ping statistics ---
1 packets transmitted, 0 received, 100% packet loss, time 0ms

3. After step2, disable & enable e1000 driver in guest, can ping a small packet.
Comment 15 Amos Kong 2013-11-27 22:32:21 EST
When I set the Jumbo-Packet parameter to 16128, I tried to ping with 16085 size.     (16086 will failed)
And I captured a ICMP request packet, its size is 16127 with Ethernet header.

It means that Ethernet header is considered during computing Jumbo-Packet limit.


| [root@amosk qemu]# ifconfig tap0 mtu 16200; arp -s 192.168.58.89 52:54:00:12:34:56 -i tap0; ping 192.168.58.89  -I tap0 -c 1 -s 16085 -M do
| ping: Warning: source address might be selected on device other than tap0.
| PING 192.168.58.89 (192.168.58.89) from 101.168.0.108 tap0: 16085(16113) bytes of data.
| 16093 bytes from 192.168.58.89: icmp_seq=1 ttl=128 time=0.571 ms
|
| --- 192.168.58.89 ping statistics ---
| 1 packets transmitted, 1 received, 0% packet loss, time 0ms
| rtt min/avg/max/mdev = 0.571/0.571/0.571/0.000 ms

| 11:26:50.042047 02:b4:ce:b2:52:e8 (oui Unknown) > 52:54:00:12:34:56 (oui Unknown), ethertype IPv4 (0x0800), length 16127: amosk.info > 192.168.58.89: ICMP echo request, id 4598, seq 1, length 16093
| 11:26:50.042298 52:54:00:12:34:56 (oui Unknown) > 02:b4:ce:b2:52:e8 (oui Unknown), ethertype IPv4 (0x0800), length 16122: 192.168.58.89 > amosk.info: ICMP echo reply, id 4598, seq 1, length 16088
| 11:26:50.042335 52:54:00:12:34:56 (oui Unknown) > 02:b4:ce:b2:52:e8 (oui Unknown), ethertype IPv4 (0x0800), length 39: 192.168.58.89 > amosk.info: icmp
|

Note You need to log in before you can comment on or make changes to this bug.