summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorhathach <[email protected]>2013-03-13 12:25:27 +0700
committerhathach <[email protected]>2013-03-13 12:25:27 +0700
commit1a932e7437309637cbd1d2b83b0478d601341661 (patch)
tree1daa54baa620b24aed99ead18999510a0c3f29cf
parent97c436a16ee6de7852c5cb77fa4359a5f00f4c46 (diff)
refractor ehci test files
adding some code for async_advance_isr add test for async_advance_isr
-rw-r--r--tests/test/host/ehci/test_ehci.h71
-rw-r--r--tests/test/host/ehci/test_ehci_init.c5
-rw-r--r--tests/test/host/ehci/test_ehci_isr.c43
-rw-r--r--tests/test/host/ehci/test_ehci_pipe_bulk_xfer.c5
-rw-r--r--tests/test/host/ehci/test_ehci_pipe_open.c6
-rw-r--r--tests/test/host/ehci/test_ehci_pipe_xfer_control.c5
-rw-r--r--tests/test/host/ehci/test_ehci_structure.c5
-rw-r--r--tests/test/support/ehci_controller.c4
-rw-r--r--tests/test/support/ehci_controller.h7
-rw-r--r--tinyusb/host/ehci/ehci.c34
10 files changed, 74 insertions, 111 deletions
diff --git a/tests/test/host/ehci/test_ehci.h b/tests/test/host/ehci/test_ehci.h
deleted file mode 100644
index d6801de69..000000000
--- a/tests/test/host/ehci/test_ehci.h
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * test_ehci.h
- *
- * Created on: Mar 5, 2013
- * Author: hathach
- */
-
-/*
- * Software License Agreement (BSD License)
- * Copyright (c) 2012, hathach (tinyusb.net)
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without modification,
- * are permitted provided that the following conditions are met:
- *
- * 1. Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
- * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
- * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
- * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
- * OF SUCH DAMAGE.
- *
- * This file is part of the tiny usb stack.
- */
-
-/** \file
- * \brief TBD
- *
- * \note TBD
- */
-
-/** \ingroup TBD
- * \defgroup TBD
- * \brief TBD
- *
- * @{
- */
-
-#ifndef _TUSB_TEST_EHCI_H_
-#define _TUSB_TEST_EHCI_H_
-
-#ifdef __cplusplus
- extern "C" {
-#endif
-
-#include <stdlib.h>
-
-ehci_registers_t* const get_operational_register(uint8_t hostid);
-ehci_link_t* const get_period_frame_list(uint8_t list_idx);
-ehci_qhd_t* const get_async_head(uint8_t hostid);
-ehci_qhd_t* const get_period_head(uint8_t hostid);
-
-#ifdef __cplusplus
- }
-#endif
-
-#endif /* _TUSB_TEST_EHCI_H_ */
-
-/** @} */
diff --git a/tests/test/host/ehci/test_ehci_init.c b/tests/test/host/ehci/test_ehci_init.c
index 4a6088cff..487df4678 100644
--- a/tests/test/host/ehci/test_ehci_init.c
+++ b/tests/test/host/ehci/test_ehci_init.c
@@ -45,13 +45,10 @@
#include "hcd.h"
#include "mock_usbh_hcd.h"
#include "ehci.h"
+#include "ehci_controller.h"
-extern ehci_data_t ehci_data;
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
//--------------------------------------------------------------------+
// Setup/Teardown + helper declare
//--------------------------------------------------------------------+
diff --git a/tests/test/host/ehci/test_ehci_isr.c b/tests/test/host/ehci/test_ehci_isr.c
index 95cbbcb5b..f6b9a09e5 100644
--- a/tests/test/host/ehci/test_ehci_isr.c
+++ b/tests/test/host/ehci/test_ehci_isr.c
@@ -47,9 +47,6 @@
#include "ehci.h"
#include "ehci_controller.h"
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
uint8_t hostid;
@@ -106,4 +103,44 @@ void test_isr_device_disconnect(void)
//------------- Code Under Test -------------//
hcd_isr(hostid);
+ ehci_registers_t * const regs = get_operational_register(hostid);
+ TEST_ASSERT(regs->usb_cmd_bit.advacne_async);
+}
+
+void test_isr_disconnect_then_async_advance(void)
+{
+ uint8_t dev_addr = 1;
+ uint8_t hostid = 0;
+ ehci_registers_t * const regs = get_operational_register(hostid);
+
+// usbh_device_info_pool[dev_addr].status = TUSB_DEVICE_STATUS_READY;
+ usbh_device_info_pool[dev_addr].core_id = hostid;
+ usbh_device_info_pool[dev_addr].hub_addr = 0;
+ usbh_device_info_pool[dev_addr].hub_port = 0;
+
+ hcd_pipe_control_open(dev_addr, 64);
+ hcd_pipe_control_xfer(dev_addr,
+ &(tusb_std_request_t) {
+ .bmRequestType = { .direction = TUSB_DIR_HOST_TO_DEV, .type = TUSB_REQUEST_TYPE_STANDARD, .recipient = TUSB_REQUEST_RECIPIENT_DEVICE },
+ .bRequest = TUSB_REQUEST_SET_ADDRESS,
+ .wValue = 3 },
+ NULL);
+
+ ehci_qhd_t *p_qhd = &ehci_data.device[dev_addr].control.qhd;
+ ehci_qtd_t *p_qtd_head = p_qhd->p_qtd_list_head;
+ ehci_qtd_t *p_qtd_tail = p_qhd->p_qtd_list_tail;
+
+ ehci_controller_device_unplug(hostid);
+ usbh_device_unplugged_isr_Expect(hostid);
+
+ //------------- Code Under Test -------------//
+ hcd_isr(hostid); // port change detect
+ regs->usb_sts_bit.port_change_detect = 0; // clear port change detect
+ hcd_isr(hostid); // async advance
+
+ TEST_ASSERT( align32(get_async_head(hostid)->next.address) != (uint32_t) p_qhd );
+ TEST_ASSERT_FALSE(p_qhd->used);
+ TEST_ASSERT_FALSE(p_qtd_head->used);
+ TEST_ASSERT_FALSE(p_qtd_tail->used);
+
}
diff --git a/tests/test/host/ehci/test_ehci_pipe_bulk_xfer.c b/tests/test/host/ehci/test_ehci_pipe_bulk_xfer.c
index 97c9e88fd..1f6221abf 100644
--- a/tests/test/host/ehci/test_ehci_pipe_bulk_xfer.c
+++ b/tests/test/host/ehci/test_ehci_pipe_bulk_xfer.c
@@ -45,15 +45,10 @@
#include "hcd.h"
#include "mock_usbh_hcd.h"
#include "ehci.h"
-#include "test_ehci.h"
#include "ehci_controller.h"
-extern ehci_data_t ehci_data;
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
uint8_t const control_max_packet_size = 64;
uint8_t const hub_addr = 2;
uint8_t const hub_port = 2;
diff --git a/tests/test/host/ehci/test_ehci_pipe_open.c b/tests/test/host/ehci/test_ehci_pipe_open.c
index 9e928d9fb..bea3709f3 100644
--- a/tests/test/host/ehci/test_ehci_pipe_open.c
+++ b/tests/test/host/ehci/test_ehci_pipe_open.c
@@ -45,14 +45,10 @@
#include "hcd.h"
#include "mock_usbh_hcd.h"
#include "ehci.h"
-#include "test_ehci.h"
+#include "ehci_controller.h"
-extern ehci_data_t ehci_data;
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
uint8_t const control_max_packet_size = 64;
uint8_t const hub_addr = 2;
uint8_t const hub_port = 2;
diff --git a/tests/test/host/ehci/test_ehci_pipe_xfer_control.c b/tests/test/host/ehci/test_ehci_pipe_xfer_control.c
index 2c54d95cd..b264994f4 100644
--- a/tests/test/host/ehci/test_ehci_pipe_xfer_control.c
+++ b/tests/test/host/ehci/test_ehci_pipe_xfer_control.c
@@ -45,15 +45,10 @@
#include "hcd.h"
#include "mock_usbh_hcd.h"
#include "ehci.h"
-#include "test_ehci.h"
#include "ehci_controller.h"
-extern ehci_data_t ehci_data;
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
uint8_t const control_max_packet_size = 64;
uint8_t const hub_addr = 2;
uint8_t const hub_port = 2;
diff --git a/tests/test/host/ehci/test_ehci_structure.c b/tests/test/host/ehci/test_ehci_structure.c
index 5b07f2720..88f56b688 100644
--- a/tests/test/host/ehci/test_ehci_structure.c
+++ b/tests/test/host/ehci/test_ehci_structure.c
@@ -45,13 +45,10 @@
#include "hcd.h"
#include "mock_usbh_hcd.h"
#include "ehci.h"
+#include "ehci_controller.h"
-extern ehci_data_t ehci_data;
usbh_device_info_t usbh_device_info_pool[TUSB_CFG_HOST_DEVICE_MAX+1];
-LPC_USB0_Type lpc_usb0;
-LPC_USB1_Type lpc_usb1;
-
//--------------------------------------------------------------------+
// Setup/Teardown + helper declare
//--------------------------------------------------------------------+
diff --git a/tests/test/support/ehci_controller.c b/tests/test/support/ehci_controller.c
index 484348566..4c3ab33ff 100644
--- a/tests/test/support/ehci_controller.c
+++ b/tests/test/support/ehci_controller.c
@@ -48,7 +48,9 @@
//--------------------------------------------------------------------+
// MACRO CONSTANT TYPEDEF
//--------------------------------------------------------------------+
-extern ehci_data_t ehci_data;
+ehci_data_t ehci_data;
+LPC_USB0_Type lpc_usb0;
+LPC_USB1_Type lpc_usb1;
//--------------------------------------------------------------------+
// IMPLEMENTATION
diff --git a/tests/test/support/ehci_controller.h b/tests/test/support/ehci_controller.h
index cb5c69313..7191b1294 100644
--- a/tests/test/support/ehci_controller.h
+++ b/tests/test/support/ehci_controller.h
@@ -55,10 +55,17 @@
extern "C" {
#endif
+extern ehci_data_t ehci_data;
+
void ehci_controller_run(uint8_t hostid);
void ehci_controller_device_plug(uint8_t hostid, tusb_speed_t speed);
void ehci_controller_device_unplug(uint8_t hostid);
+ehci_registers_t* const get_operational_register(uint8_t hostid);
+ehci_link_t* const get_period_frame_list(uint8_t list_idx);
+ehci_qhd_t* const get_async_head(uint8_t hostid);
+ehci_qhd_t* const get_period_head(uint8_t hostid);
+
#ifdef __cplusplus
}
#endif
diff --git a/tinyusb/host/ehci/ehci.c b/tinyusb/host/ehci/ehci.c
index f79b478e6..20750316c 100644
--- a/tinyusb/host/ehci/ehci.c
+++ b/tinyusb/host/ehci/ehci.c
@@ -165,8 +165,17 @@ static inline uint8_t get_qhd_index(ehci_qhd_t * p_qhd)
return p_qhd - ehci_data.device[p_qhd->device_address].qhd;
}
+void async_advance_isr(ehci_qhd_t * const async_head)
+{
+ ehci_qhd_t *p_qhd = async_head;
+ do
+ {
+
+ p_qhd = (ehci_qhd_t*) align32(p_qhd->next.address);
+ }while(p_qhd != async_head); // stop if loop around
+}
-void port_connect_status_isr(uint8_t hostid)
+void port_connect_status_change_isr(uint8_t hostid)
{
ehci_registers_t* const regs = get_operational_register(hostid);
@@ -177,6 +186,8 @@ void port_connect_status_isr(uint8_t hostid)
}else // device unplugged
{
usbh_device_unplugged_isr(hostid);
+
+ regs->usb_cmd_bit.advacne_async = 1; // Async doorbell check EHCI 4.8.2 for operational details
}
}
@@ -186,10 +197,7 @@ void async_list_process_isr(ehci_qhd_t * const async_head, ehci_registers_t * co
ehci_qhd_t *p_qhd = async_head;
do
{
- if ( p_qhd->qtd_overlay.halted )
- {
- // TODO invoke some error callback if not async head
- } else
+ if ( !p_qhd->qtd_overlay.halted )
{
// free all TDs from the head td to the first active TD
while(p_qhd->p_qtd_list_head != NULL && !p_qhd->p_qtd_list_head->active)
@@ -217,7 +225,7 @@ void async_list_process_isr(ehci_qhd_t * const async_head, ehci_registers_t * co
}
}
p_qhd = (ehci_qhd_t*) align32(p_qhd->next.address);
- }while(p_qhd != async_head); // stop if loop around
+ }while(p_qhd != async_head); // async list traversal, stop if loop around
}
//------------- Host Controller Driver's Interrupt Handler -------------//
@@ -232,7 +240,8 @@ void hcd_isr(uint8_t hostid)
if (int_status & EHCI_INT_MASK_ERROR)
{
- // TODO something going wrong
+ // TODO handle Queue Head halted
+ // TODO invoke some error callback if not async head
ASM_BREAKPOINT;
}
@@ -251,7 +260,7 @@ void hcd_isr(uint8_t hostid)
{
if (regs->portsc_bit.connect_status_change)
{
- port_connect_status_isr(hostid);
+ port_connect_status_change_isr(hostid);
}
regs->portsc |= EHCI_PORTSC_MASK_ALL; // Acknowledge all the change bit in portsc
@@ -259,7 +268,7 @@ void hcd_isr(uint8_t hostid)
if (int_status & EHCI_INT_MASK_ASYNC_ADVANCE)
{
-
+ async_advance_isr( get_async_head(hostid) );
}
regs->usb_sts |= regs->usb_sts; // Acknowledge interrupt & clear it
@@ -276,12 +285,11 @@ tusb_error_t hcd_controller_init(uint8_t hostid)
//------------- USB INT Register -------------//
regs->usb_int_enable = 0; // 1. disable all the interrupt
regs->usb_sts = EHCI_INT_MASK_ALL; // 2. clear all status
- regs->usb_int_enable =
- EHCI_INT_MASK_ERROR | EHCI_INT_MASK_PORT_CHANGE
+ regs->usb_int_enable = EHCI_INT_MASK_ERROR | EHCI_INT_MASK_PORT_CHANGE |
#if EHCI_PERIODIC_LIST
- | EHCI_INT_MASK_NXP_PERIODIC
+ EHCI_INT_MASK_NXP_PERIODIC |
#endif
- | EHCI_INT_MASK_ASYNC_ADVANCE | EHCI_INT_MASK_NXP_ASYNC;
+ EHCI_INT_MASK_ASYNC_ADVANCE | EHCI_INT_MASK_NXP_ASYNC;
//------------- Asynchronous List -------------//
ehci_qhd_t * const async_head = get_async_head(hostid);