aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--hw/bt.c26
1 files changed, 17 insertions, 9 deletions
diff --git a/hw/bt.c b/hw/bt.c
index a53ff14..6d559d0 100644
--- a/hw/bt.c
+++ b/hw/bt.c
@@ -165,15 +165,11 @@ static void bt_reset_interface(void)
/* Try and send a message from the message queue. Caller must hold
* bt.bt_lock and bt.lock and ensue the message queue is not
* empty. */
-static void bt_send_msg(void)
+static void bt_send_msg(struct bt_msg *bt_msg)
{
int i;
- struct bt_msg *bt_msg;
struct ipmi_msg *ipmi_msg;
- bt_msg = list_top(&bt.msgq, struct bt_msg, link);
- assert(bt_msg);
-
ipmi_msg = &bt_msg->ipmi_msg;
/* Send the message */
@@ -195,7 +191,6 @@ static void bt_send_msg(void)
for (i = 0; i < ipmi_msg->req_size; i++)
bt_outb(ipmi_msg->data[i], BT_HOST2BMC);
- bt_msg->tb = mftb();
bt_outb(BT_CTRL_H2B_ATN, BT_CTRL);
bt_set_state(BT_STATE_RESP_WAIT);
@@ -346,9 +341,22 @@ static void print_debug_queue_info(void) {}
static void bt_send_and_unlock(void)
{
- if (lpc_ok() && bt_idle() && !list_empty(&bt.msgq)
- && bt.state == BT_STATE_IDLE)
- bt_send_msg();
+ if (lpc_ok() && !list_empty(&bt.msgq)) {
+ struct bt_msg *bt_msg;
+
+ bt_msg = list_top(&bt.msgq, struct bt_msg, link);
+ assert(bt_msg);
+
+ /* Start the message timeout once it gets to the top
+ * of the queue. This will ensure we timeout messages
+ * in the case of a broken bt interface as occurs when
+ * the BMC is not responding to any IPMI messages. */
+ if (bt_msg->tb == 0)
+ bt_msg->tb = mftb();
+
+ if (bt_idle() && bt.state == BT_STATE_IDLE)
+ bt_send_msg(bt_msg);
+ }
unlock(&bt.lock);
return;