bugGNU GRUB - Bugs: bug #38111, EFI TFTP packet corruption

 
 

You are not allowed to post comments on this tracker with your current authentification level.

bug #38111: EFI TFTP packet corruption

Submitted by:  Lingzhu Xiang <xlz>
Submitted on:  Fri 18 Jan 2013 04:25:54 AM UTC  
 
Category: NetworkSeverity: Major
Priority: 5 - NormalItem Group: Software Error
Status: FixedPrivacy: Public
Assigned to: NoneOriginator Name: 
Open/Closed: ClosedRelease: 
Release: otherReproducibility: Every Time
Planned Release: None

Thu 07 Mar 2013 01:54:41 PM UTC, comment #1:

Hi

I confirm the issue. On a custom UEFI firmware based on UDK2010.SR1 (or EDKII head), UEFI PXE boot fails with grub2 (release and latest version).

If I enable only the IPv4 stack in the firmware and the old PXE BC driver, it works most of the time. I sometime have "Not an IP" or "couldn't send packet" when I download a linux kernel...

If I enable both IPv4 and IPv6, and the new PXE BC code, it doesn't work. As Lingzhu Xiang explained, the IPv6 stack sends icmpv6 messages which gets into a race condition. This can easily be observed with wireshark. An incoming icmpv6 message during a file transfer will stall it.

For your information, the problem doesn't occur with Elilo. Elilo uses MTFP protocol and it always works.

Regards,
Thomas

Thomas Jourdan <tjourdan>
Fri 18 Jan 2013 04:25:54 AM UTC, original submission:

UEFI PXE boot fails and falls back to command line.

Packet capture shows it successfully loaded grub.cfg and a few files. Then it sends two malformed packets of 60 zero bytes and no more packets are sent. There are icmpv6 messages like router solicitation and listener report.

Version: Fedora's grub2-efi-2.00-15.fc18 based on grub-2.00.

Reproduced on Dell XPS 8500 (Firmware: EFI v2.31, likely a EDK2 mod), capable of IPv4/6 PXE.

Adding random link delay between the booting machine and tftp server with netem won't change the number and order of malformed packets. Malformed packets are sent after certain tftp requests in a deterministic manner.

I added a printf in net/drivers/efi/efinet.c:

static grub_err_t
send_card_buffer (struct grub_net_card *dev,
struct grub_net_buff *pack)
{
...
if (dev->txbusy)
while (1)
{
void *txbuf = NULL;
st = efi_call_3 (net->get_status, net, 0, &txbuf);
if (st != GRUB_EFI_SUCCESS)
return grub_error (GRUB_ERR_IO,
N_("couldn't send network packet"));
if (txbuf == dev->txbuf)
{
dev->txbusy = 0;
break;
}
if (txbuf)
grub_printf("not my txbuf: txbuf=%p dev->txbuf=%p\n", txbuf, dev->txbuf);
if (limit_time < grub_get_time_ms ())
return grub_error (GRUB_ERR_TIMEOUT, N_("couldn't send network packet"));
}

I got "not my txbuf: txbuf=0xd237a698 dev->txbuf=0xce9b6160" before falling back into command line. I hasn't seen txbuf value other than 0xd237a698, but dev->txbuf sometimes changes.

My guess is that the firmware's ipv6 stack sending icmpv6 messages gets into a race condition with GetStatus by grub's efinet. GetStatus in SNP will remove the returned txbuf from the "transmitted buffer queue" and indicate the txbuf has finished transmission. The "not my txbuf" message probably shows grub stole the txbuf of an icmpv6 router solicitation and couldn't get its own txbuf any more. Hence the network stalls.

Grub's efinet uses SNP which only allows exclusive access for one application while the firmware's (EDK2) IPv6 stack uses MNP which is an abstraction over SNP to allow concurrent operation. This looks quite problematic.

Lingzhu Xiang <xlz>

 

No files currently attached

 

Depends on the following items: None found

Items that depend on this one: None found

 

Carbon-Copy List
  • -unavailable- added by phcoder (Updated the item)
  • -unavailable- added by tjourdan (Posted a comment)
  • -unavailable- added by xlz (Submitted the item)
  •  

    Do you think this task is very important?
    If so, you can click here to add your encouragement to it.
    This task has 0 encouragements so far.

    Only logged-in users can vote.

     

    Please enter the title of George Orwell's famous dystopian book (it's a date):

     

     

    Follow 2 latest changes.

    Date Changed By Updated Field Previous Value => Replaced By
    Sun 17 Mar 2013 12:37:20 PM UTCphcoderStatusNone=>Fixed
      Open/ClosedOpen=>Closed

    Back to the top


    Powered by Savane 3.1-cleanup