Openembedded Core Discussions
 help / color / mirror / Atom feed
From: Richard Purdie <richard.purdie@linuxfoundation.org>
To: openembedded-core <openembedded-core@lists.openembedded.org>
Subject: [PATCH] qemu: Add fixes for smc91c11 qemu segfaults on arm
Date: Mon, 07 Sep 2015 15:35:49 +0100	[thread overview]
Message-ID: <1441636549.24871.251.camel@linuxfoundation.org> (raw)

The smc91c111.c driver appears to have several issues. The can_receive()
function can return that the driver is ready when rx_fifo has not been 
freed yet. There is also no sanity check of rx_fifo() in _receive() which
can lead to corruption of the rx_fifo array.

release_packet() can also call qemu_flush_queued_packets() before rx_fifo 
has been cleaned up, resulting in cases where packets are submitted
for which there is not yet any space.

This patch therefore:

* fixes the logic in can_receive()
* adds logic to receive() as a sanity check
* moves the flush() calls to the correct places where data is ready
  to be received

Its currently undergoing discussion upstream about exactly which pieces
are the correct fix but for now, this stops the segfaults OE is seeing
which has to be an improvement.

[YOCTO #8234]

Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>

diff --git a/meta/recipes-devtools/qemu/qemu/smc91c111_fix.patch b/meta/recipes-devtools/qemu/qemu/smc91c111_fix.patch
new file mode 100644
index 0000000..e69af94
--- /dev/null
+++ b/meta/recipes-devtools/qemu/qemu/smc91c111_fix.patch
@@ -0,0 +1,77 @@
+The smc91c111.c driver appears to have several issues. The can_receive()
+function can return that the driver is ready when rx_fifo has not been 
+freed yet. There is also no sanity check of rx_fifo() in _receive() which
+can lead to corruption of the rx_fifo array.
+
+release_packet() can also call qemu_flush_queued_packets() before rx_fifo 
+has been cleaned up, resulting in cases where packets are submitted
+for which there is not yet any space.
+
+This patch therefore:
+
+* fixes the logic in can_receive()
+* adds logic to receive() as a sanity check
+* moves the flush() calls to the correct places where data is ready
+  to be received
+
+Upstream-Status: Pending [discussion in progress on mailing list]
+RP 2015/9/7
+
+Index: qemu-2.4.0/hw/net/smc91c111.c
+===================================================================
+--- qemu-2.4.0.orig/hw/net/smc91c111.c
++++ qemu-2.4.0/hw/net/smc91c111.c
+@@ -185,7 +185,6 @@ static void smc91c111_release_packet(smc
+     s->allocated &= ~(1 << packet);
+     if (s->tx_alloc == 0x80)
+         smc91c111_tx_alloc(s);
+-    qemu_flush_queued_packets(qemu_get_queue(s->nic));
+ }
+ 
+ /* Flush the TX FIFO.  */
+@@ -237,9 +236,11 @@ static void smc91c111_do_tx(smc91c111_st
+             }
+         }
+ #endif
+-        if (s->ctr & CTR_AUTO_RELEASE)
++        if (s->ctr & CTR_AUTO_RELEASE) {
+             /* Race?  */
+             smc91c111_release_packet(s, packetnum);
++            qemu_flush_queued_packets(qemu_get_queue(s->nic));
++        }
+         else if (s->tx_fifo_done_len < NUM_PACKETS)
+             s->tx_fifo_done[s->tx_fifo_done_len++] = packetnum;
+         qemu_send_packet(qemu_get_queue(s->nic), p, len);
+@@ -379,9 +380,11 @@ static void smc91c111_writeb(void *opaqu
+                     smc91c111_release_packet(s, s->rx_fifo[0]);
+                 }
+                 smc91c111_pop_rx_fifo(s);
++                qemu_flush_queued_packets(qemu_get_queue(s->nic));
+                 break;
+             case 5: /* Release.  */
+                 smc91c111_release_packet(s, s->packet_num);
++                qemu_flush_queued_packets(qemu_get_queue(s->nic));
+                 break;
+             case 6: /* Add to TX FIFO.  */
+                 smc91c111_queue_tx(s, s->packet_num);
+@@ -642,7 +642,7 @@ static int smc91c111_can_receive(NetClie
+ 
+     if ((s->rcr & RCR_RXEN) == 0 || (s->rcr & RCR_SOFT_RST))
+         return 1;
+-    if (s->allocated == (1 << NUM_PACKETS) - 1)
++    if ((s->allocated == (1 << NUM_PACKETS) - 1) || (s->rx_fifo_len == NUM_PACKETS))
+         return 0;
+     return 1;
+ }
+@@ -671,9 +671,11 @@ static ssize_t smc91c111_receive(NetClie
+     /* TODO: Flag overrun and receive errors.  */
+     if (packetsize > 2048)
+         return -1;
++    if  (s->rx_fifo_len == NUM_PACKETS)
++        return -1;    
+     packetnum = smc91c111_allocate_packet(s);
+     if (packetnum == 0x80)
+         return -1;
+     s->rx_fifo[s->rx_fifo_len++] = packetnum;
+ 
+     p = &s->data[packetnum][0];
diff --git a/meta/recipes-devtools/qemu/qemu_2.4.0.bb b/meta/recipes-devtools/qemu/qemu_2.4.0.bb
index 5e5f786..d545b60 100644
--- a/meta/recipes-devtools/qemu/qemu_2.4.0.bb
+++ b/meta/recipes-devtools/qemu/qemu_2.4.0.bb
@@ -6,6 +6,7 @@ LIC_FILES_CHKSUM = "file://COPYING;md5=441c28d2cf86e15a37fa47e15a72fbac \
 SRC_URI += "file://configure-fix-Darwin-target-detection.patch \
             file://qemu-enlarge-env-entry-size.patch \
             file://Qemu-Arm-versatilepb-Add-memory-size-checking.patch \
+            file://smc91c111_fix.patch \
            "
 SRC_URI_prepend = "http://wiki.qemu-project.org/download/${BP}.tar.bz2"
 SRC_URI[md5sum] = "186ee8194140a484a455f8e3c74589f4"




                 reply	other threads:[~2015-09-07 14:36 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1441636549.24871.251.camel@linuxfoundation.org \
    --to=richard.purdie@linuxfoundation.org \
    --cc=openembedded-core@lists.openembedded.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox