Skip to content

Commit

Permalink
NetKVM: BZ#1237024: Fix payload length calculation in IPv6 header
Browse files Browse the repository at this point in the history
This bugfix resolves issues related to TX slow speed of large packets
over IPv6 protocol with enabled Offload.Tx.Checksum option in conjunction with
Offload.Tx.LSO option.

Signed-off-by: Igor Derzhavets <iderzhav@redhat.com>
  • Loading branch information
Igor Derzhavets authored and vrozenfe committed Jul 18, 2015
1 parent 31ef0c9 commit 1ca9a38
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 6 deletions.
22 changes: 17 additions & 5 deletions NetKVM/Common/ParaNdis-TX.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -656,19 +656,31 @@ bool CNB::ScheduleBuildSGListForTx()
NDIS_SG_LIST_WRITE_TO_DEVICE, nullptr, 0) == NDIS_STATUS_SUCCESS;
}

void CNB::PopulateIPLength(IPv4Header *IpHeader, USHORT IpLength) const
void CNB::PopulateIPLength(IPHeader *IpHeader, USHORT IpLength) const
{
if ((IpHeader->ip_verlen & 0xF0) == 0x40)
if ((IpHeader->v4.ip_verlen & 0xF0) == 0x40)
{
if (!IpHeader->ip_length) {
IpHeader->ip_length = swap_short(IpLength);
if (!IpHeader->v4.ip_length)
{
IpHeader->v4.ip_length = swap_short(IpLength);
}
}
else if ((IpHeader->v6.ip6_ver_tc & 0xF0) == 0x60)
{
if (!IpHeader->v6.ip6_payload_len)
{
IpHeader->v6.ip6_payload_len = swap_short(IpLength - IPV6_HEADER_MIN_SIZE);
}
}
else
{
DPrintf(0, ("[%s] ERROR: Bad version of IP header!\n", __FUNCTION__));
}
}

void CNB::SetupLSO(virtio_net_hdr_v1 *VirtioHeader, PVOID IpHeader, ULONG EthPayloadLength) const
{
PopulateIPLength(reinterpret_cast<IPv4Header*>(IpHeader), static_cast<USHORT>(EthPayloadLength));
PopulateIPLength(reinterpret_cast<IPHeader*>(IpHeader), static_cast<USHORT>(EthPayloadLength));

tTcpIpPacketParsingResult packetReview;
packetReview = ParaNdis_CheckSumVerifyFlat(reinterpret_cast<IPv4Header*>(IpHeader), EthPayloadLength,
Expand Down
2 changes: 1 addition & 1 deletion NetKVM/Common/ParaNdis-TX.h
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,7 @@ class CNB : public CNdisAllocatable<CNB, 'BNHR'>
void SetupCSO(virtio_net_hdr_v1 *VirtioHeader, ULONG L4HeaderOffset) const;
bool FillDescriptorSGList(CTXDescriptor &Descriptor, ULONG DataOffset) const;
bool MapDataToVirtioSGL(CTXDescriptor &Descriptor, ULONG Offset) const;
void PopulateIPLength(IPv4Header *IpHeader, USHORT IpLength) const;
void PopulateIPLength(IPHeader *IpHeader, USHORT IpLength) const;

PNET_BUFFER m_NB;
CNBL *m_ParentNBL;
Expand Down
2 changes: 2 additions & 0 deletions NetKVM/Common/ethernetutils.h
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,8 @@ typedef union
IPv4Header v4;
} IPHeader;

#define IPV6_HEADER_MIN_SIZE (sizeof(IPv6Header))

// TCP header RFC 793
typedef struct _tagTCPHeader {
USHORT tcp_src; // Source port
Expand Down

0 comments on commit 1ca9a38

Please sign in to comment.