mirror of
https://github.com/OneOfEleven/uv-k5-firmware-custom.git
synced 2025-06-20 06:58:39 +03:00
Initial commit
This commit is contained in:
1816
external/CMSIS_5/CMSIS/DAP/Firmware/Source/DAP.c
vendored
Normal file
1816
external/CMSIS_5/CMSIS/DAP/Firmware/Source/DAP.c
vendored
Normal file
File diff suppressed because it is too large
Load Diff
100
external/CMSIS_5/CMSIS/DAP/Firmware/Source/DAP_vendor.c
vendored
Normal file
100
external/CMSIS_5/CMSIS/DAP/Firmware/Source/DAP_vendor.c
vendored
Normal file
@ -0,0 +1,100 @@
|
||||
/*
|
||||
* Copyright (c) 2013-2017 ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the License); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ----------------------------------------------------------------------
|
||||
*
|
||||
* $Date: 1. December 2017
|
||||
* $Revision: V2.0.0
|
||||
*
|
||||
* Project: CMSIS-DAP Source
|
||||
* Title: DAP_vendor.c CMSIS-DAP Vendor Commands
|
||||
*
|
||||
*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "DAP_config.h"
|
||||
#include "DAP.h"
|
||||
|
||||
//**************************************************************************************************
|
||||
/**
|
||||
\defgroup DAP_Vendor_Adapt_gr Adapt Vendor Commands
|
||||
\ingroup DAP_Vendor_gr
|
||||
@{
|
||||
|
||||
The file DAP_vendor.c provides template source code for extension of a Debug Unit with
|
||||
Vendor Commands. Copy this file to the project folder of the Debug Unit and add the
|
||||
file to the MDK-ARM project under the file group Configuration.
|
||||
*/
|
||||
|
||||
/** Process DAP Vendor Command and prepare Response Data
|
||||
\param request pointer to request data
|
||||
\param response pointer to response data
|
||||
\return number of bytes in response (lower 16 bits)
|
||||
number of bytes in request (upper 16 bits)
|
||||
*/
|
||||
uint32_t DAP_ProcessVendorCommand(const uint8_t *request, uint8_t *response) {
|
||||
uint32_t num = (1U << 16) | 1U;
|
||||
|
||||
*response++ = *request; // copy Command ID
|
||||
|
||||
switch (*request++) { // first byte in request is Command ID
|
||||
case ID_DAP_Vendor0:
|
||||
#if 0 // example user command
|
||||
num += 1U << 16; // increment request count
|
||||
if (*request == 1U) { // when first command data byte is 1
|
||||
*response++ = 'X'; // send 'X' as response
|
||||
num++; // increment response count
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
|
||||
case ID_DAP_Vendor1: break;
|
||||
case ID_DAP_Vendor2: break;
|
||||
case ID_DAP_Vendor3: break;
|
||||
case ID_DAP_Vendor4: break;
|
||||
case ID_DAP_Vendor5: break;
|
||||
case ID_DAP_Vendor6: break;
|
||||
case ID_DAP_Vendor7: break;
|
||||
case ID_DAP_Vendor8: break;
|
||||
case ID_DAP_Vendor9: break;
|
||||
case ID_DAP_Vendor10: break;
|
||||
case ID_DAP_Vendor11: break;
|
||||
case ID_DAP_Vendor12: break;
|
||||
case ID_DAP_Vendor13: break;
|
||||
case ID_DAP_Vendor14: break;
|
||||
case ID_DAP_Vendor15: break;
|
||||
case ID_DAP_Vendor16: break;
|
||||
case ID_DAP_Vendor17: break;
|
||||
case ID_DAP_Vendor18: break;
|
||||
case ID_DAP_Vendor19: break;
|
||||
case ID_DAP_Vendor20: break;
|
||||
case ID_DAP_Vendor21: break;
|
||||
case ID_DAP_Vendor22: break;
|
||||
case ID_DAP_Vendor23: break;
|
||||
case ID_DAP_Vendor24: break;
|
||||
case ID_DAP_Vendor25: break;
|
||||
case ID_DAP_Vendor26: break;
|
||||
case ID_DAP_Vendor27: break;
|
||||
case ID_DAP_Vendor28: break;
|
||||
case ID_DAP_Vendor29: break;
|
||||
case ID_DAP_Vendor30: break;
|
||||
case ID_DAP_Vendor31: break;
|
||||
}
|
||||
|
||||
return (num);
|
||||
}
|
||||
|
||||
///@}
|
370
external/CMSIS_5/CMSIS/DAP/Firmware/Source/JTAG_DP.c
vendored
Normal file
370
external/CMSIS_5/CMSIS/DAP/Firmware/Source/JTAG_DP.c
vendored
Normal file
@ -0,0 +1,370 @@
|
||||
/*
|
||||
* Copyright (c) 2013-2017 ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the License); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ----------------------------------------------------------------------
|
||||
*
|
||||
* $Date: 1. December 2017
|
||||
* $Revision: V2.0.0
|
||||
*
|
||||
* Project: CMSIS-DAP Source
|
||||
* Title: JTAG_DP.c CMSIS-DAP JTAG DP I/O
|
||||
*
|
||||
*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "DAP_config.h"
|
||||
#include "DAP.h"
|
||||
|
||||
|
||||
// JTAG Macros
|
||||
|
||||
#define PIN_TCK_SET PIN_SWCLK_TCK_SET
|
||||
#define PIN_TCK_CLR PIN_SWCLK_TCK_CLR
|
||||
#define PIN_TMS_SET PIN_SWDIO_TMS_SET
|
||||
#define PIN_TMS_CLR PIN_SWDIO_TMS_CLR
|
||||
|
||||
#define JTAG_CYCLE_TCK() \
|
||||
PIN_TCK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
PIN_TCK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define JTAG_CYCLE_TDI(tdi) \
|
||||
PIN_TDI_OUT(tdi); \
|
||||
PIN_TCK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
PIN_TCK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define JTAG_CYCLE_TDO(tdo) \
|
||||
PIN_TCK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
tdo = PIN_TDO_IN(); \
|
||||
PIN_TCK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define JTAG_CYCLE_TDIO(tdi,tdo) \
|
||||
PIN_TDI_OUT(tdi); \
|
||||
PIN_TCK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
tdo = PIN_TDO_IN(); \
|
||||
PIN_TCK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define PIN_DELAY() PIN_DELAY_SLOW(DAP_Data.clock_delay)
|
||||
|
||||
|
||||
#if (DAP_JTAG != 0)
|
||||
|
||||
|
||||
// Generate JTAG Sequence
|
||||
// info: sequence information
|
||||
// tdi: pointer to TDI generated data
|
||||
// tdo: pointer to TDO captured data
|
||||
// return: none
|
||||
void JTAG_Sequence (uint32_t info, const uint8_t *tdi, uint8_t *tdo) {
|
||||
uint32_t i_val;
|
||||
uint32_t o_val;
|
||||
uint32_t bit;
|
||||
uint32_t n, k;
|
||||
|
||||
n = info & JTAG_SEQUENCE_TCK;
|
||||
if (n == 0U) {
|
||||
n = 64U;
|
||||
}
|
||||
|
||||
if (info & JTAG_SEQUENCE_TMS) {
|
||||
PIN_TMS_SET();
|
||||
} else {
|
||||
PIN_TMS_CLR();
|
||||
}
|
||||
|
||||
while (n) {
|
||||
i_val = *tdi++;
|
||||
o_val = 0U;
|
||||
for (k = 8U; k && n; k--, n--) {
|
||||
JTAG_CYCLE_TDIO(i_val, bit);
|
||||
i_val >>= 1;
|
||||
o_val >>= 1;
|
||||
o_val |= bit << 7;
|
||||
}
|
||||
o_val >>= k;
|
||||
if (info & JTAG_SEQUENCE_TDO) {
|
||||
*tdo++ = (uint8_t)o_val;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// JTAG Set IR
|
||||
// ir: IR value
|
||||
// return: none
|
||||
#define JTAG_IR_Function(speed) /**/ \
|
||||
static void JTAG_IR_##speed (uint32_t ir) { \
|
||||
uint32_t n; \
|
||||
\
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Select-DR-Scan */ \
|
||||
JTAG_CYCLE_TCK(); /* Select-IR-Scan */ \
|
||||
PIN_TMS_CLR(); \
|
||||
JTAG_CYCLE_TCK(); /* Capture-IR */ \
|
||||
JTAG_CYCLE_TCK(); /* Shift-IR */ \
|
||||
\
|
||||
PIN_TDI_OUT(1U); \
|
||||
for (n = DAP_Data.jtag_dev.ir_before[DAP_Data.jtag_dev.index]; n; n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Bypass before data */ \
|
||||
} \
|
||||
for (n = DAP_Data.jtag_dev.ir_length[DAP_Data.jtag_dev.index] - 1U; n; n--) { \
|
||||
JTAG_CYCLE_TDI(ir); /* Set IR bits (except last) */ \
|
||||
ir >>= 1; \
|
||||
} \
|
||||
n = DAP_Data.jtag_dev.ir_after[DAP_Data.jtag_dev.index]; \
|
||||
if (n) { \
|
||||
JTAG_CYCLE_TDI(ir); /* Set last IR bit */ \
|
||||
PIN_TDI_OUT(1U); \
|
||||
for (--n; n; n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Bypass after data */ \
|
||||
} \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Bypass & Exit1-IR */ \
|
||||
} else { \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TDI(ir); /* Set last IR bit & Exit1-IR */ \
|
||||
} \
|
||||
\
|
||||
JTAG_CYCLE_TCK(); /* Update-IR */ \
|
||||
PIN_TMS_CLR(); \
|
||||
JTAG_CYCLE_TCK(); /* Idle */ \
|
||||
PIN_TDI_OUT(1U); \
|
||||
}
|
||||
|
||||
|
||||
// JTAG Transfer I/O
|
||||
// request: A[3:2] RnW APnDP
|
||||
// data: DATA[31:0]
|
||||
// return: ACK[2:0]
|
||||
#define JTAG_TransferFunction(speed) /**/ \
|
||||
static uint8_t JTAG_Transfer##speed (uint32_t request, uint32_t *data) { \
|
||||
uint32_t ack; \
|
||||
uint32_t bit; \
|
||||
uint32_t val; \
|
||||
uint32_t n; \
|
||||
\
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Select-DR-Scan */ \
|
||||
PIN_TMS_CLR(); \
|
||||
JTAG_CYCLE_TCK(); /* Capture-DR */ \
|
||||
JTAG_CYCLE_TCK(); /* Shift-DR */ \
|
||||
\
|
||||
for (n = DAP_Data.jtag_dev.index; n; n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Bypass before data */ \
|
||||
} \
|
||||
\
|
||||
JTAG_CYCLE_TDIO(request >> 1, bit); /* Set RnW, Get ACK.0 */ \
|
||||
ack = bit << 1; \
|
||||
JTAG_CYCLE_TDIO(request >> 2, bit); /* Set A2, Get ACK.1 */ \
|
||||
ack |= bit << 0; \
|
||||
JTAG_CYCLE_TDIO(request >> 3, bit); /* Set A3, Get ACK.2 */ \
|
||||
ack |= bit << 2; \
|
||||
\
|
||||
if (ack != DAP_TRANSFER_OK) { \
|
||||
/* Exit on error */ \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Exit1-DR */ \
|
||||
goto exit; \
|
||||
} \
|
||||
\
|
||||
if (request & DAP_TRANSFER_RnW) { \
|
||||
/* Read Transfer */ \
|
||||
val = 0U; \
|
||||
for (n = 31U; n; n--) { \
|
||||
JTAG_CYCLE_TDO(bit); /* Get D0..D30 */ \
|
||||
val |= bit << 31; \
|
||||
val >>= 1; \
|
||||
} \
|
||||
n = DAP_Data.jtag_dev.count - DAP_Data.jtag_dev.index - 1U; \
|
||||
if (n) { \
|
||||
JTAG_CYCLE_TDO(bit); /* Get D31 */ \
|
||||
for (--n; n; n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Bypass after data */ \
|
||||
} \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Bypass & Exit1-DR */ \
|
||||
} else { \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TDO(bit); /* Get D31 & Exit1-DR */ \
|
||||
} \
|
||||
val |= bit << 31; \
|
||||
if (data) { *data = val; } \
|
||||
} else { \
|
||||
/* Write Transfer */ \
|
||||
val = *data; \
|
||||
for (n = 31U; n; n--) { \
|
||||
JTAG_CYCLE_TDI(val); /* Set D0..D30 */ \
|
||||
val >>= 1; \
|
||||
} \
|
||||
n = DAP_Data.jtag_dev.count - DAP_Data.jtag_dev.index - 1U; \
|
||||
if (n) { \
|
||||
JTAG_CYCLE_TDI(val); /* Set D31 */ \
|
||||
for (--n; n; n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Bypass after data */ \
|
||||
} \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TCK(); /* Bypass & Exit1-DR */ \
|
||||
} else { \
|
||||
PIN_TMS_SET(); \
|
||||
JTAG_CYCLE_TDI(val); /* Set D31 & Exit1-DR */ \
|
||||
} \
|
||||
} \
|
||||
\
|
||||
exit: \
|
||||
JTAG_CYCLE_TCK(); /* Update-DR */ \
|
||||
PIN_TMS_CLR(); \
|
||||
JTAG_CYCLE_TCK(); /* Idle */ \
|
||||
PIN_TDI_OUT(1U); \
|
||||
\
|
||||
/* Capture Timestamp */ \
|
||||
if (request & DAP_TRANSFER_TIMESTAMP) { \
|
||||
DAP_Data.timestamp = TIMESTAMP_GET(); \
|
||||
} \
|
||||
\
|
||||
/* Idle cycles */ \
|
||||
n = DAP_Data.transfer.idle_cycles; \
|
||||
while (n--) { \
|
||||
JTAG_CYCLE_TCK(); /* Idle */ \
|
||||
} \
|
||||
\
|
||||
return ((uint8_t)ack); \
|
||||
}
|
||||
|
||||
|
||||
#undef PIN_DELAY
|
||||
#define PIN_DELAY() PIN_DELAY_FAST()
|
||||
JTAG_IR_Function(Fast)
|
||||
JTAG_TransferFunction(Fast)
|
||||
|
||||
#undef PIN_DELAY
|
||||
#define PIN_DELAY() PIN_DELAY_SLOW(DAP_Data.clock_delay)
|
||||
JTAG_IR_Function(Slow)
|
||||
JTAG_TransferFunction(Slow)
|
||||
|
||||
|
||||
// JTAG Read IDCODE register
|
||||
// return: value read
|
||||
uint32_t JTAG_ReadIDCode (void) {
|
||||
uint32_t bit;
|
||||
uint32_t val;
|
||||
uint32_t n;
|
||||
|
||||
PIN_TMS_SET();
|
||||
JTAG_CYCLE_TCK(); /* Select-DR-Scan */
|
||||
PIN_TMS_CLR();
|
||||
JTAG_CYCLE_TCK(); /* Capture-DR */
|
||||
JTAG_CYCLE_TCK(); /* Shift-DR */
|
||||
|
||||
for (n = DAP_Data.jtag_dev.index; n; n--) {
|
||||
JTAG_CYCLE_TCK(); /* Bypass before data */
|
||||
}
|
||||
|
||||
val = 0U;
|
||||
for (n = 31U; n; n--) {
|
||||
JTAG_CYCLE_TDO(bit); /* Get D0..D30 */
|
||||
val |= bit << 31;
|
||||
val >>= 1;
|
||||
}
|
||||
PIN_TMS_SET();
|
||||
JTAG_CYCLE_TDO(bit); /* Get D31 & Exit1-DR */
|
||||
val |= bit << 31;
|
||||
|
||||
JTAG_CYCLE_TCK(); /* Update-DR */
|
||||
PIN_TMS_CLR();
|
||||
JTAG_CYCLE_TCK(); /* Idle */
|
||||
|
||||
return (val);
|
||||
}
|
||||
|
||||
|
||||
// JTAG Write ABORT register
|
||||
// data: value to write
|
||||
// return: none
|
||||
void JTAG_WriteAbort (uint32_t data) {
|
||||
uint32_t n;
|
||||
|
||||
PIN_TMS_SET();
|
||||
JTAG_CYCLE_TCK(); /* Select-DR-Scan */
|
||||
PIN_TMS_CLR();
|
||||
JTAG_CYCLE_TCK(); /* Capture-DR */
|
||||
JTAG_CYCLE_TCK(); /* Shift-DR */
|
||||
|
||||
for (n = DAP_Data.jtag_dev.index; n; n--) {
|
||||
JTAG_CYCLE_TCK(); /* Bypass before data */
|
||||
}
|
||||
|
||||
PIN_TDI_OUT(0U);
|
||||
JTAG_CYCLE_TCK(); /* Set RnW=0 (Write) */
|
||||
JTAG_CYCLE_TCK(); /* Set A2=0 */
|
||||
JTAG_CYCLE_TCK(); /* Set A3=0 */
|
||||
|
||||
for (n = 31U; n; n--) {
|
||||
JTAG_CYCLE_TDI(data); /* Set D0..D30 */
|
||||
data >>= 1;
|
||||
}
|
||||
n = DAP_Data.jtag_dev.count - DAP_Data.jtag_dev.index - 1U;
|
||||
if (n) {
|
||||
JTAG_CYCLE_TDI(data); /* Set D31 */
|
||||
for (--n; n; n--) {
|
||||
JTAG_CYCLE_TCK(); /* Bypass after data */
|
||||
}
|
||||
PIN_TMS_SET();
|
||||
JTAG_CYCLE_TCK(); /* Bypass & Exit1-DR */
|
||||
} else {
|
||||
PIN_TMS_SET();
|
||||
JTAG_CYCLE_TDI(data); /* Set D31 & Exit1-DR */
|
||||
}
|
||||
|
||||
JTAG_CYCLE_TCK(); /* Update-DR */
|
||||
PIN_TMS_CLR();
|
||||
JTAG_CYCLE_TCK(); /* Idle */
|
||||
PIN_TDI_OUT(1U);
|
||||
}
|
||||
|
||||
|
||||
// JTAG Set IR
|
||||
// ir: IR value
|
||||
// return: none
|
||||
void JTAG_IR (uint32_t ir) {
|
||||
if (DAP_Data.fast_clock) {
|
||||
JTAG_IR_Fast(ir);
|
||||
} else {
|
||||
JTAG_IR_Slow(ir);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// JTAG Transfer I/O
|
||||
// request: A[3:2] RnW APnDP
|
||||
// data: DATA[31:0]
|
||||
// return: ACK[2:0]
|
||||
uint8_t JTAG_Transfer(uint32_t request, uint32_t *data) {
|
||||
if (DAP_Data.fast_clock) {
|
||||
return JTAG_TransferFast(request, data);
|
||||
} else {
|
||||
return JTAG_TransferSlow(request, data);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endif /* (DAP_JTAG != 0) */
|
798
external/CMSIS_5/CMSIS/DAP/Firmware/Source/SWO.c
vendored
Normal file
798
external/CMSIS_5/CMSIS/DAP/Firmware/Source/SWO.c
vendored
Normal file
@ -0,0 +1,798 @@
|
||||
/*
|
||||
* Copyright (c) 2013-2021 ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the License); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ----------------------------------------------------------------------
|
||||
*
|
||||
* $Date: 29. March 2021
|
||||
* $Revision: V2.0.1
|
||||
*
|
||||
* Project: CMSIS-DAP Source
|
||||
* Title: SWO.c CMSIS-DAP SWO I/O
|
||||
*
|
||||
*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "DAP_config.h"
|
||||
#include "DAP.h"
|
||||
#if (SWO_UART != 0)
|
||||
#include "Driver_USART.h"
|
||||
#endif
|
||||
#if (SWO_STREAM != 0)
|
||||
#include "cmsis_os2.h"
|
||||
#define osObjectsExternal
|
||||
#include "osObjects.h"
|
||||
#endif
|
||||
|
||||
#if (SWO_STREAM != 0)
|
||||
#ifdef DAP_FW_V1
|
||||
#error "SWO Streaming Trace not supported in DAP V1!"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if (SWO_UART != 0)
|
||||
|
||||
// USART Driver
|
||||
#define _USART_Driver_(n) Driver_USART##n
|
||||
#define USART_Driver_(n) _USART_Driver_(n)
|
||||
extern ARM_DRIVER_USART USART_Driver_(SWO_UART_DRIVER);
|
||||
#define pUSART (&USART_Driver_(SWO_UART_DRIVER))
|
||||
|
||||
static uint8_t USART_Ready = 0U;
|
||||
|
||||
#endif /* (SWO_UART != 0) */
|
||||
|
||||
|
||||
#if ((SWO_UART != 0) || (SWO_MANCHESTER != 0))
|
||||
|
||||
|
||||
#define SWO_STREAM_TIMEOUT 50U /* Stream timeout in ms */
|
||||
|
||||
#define USB_BLOCK_SIZE 512U /* USB Block Size */
|
||||
#define TRACE_BLOCK_SIZE 64U /* Trace Block Size (2^n: 32...512) */
|
||||
|
||||
// Trace State
|
||||
static uint8_t TraceTransport = 0U; /* Trace Transport */
|
||||
static uint8_t TraceMode = 0U; /* Trace Mode */
|
||||
static uint8_t TraceStatus = 0U; /* Trace Status without Errors */
|
||||
static uint8_t TraceError[2] = {0U, 0U}; /* Trace Error flags (banked) */
|
||||
static uint8_t TraceError_n = 0U; /* Active Trace Error bank */
|
||||
|
||||
// Trace Buffer
|
||||
static uint8_t TraceBuf[SWO_BUFFER_SIZE]; /* Trace Buffer (must be 2^n) */
|
||||
static volatile uint32_t TraceIndexI = 0U; /* Incoming Trace Index */
|
||||
static volatile uint32_t TraceIndexO = 0U; /* Outgoing Trace Index */
|
||||
static volatile uint8_t TraceUpdate; /* Trace Update Flag */
|
||||
static uint32_t TraceBlockSize; /* Current Trace Block Size */
|
||||
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
// Trace Timestamp
|
||||
static volatile struct {
|
||||
uint32_t index;
|
||||
uint32_t tick;
|
||||
} TraceTimestamp;
|
||||
#endif
|
||||
|
||||
// Trace Helper functions
|
||||
static void ClearTrace (void);
|
||||
static void ResumeTrace (void);
|
||||
static uint32_t GetTraceCount (void);
|
||||
static uint8_t GetTraceStatus (void);
|
||||
static void SetTraceError (uint8_t flag);
|
||||
|
||||
#if (SWO_STREAM != 0)
|
||||
extern osThreadId_t SWO_ThreadId;
|
||||
static volatile uint8_t TransferBusy = 0U; /* Transfer Busy Flag */
|
||||
static uint32_t TransferSize; /* Current Transfer Size */
|
||||
#endif
|
||||
|
||||
|
||||
#if (SWO_UART != 0)
|
||||
|
||||
// USART Driver Callback function
|
||||
// event: event mask
|
||||
static void USART_Callback (uint32_t event) {
|
||||
uint32_t index_i;
|
||||
uint32_t index_o;
|
||||
uint32_t count;
|
||||
uint32_t num;
|
||||
|
||||
if (event & ARM_USART_EVENT_RECEIVE_COMPLETE) {
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
TraceTimestamp.tick = TIMESTAMP_GET();
|
||||
#endif
|
||||
index_o = TraceIndexO;
|
||||
index_i = TraceIndexI;
|
||||
index_i += TraceBlockSize;
|
||||
TraceIndexI = index_i;
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
TraceTimestamp.index = index_i;
|
||||
#endif
|
||||
num = TRACE_BLOCK_SIZE - (index_i & (TRACE_BLOCK_SIZE - 1U));
|
||||
count = index_i - index_o;
|
||||
if (count <= (SWO_BUFFER_SIZE - num)) {
|
||||
index_i &= SWO_BUFFER_SIZE - 1U;
|
||||
TraceBlockSize = num;
|
||||
pUSART->Receive(&TraceBuf[index_i], num);
|
||||
} else {
|
||||
TraceStatus = DAP_SWO_CAPTURE_ACTIVE | DAP_SWO_CAPTURE_PAUSED;
|
||||
}
|
||||
TraceUpdate = 1U;
|
||||
#if (SWO_STREAM != 0)
|
||||
if (TraceTransport == 2U) {
|
||||
if (count >= (USB_BLOCK_SIZE - (index_o & (USB_BLOCK_SIZE - 1U)))) {
|
||||
osThreadFlagsSet(SWO_ThreadId, 1U);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
if (event & ARM_USART_EVENT_RX_OVERFLOW) {
|
||||
SetTraceError(DAP_SWO_BUFFER_OVERRUN);
|
||||
}
|
||||
if (event & (ARM_USART_EVENT_RX_BREAK |
|
||||
ARM_USART_EVENT_RX_FRAMING_ERROR |
|
||||
ARM_USART_EVENT_RX_PARITY_ERROR)) {
|
||||
SetTraceError(DAP_SWO_STREAM_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
// Enable or disable SWO Mode (UART)
|
||||
// enable: enable flag
|
||||
// return: 1 - Success, 0 - Error
|
||||
__WEAK uint32_t SWO_Mode_UART (uint32_t enable) {
|
||||
int32_t status;
|
||||
|
||||
USART_Ready = 0U;
|
||||
|
||||
if (enable != 0U) {
|
||||
status = pUSART->Initialize(USART_Callback);
|
||||
if (status != ARM_DRIVER_OK) {
|
||||
return (0U);
|
||||
}
|
||||
status = pUSART->PowerControl(ARM_POWER_FULL);
|
||||
if (status != ARM_DRIVER_OK) {
|
||||
pUSART->Uninitialize();
|
||||
return (0U);
|
||||
}
|
||||
} else {
|
||||
pUSART->Control(ARM_USART_CONTROL_RX, 0U);
|
||||
pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U);
|
||||
pUSART->PowerControl(ARM_POWER_OFF);
|
||||
pUSART->Uninitialize();
|
||||
}
|
||||
return (1U);
|
||||
}
|
||||
|
||||
// Configure SWO Baudrate (UART)
|
||||
// baudrate: requested baudrate
|
||||
// return: actual baudrate or 0 when not configured
|
||||
__WEAK uint32_t SWO_Baudrate_UART (uint32_t baudrate) {
|
||||
int32_t status;
|
||||
uint32_t index;
|
||||
uint32_t num;
|
||||
|
||||
if (baudrate > SWO_UART_MAX_BAUDRATE) {
|
||||
baudrate = SWO_UART_MAX_BAUDRATE;
|
||||
}
|
||||
|
||||
if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) {
|
||||
pUSART->Control(ARM_USART_CONTROL_RX, 0U);
|
||||
if (pUSART->GetStatus().rx_busy) {
|
||||
TraceIndexI += pUSART->GetRxCount();
|
||||
pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U);
|
||||
}
|
||||
}
|
||||
|
||||
status = pUSART->Control(ARM_USART_MODE_ASYNCHRONOUS |
|
||||
ARM_USART_DATA_BITS_8 |
|
||||
ARM_USART_PARITY_NONE |
|
||||
ARM_USART_STOP_BITS_1,
|
||||
baudrate);
|
||||
|
||||
if (status == ARM_DRIVER_OK) {
|
||||
USART_Ready = 1U;
|
||||
} else {
|
||||
USART_Ready = 0U;
|
||||
return (0U);
|
||||
}
|
||||
|
||||
if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) {
|
||||
if ((TraceStatus & DAP_SWO_CAPTURE_PAUSED) == 0U) {
|
||||
index = TraceIndexI & (SWO_BUFFER_SIZE - 1U);
|
||||
num = TRACE_BLOCK_SIZE - (index & (TRACE_BLOCK_SIZE - 1U));
|
||||
TraceBlockSize = num;
|
||||
pUSART->Receive(&TraceBuf[index], num);
|
||||
}
|
||||
pUSART->Control(ARM_USART_CONTROL_RX, 1U);
|
||||
}
|
||||
|
||||
return (baudrate);
|
||||
}
|
||||
|
||||
// Control SWO Capture (UART)
|
||||
// active: active flag
|
||||
// return: 1 - Success, 0 - Error
|
||||
__WEAK uint32_t SWO_Control_UART (uint32_t active) {
|
||||
int32_t status;
|
||||
|
||||
if (active) {
|
||||
if (!USART_Ready) {
|
||||
return (0U);
|
||||
}
|
||||
TraceBlockSize = 1U;
|
||||
status = pUSART->Receive(&TraceBuf[0], 1U);
|
||||
if (status != ARM_DRIVER_OK) {
|
||||
return (0U);
|
||||
}
|
||||
status = pUSART->Control(ARM_USART_CONTROL_RX, 1U);
|
||||
if (status != ARM_DRIVER_OK) {
|
||||
return (0U);
|
||||
}
|
||||
} else {
|
||||
pUSART->Control(ARM_USART_CONTROL_RX, 0U);
|
||||
if (pUSART->GetStatus().rx_busy) {
|
||||
TraceIndexI += pUSART->GetRxCount();
|
||||
pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U);
|
||||
}
|
||||
}
|
||||
return (1U);
|
||||
}
|
||||
|
||||
// Start SWO Capture (UART)
|
||||
// buf: pointer to buffer for capturing
|
||||
// num: number of bytes to capture
|
||||
__WEAK void SWO_Capture_UART (uint8_t *buf, uint32_t num) {
|
||||
TraceBlockSize = num;
|
||||
pUSART->Receive(buf, num);
|
||||
}
|
||||
|
||||
// Get SWO Pending Trace Count (UART)
|
||||
// return: number of pending trace data bytes
|
||||
__WEAK uint32_t SWO_GetCount_UART (void) {
|
||||
uint32_t count;
|
||||
|
||||
if (pUSART->GetStatus().rx_busy) {
|
||||
count = pUSART->GetRxCount();
|
||||
} else {
|
||||
count = 0U;
|
||||
}
|
||||
return (count);
|
||||
}
|
||||
|
||||
#endif /* (SWO_UART != 0) */
|
||||
|
||||
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
|
||||
// Enable or disable SWO Mode (Manchester)
|
||||
// enable: enable flag
|
||||
// return: 1 - Success, 0 - Error
|
||||
__WEAK uint32_t SWO_Mode_Manchester (uint32_t enable) {
|
||||
return (0U);
|
||||
}
|
||||
|
||||
// Configure SWO Baudrate (Manchester)
|
||||
// baudrate: requested baudrate
|
||||
// return: actual baudrate or 0 when not configured
|
||||
__WEAK uint32_t SWO_Baudrate_Manchester (uint32_t baudrate) {
|
||||
return (0U);
|
||||
}
|
||||
|
||||
// Control SWO Capture (Manchester)
|
||||
// active: active flag
|
||||
// return: 1 - Success, 0 - Error
|
||||
__WEAK uint32_t SWO_Control_Manchester (uint32_t active) {
|
||||
return (0U);
|
||||
}
|
||||
|
||||
// Start SWO Capture (Manchester)
|
||||
// buf: pointer to buffer for capturing
|
||||
// num: number of bytes to capture
|
||||
__WEAK void SWO_Capture_Manchester (uint8_t *buf, uint32_t num) {
|
||||
}
|
||||
|
||||
// Get SWO Pending Trace Count (Manchester)
|
||||
// return: number of pending trace data bytes
|
||||
__WEAK uint32_t SWO_GetCount_Manchester (void) {
|
||||
}
|
||||
|
||||
#endif /* (SWO_MANCHESTER != 0) */
|
||||
|
||||
|
||||
// Clear Trace Errors and Data
|
||||
static void ClearTrace (void) {
|
||||
|
||||
#if (SWO_STREAM != 0)
|
||||
if (TraceTransport == 2U) {
|
||||
if (TransferBusy != 0U) {
|
||||
SWO_AbortTransfer();
|
||||
TransferBusy = 0U;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
TraceError[0] = 0U;
|
||||
TraceError[1] = 0U;
|
||||
TraceError_n = 0U;
|
||||
TraceIndexI = 0U;
|
||||
TraceIndexO = 0U;
|
||||
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
TraceTimestamp.index = 0U;
|
||||
TraceTimestamp.tick = 0U;
|
||||
#endif
|
||||
}
|
||||
|
||||
// Resume Trace Capture
|
||||
static void ResumeTrace (void) {
|
||||
uint32_t index_i;
|
||||
uint32_t index_o;
|
||||
|
||||
if (TraceStatus == (DAP_SWO_CAPTURE_ACTIVE | DAP_SWO_CAPTURE_PAUSED)) {
|
||||
index_i = TraceIndexI;
|
||||
index_o = TraceIndexO;
|
||||
if ((index_i - index_o) < SWO_BUFFER_SIZE) {
|
||||
index_i &= SWO_BUFFER_SIZE - 1U;
|
||||
switch (TraceMode) {
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
TraceStatus = DAP_SWO_CAPTURE_ACTIVE;
|
||||
SWO_Capture_UART(&TraceBuf[index_i], 1U);
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
TraceStatus = DAP_SWO_CAPTURE_ACTIVE;
|
||||
SWO_Capture_Manchester(&TraceBuf[index_i], 1U);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Get Trace Count
|
||||
// return: number of available data bytes in trace buffer
|
||||
static uint32_t GetTraceCount (void) {
|
||||
uint32_t count;
|
||||
|
||||
if (TraceStatus == DAP_SWO_CAPTURE_ACTIVE) {
|
||||
do {
|
||||
TraceUpdate = 0U;
|
||||
count = TraceIndexI - TraceIndexO;
|
||||
switch (TraceMode) {
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
count += SWO_GetCount_UART();
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
count += SWO_GetCount_Manchester();
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
} while (TraceUpdate != 0U);
|
||||
} else {
|
||||
count = TraceIndexI - TraceIndexO;
|
||||
}
|
||||
|
||||
return (count);
|
||||
}
|
||||
|
||||
// Get Trace Status (clear Error flags)
|
||||
// return: Trace Status (Active flag and Error flags)
|
||||
static uint8_t GetTraceStatus (void) {
|
||||
uint8_t status;
|
||||
uint32_t n;
|
||||
|
||||
n = TraceError_n;
|
||||
TraceError_n ^= 1U;
|
||||
status = TraceStatus | TraceError[n];
|
||||
TraceError[n] = 0U;
|
||||
|
||||
return (status);
|
||||
}
|
||||
|
||||
// Set Trace Error flag(s)
|
||||
// flag: error flag(s) to set
|
||||
static void SetTraceError (uint8_t flag) {
|
||||
TraceError[TraceError_n] |= flag;
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Transport command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_Transport (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t transport;
|
||||
uint32_t result;
|
||||
|
||||
if ((TraceStatus & DAP_SWO_CAPTURE_ACTIVE) == 0U) {
|
||||
transport = *request;
|
||||
switch (transport) {
|
||||
case 0U:
|
||||
case 1U:
|
||||
#if (SWO_STREAM != 0)
|
||||
case 2U:
|
||||
#endif
|
||||
TraceTransport = transport;
|
||||
result = 1U;
|
||||
break;
|
||||
default:
|
||||
result = 0U;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
result = 0U;
|
||||
}
|
||||
|
||||
if (result != 0U) {
|
||||
*response = DAP_OK;
|
||||
} else {
|
||||
*response = DAP_ERROR;
|
||||
}
|
||||
|
||||
return ((1U << 16) | 1U);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Mode command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_Mode (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t mode;
|
||||
uint32_t result;
|
||||
|
||||
mode = *request;
|
||||
|
||||
switch (TraceMode) {
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
SWO_Mode_UART(0U);
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
SWO_Mode_Manchester(0U);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
switch (mode) {
|
||||
case DAP_SWO_OFF:
|
||||
result = 1U;
|
||||
break;
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
result = SWO_Mode_UART(1U);
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
result = SWO_Mode_Manchester(1U);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
result = 0U;
|
||||
break;
|
||||
}
|
||||
if (result != 0U) {
|
||||
TraceMode = mode;
|
||||
} else {
|
||||
TraceMode = DAP_SWO_OFF;
|
||||
}
|
||||
|
||||
TraceStatus = 0U;
|
||||
|
||||
if (result != 0U) {
|
||||
*response = DAP_OK;
|
||||
} else {
|
||||
*response = DAP_ERROR;
|
||||
}
|
||||
|
||||
return ((1U << 16) | 1U);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Baudrate command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_Baudrate (const uint8_t *request, uint8_t *response) {
|
||||
uint32_t baudrate;
|
||||
|
||||
baudrate = (uint32_t)(*(request+0) << 0) |
|
||||
(uint32_t)(*(request+1) << 8) |
|
||||
(uint32_t)(*(request+2) << 16) |
|
||||
(uint32_t)(*(request+3) << 24);
|
||||
|
||||
switch (TraceMode) {
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
baudrate = SWO_Baudrate_UART(baudrate);
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
baudrate = SWO_Baudrate_Manchester(baudrate);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
baudrate = 0U;
|
||||
break;
|
||||
}
|
||||
|
||||
if (baudrate == 0U) {
|
||||
TraceStatus = 0U;
|
||||
}
|
||||
|
||||
*response++ = (uint8_t)(baudrate >> 0);
|
||||
*response++ = (uint8_t)(baudrate >> 8);
|
||||
*response++ = (uint8_t)(baudrate >> 16);
|
||||
*response = (uint8_t)(baudrate >> 24);
|
||||
|
||||
return ((4U << 16) | 4U);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Control command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_Control (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t active;
|
||||
uint32_t result;
|
||||
|
||||
active = *request & DAP_SWO_CAPTURE_ACTIVE;
|
||||
|
||||
if (active != (TraceStatus & DAP_SWO_CAPTURE_ACTIVE)) {
|
||||
if (active) {
|
||||
ClearTrace();
|
||||
}
|
||||
switch (TraceMode) {
|
||||
#if (SWO_UART != 0)
|
||||
case DAP_SWO_UART:
|
||||
result = SWO_Control_UART(active);
|
||||
break;
|
||||
#endif
|
||||
#if (SWO_MANCHESTER != 0)
|
||||
case DAP_SWO_MANCHESTER:
|
||||
result = SWO_Control_Manchester(active);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
result = 0U;
|
||||
break;
|
||||
}
|
||||
if (result != 0U) {
|
||||
TraceStatus = active;
|
||||
#if (SWO_STREAM != 0)
|
||||
if (TraceTransport == 2U) {
|
||||
osThreadFlagsSet(SWO_ThreadId, 1U);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
} else {
|
||||
result = 1U;
|
||||
}
|
||||
|
||||
if (result != 0U) {
|
||||
*response = DAP_OK;
|
||||
} else {
|
||||
*response = DAP_ERROR;
|
||||
}
|
||||
|
||||
return ((1U << 16) | 1U);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Status command and prepare response
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response
|
||||
uint32_t SWO_Status (uint8_t *response) {
|
||||
uint8_t status;
|
||||
uint32_t count;
|
||||
|
||||
status = GetTraceStatus();
|
||||
count = GetTraceCount();
|
||||
|
||||
*response++ = status;
|
||||
*response++ = (uint8_t)(count >> 0);
|
||||
*response++ = (uint8_t)(count >> 8);
|
||||
*response++ = (uint8_t)(count >> 16);
|
||||
*response = (uint8_t)(count >> 24);
|
||||
|
||||
return (5U);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Extended Status command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_ExtendedStatus (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t cmd;
|
||||
uint8_t status;
|
||||
uint32_t count;
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
uint32_t index;
|
||||
uint32_t tick;
|
||||
#endif
|
||||
uint32_t num;
|
||||
|
||||
num = 0U;
|
||||
cmd = *request;
|
||||
|
||||
if (cmd & 0x01U) {
|
||||
status = GetTraceStatus();
|
||||
*response++ = status;
|
||||
num += 1U;
|
||||
}
|
||||
|
||||
if (cmd & 0x02U) {
|
||||
count = GetTraceCount();
|
||||
*response++ = (uint8_t)(count >> 0);
|
||||
*response++ = (uint8_t)(count >> 8);
|
||||
*response++ = (uint8_t)(count >> 16);
|
||||
*response++ = (uint8_t)(count >> 24);
|
||||
num += 4U;
|
||||
}
|
||||
|
||||
#if (TIMESTAMP_CLOCK != 0U)
|
||||
if (cmd & 0x04U) {
|
||||
do {
|
||||
TraceUpdate = 0U;
|
||||
index = TraceTimestamp.index;
|
||||
tick = TraceTimestamp.tick;
|
||||
} while (TraceUpdate != 0U);
|
||||
*response++ = (uint8_t)(index >> 0);
|
||||
*response++ = (uint8_t)(index >> 8);
|
||||
*response++ = (uint8_t)(index >> 16);
|
||||
*response++ = (uint8_t)(index >> 24);
|
||||
*response++ = (uint8_t)(tick >> 0);
|
||||
*response++ = (uint8_t)(tick >> 8);
|
||||
*response++ = (uint8_t)(tick >> 16);
|
||||
*response++ = (uint8_t)(tick >> 24);
|
||||
num += 4U;
|
||||
}
|
||||
#endif
|
||||
|
||||
return ((1U << 16) | num);
|
||||
}
|
||||
|
||||
|
||||
// Process SWO Data command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t SWO_Data (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t status;
|
||||
uint32_t count;
|
||||
uint32_t index;
|
||||
uint32_t n, i;
|
||||
|
||||
status = GetTraceStatus();
|
||||
count = GetTraceCount();
|
||||
|
||||
if (TraceTransport == 1U) {
|
||||
n = (uint32_t)(*(request+0) << 0) |
|
||||
(uint32_t)(*(request+1) << 8);
|
||||
if (n > (DAP_PACKET_SIZE - 4U)) {
|
||||
n = DAP_PACKET_SIZE - 4U;
|
||||
}
|
||||
if (count > n) {
|
||||
count = n;
|
||||
}
|
||||
} else {
|
||||
count = 0U;
|
||||
}
|
||||
|
||||
*response++ = status;
|
||||
*response++ = (uint8_t)(count >> 0);
|
||||
*response++ = (uint8_t)(count >> 8);
|
||||
|
||||
if (TraceTransport == 1U) {
|
||||
index = TraceIndexO;
|
||||
for (i = index, n = count; n; n--) {
|
||||
i &= SWO_BUFFER_SIZE - 1U;
|
||||
*response++ = TraceBuf[i++];
|
||||
}
|
||||
TraceIndexO = index + count;
|
||||
ResumeTrace();
|
||||
}
|
||||
|
||||
return ((2U << 16) | (3U + count));
|
||||
}
|
||||
|
||||
|
||||
#if (SWO_STREAM != 0)
|
||||
|
||||
// SWO Data Transfer complete callback
|
||||
void SWO_TransferComplete (void) {
|
||||
TraceIndexO += TransferSize;
|
||||
TransferBusy = 0U;
|
||||
ResumeTrace();
|
||||
osThreadFlagsSet(SWO_ThreadId, 1U);
|
||||
}
|
||||
|
||||
// SWO Thread
|
||||
__NO_RETURN void SWO_Thread (void *argument) {
|
||||
uint32_t timeout;
|
||||
uint32_t flags;
|
||||
uint32_t count;
|
||||
uint32_t index;
|
||||
uint32_t i, n;
|
||||
(void) argument;
|
||||
|
||||
timeout = osWaitForever;
|
||||
|
||||
for (;;) {
|
||||
flags = osThreadFlagsWait(1U, osFlagsWaitAny, timeout);
|
||||
if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) {
|
||||
timeout = SWO_STREAM_TIMEOUT;
|
||||
} else {
|
||||
timeout = osWaitForever;
|
||||
flags = osFlagsErrorTimeout;
|
||||
}
|
||||
if (TransferBusy == 0U) {
|
||||
count = GetTraceCount();
|
||||
if (count != 0U) {
|
||||
index = TraceIndexO & (SWO_BUFFER_SIZE - 1U);
|
||||
n = SWO_BUFFER_SIZE - index;
|
||||
if (count > n) {
|
||||
count = n;
|
||||
}
|
||||
if (flags != osFlagsErrorTimeout) {
|
||||
i = index & (USB_BLOCK_SIZE - 1U);
|
||||
if (i == 0U) {
|
||||
count &= ~(USB_BLOCK_SIZE - 1U);
|
||||
} else {
|
||||
n = USB_BLOCK_SIZE - i;
|
||||
if (count >= n) {
|
||||
count = n;
|
||||
} else {
|
||||
count = 0U;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (count != 0U) {
|
||||
TransferSize = count;
|
||||
TransferBusy = 1U;
|
||||
SWO_QueueTransfer(&TraceBuf[index], count);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* (SWO_STREAM != 0) */
|
||||
|
||||
|
||||
#endif /* ((SWO_UART != 0) || (SWO_MANCHESTER != 0)) */
|
286
external/CMSIS_5/CMSIS/DAP/Firmware/Source/SW_DP.c
vendored
Normal file
286
external/CMSIS_5/CMSIS/DAP/Firmware/Source/SW_DP.c
vendored
Normal file
@ -0,0 +1,286 @@
|
||||
/*
|
||||
* Copyright (c) 2013-2017 ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the License); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ----------------------------------------------------------------------
|
||||
*
|
||||
* $Date: 1. December 2017
|
||||
* $Revision: V2.0.0
|
||||
*
|
||||
* Project: CMSIS-DAP Source
|
||||
* Title: SW_DP.c CMSIS-DAP SW DP I/O
|
||||
*
|
||||
*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "DAP_config.h"
|
||||
#include "DAP.h"
|
||||
|
||||
|
||||
// SW Macros
|
||||
|
||||
#define PIN_SWCLK_SET PIN_SWCLK_TCK_SET
|
||||
#define PIN_SWCLK_CLR PIN_SWCLK_TCK_CLR
|
||||
|
||||
#define SW_CLOCK_CYCLE() \
|
||||
PIN_SWCLK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
PIN_SWCLK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define SW_WRITE_BIT(bit) \
|
||||
PIN_SWDIO_OUT(bit); \
|
||||
PIN_SWCLK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
PIN_SWCLK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define SW_READ_BIT(bit) \
|
||||
PIN_SWCLK_CLR(); \
|
||||
PIN_DELAY(); \
|
||||
bit = PIN_SWDIO_IN(); \
|
||||
PIN_SWCLK_SET(); \
|
||||
PIN_DELAY()
|
||||
|
||||
#define PIN_DELAY() PIN_DELAY_SLOW(DAP_Data.clock_delay)
|
||||
|
||||
|
||||
// Generate SWJ Sequence
|
||||
// count: sequence bit count
|
||||
// data: pointer to sequence bit data
|
||||
// return: none
|
||||
#if ((DAP_SWD != 0) || (DAP_JTAG != 0))
|
||||
void SWJ_Sequence (uint32_t count, const uint8_t *data) {
|
||||
uint32_t val;
|
||||
uint32_t n;
|
||||
|
||||
val = 0U;
|
||||
n = 0U;
|
||||
while (count--) {
|
||||
if (n == 0U) {
|
||||
val = *data++;
|
||||
n = 8U;
|
||||
}
|
||||
if (val & 1U) {
|
||||
PIN_SWDIO_TMS_SET();
|
||||
} else {
|
||||
PIN_SWDIO_TMS_CLR();
|
||||
}
|
||||
SW_CLOCK_CYCLE();
|
||||
val >>= 1;
|
||||
n--;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
// Generate SWD Sequence
|
||||
// info: sequence information
|
||||
// swdo: pointer to SWDIO generated data
|
||||
// swdi: pointer to SWDIO captured data
|
||||
// return: none
|
||||
#if (DAP_SWD != 0)
|
||||
void SWD_Sequence (uint32_t info, const uint8_t *swdo, uint8_t *swdi) {
|
||||
uint32_t val;
|
||||
uint32_t bit;
|
||||
uint32_t n, k;
|
||||
|
||||
n = info & SWD_SEQUENCE_CLK;
|
||||
if (n == 0U) {
|
||||
n = 64U;
|
||||
}
|
||||
|
||||
if (info & SWD_SEQUENCE_DIN) {
|
||||
while (n) {
|
||||
val = 0U;
|
||||
for (k = 8U; k && n; k--, n--) {
|
||||
SW_READ_BIT(bit);
|
||||
val >>= 1;
|
||||
val |= bit << 7;
|
||||
}
|
||||
val >>= k;
|
||||
*swdi++ = (uint8_t)val;
|
||||
}
|
||||
} else {
|
||||
while (n) {
|
||||
val = *swdo++;
|
||||
for (k = 8U; k && n; k--, n--) {
|
||||
SW_WRITE_BIT(val);
|
||||
val >>= 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if (DAP_SWD != 0)
|
||||
|
||||
|
||||
// SWD Transfer I/O
|
||||
// request: A[3:2] RnW APnDP
|
||||
// data: DATA[31:0]
|
||||
// return: ACK[2:0]
|
||||
#define SWD_TransferFunction(speed) /**/ \
|
||||
static uint8_t SWD_Transfer##speed (uint32_t request, uint32_t *data) { \
|
||||
uint32_t ack; \
|
||||
uint32_t bit; \
|
||||
uint32_t val; \
|
||||
uint32_t parity; \
|
||||
\
|
||||
uint32_t n; \
|
||||
\
|
||||
/* Packet Request */ \
|
||||
parity = 0U; \
|
||||
SW_WRITE_BIT(1U); /* Start Bit */ \
|
||||
bit = request >> 0; \
|
||||
SW_WRITE_BIT(bit); /* APnDP Bit */ \
|
||||
parity += bit; \
|
||||
bit = request >> 1; \
|
||||
SW_WRITE_BIT(bit); /* RnW Bit */ \
|
||||
parity += bit; \
|
||||
bit = request >> 2; \
|
||||
SW_WRITE_BIT(bit); /* A2 Bit */ \
|
||||
parity += bit; \
|
||||
bit = request >> 3; \
|
||||
SW_WRITE_BIT(bit); /* A3 Bit */ \
|
||||
parity += bit; \
|
||||
SW_WRITE_BIT(parity); /* Parity Bit */ \
|
||||
SW_WRITE_BIT(0U); /* Stop Bit */ \
|
||||
SW_WRITE_BIT(1U); /* Park Bit */ \
|
||||
\
|
||||
/* Turnaround */ \
|
||||
PIN_SWDIO_OUT_DISABLE(); \
|
||||
for (n = DAP_Data.swd_conf.turnaround; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); \
|
||||
} \
|
||||
\
|
||||
/* Acknowledge response */ \
|
||||
SW_READ_BIT(bit); \
|
||||
ack = bit << 0; \
|
||||
SW_READ_BIT(bit); \
|
||||
ack |= bit << 1; \
|
||||
SW_READ_BIT(bit); \
|
||||
ack |= bit << 2; \
|
||||
\
|
||||
if (ack == DAP_TRANSFER_OK) { /* OK response */ \
|
||||
/* Data transfer */ \
|
||||
if (request & DAP_TRANSFER_RnW) { \
|
||||
/* Read data */ \
|
||||
val = 0U; \
|
||||
parity = 0U; \
|
||||
for (n = 32U; n; n--) { \
|
||||
SW_READ_BIT(bit); /* Read RDATA[0:31] */ \
|
||||
parity += bit; \
|
||||
val >>= 1; \
|
||||
val |= bit << 31; \
|
||||
} \
|
||||
SW_READ_BIT(bit); /* Read Parity */ \
|
||||
if ((parity ^ bit) & 1U) { \
|
||||
ack = DAP_TRANSFER_ERROR; \
|
||||
} \
|
||||
if (data) { *data = val; } \
|
||||
/* Turnaround */ \
|
||||
for (n = DAP_Data.swd_conf.turnaround; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); \
|
||||
} \
|
||||
PIN_SWDIO_OUT_ENABLE(); \
|
||||
} else { \
|
||||
/* Turnaround */ \
|
||||
for (n = DAP_Data.swd_conf.turnaround; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); \
|
||||
} \
|
||||
PIN_SWDIO_OUT_ENABLE(); \
|
||||
/* Write data */ \
|
||||
val = *data; \
|
||||
parity = 0U; \
|
||||
for (n = 32U; n; n--) { \
|
||||
SW_WRITE_BIT(val); /* Write WDATA[0:31] */ \
|
||||
parity += val; \
|
||||
val >>= 1; \
|
||||
} \
|
||||
SW_WRITE_BIT(parity); /* Write Parity Bit */ \
|
||||
} \
|
||||
/* Capture Timestamp */ \
|
||||
if (request & DAP_TRANSFER_TIMESTAMP) { \
|
||||
DAP_Data.timestamp = TIMESTAMP_GET(); \
|
||||
} \
|
||||
/* Idle cycles */ \
|
||||
n = DAP_Data.transfer.idle_cycles; \
|
||||
if (n) { \
|
||||
PIN_SWDIO_OUT(0U); \
|
||||
for (; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); \
|
||||
} \
|
||||
} \
|
||||
PIN_SWDIO_OUT(1U); \
|
||||
return ((uint8_t)ack); \
|
||||
} \
|
||||
\
|
||||
if ((ack == DAP_TRANSFER_WAIT) || (ack == DAP_TRANSFER_FAULT)) { \
|
||||
/* WAIT or FAULT response */ \
|
||||
if (DAP_Data.swd_conf.data_phase && ((request & DAP_TRANSFER_RnW) != 0U)) { \
|
||||
for (n = 32U+1U; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); /* Dummy Read RDATA[0:31] + Parity */ \
|
||||
} \
|
||||
} \
|
||||
/* Turnaround */ \
|
||||
for (n = DAP_Data.swd_conf.turnaround; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); \
|
||||
} \
|
||||
PIN_SWDIO_OUT_ENABLE(); \
|
||||
if (DAP_Data.swd_conf.data_phase && ((request & DAP_TRANSFER_RnW) == 0U)) { \
|
||||
PIN_SWDIO_OUT(0U); \
|
||||
for (n = 32U+1U; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); /* Dummy Write WDATA[0:31] + Parity */ \
|
||||
} \
|
||||
} \
|
||||
PIN_SWDIO_OUT(1U); \
|
||||
return ((uint8_t)ack); \
|
||||
} \
|
||||
\
|
||||
/* Protocol error */ \
|
||||
for (n = DAP_Data.swd_conf.turnaround + 32U + 1U; n; n--) { \
|
||||
SW_CLOCK_CYCLE(); /* Back off data phase */ \
|
||||
} \
|
||||
PIN_SWDIO_OUT_ENABLE(); \
|
||||
PIN_SWDIO_OUT(1U); \
|
||||
return ((uint8_t)ack); \
|
||||
}
|
||||
|
||||
|
||||
#undef PIN_DELAY
|
||||
#define PIN_DELAY() PIN_DELAY_FAST()
|
||||
SWD_TransferFunction(Fast)
|
||||
|
||||
#undef PIN_DELAY
|
||||
#define PIN_DELAY() PIN_DELAY_SLOW(DAP_Data.clock_delay)
|
||||
SWD_TransferFunction(Slow)
|
||||
|
||||
|
||||
// SWD Transfer I/O
|
||||
// request: A[3:2] RnW APnDP
|
||||
// data: DATA[31:0]
|
||||
// return: ACK[2:0]
|
||||
uint8_t SWD_Transfer(uint32_t request, uint32_t *data) {
|
||||
if (DAP_Data.fast_clock) {
|
||||
return SWD_TransferFast(request, data);
|
||||
} else {
|
||||
return SWD_TransferSlow(request, data);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endif /* (DAP_SWD != 0) */
|
652
external/CMSIS_5/CMSIS/DAP/Firmware/Source/UART.c
vendored
Normal file
652
external/CMSIS_5/CMSIS/DAP/Firmware/Source/UART.c
vendored
Normal file
@ -0,0 +1,652 @@
|
||||
/*
|
||||
* Copyright (c) 2021 ARM Limited. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the License); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ----------------------------------------------------------------------
|
||||
*
|
||||
* $Date: 1. March 2021
|
||||
* $Revision: V1.0.0
|
||||
*
|
||||
* Project: CMSIS-DAP Source
|
||||
* Title: UART.c CMSIS-DAP UART
|
||||
*
|
||||
*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "DAP_config.h"
|
||||
#include "DAP.h"
|
||||
|
||||
#if (DAP_UART != 0)
|
||||
|
||||
#ifdef DAP_FW_V1
|
||||
#error "UART Communication Port not supported in DAP V1!"
|
||||
#endif
|
||||
|
||||
#include "Driver_USART.h"
|
||||
|
||||
#include "cmsis_os2.h"
|
||||
#include <string.h>
|
||||
|
||||
#define UART_RX_BLOCK_SIZE 32U /* Uart Rx Block Size (must be 2^n) */
|
||||
|
||||
// USART Driver
|
||||
#define _USART_Driver_(n) Driver_USART##n
|
||||
#define USART_Driver_(n) _USART_Driver_(n)
|
||||
extern ARM_DRIVER_USART USART_Driver_(DAP_UART_DRIVER);
|
||||
#define pUSART (&USART_Driver_(DAP_UART_DRIVER))
|
||||
|
||||
// UART Configuration
|
||||
#if (DAP_UART_USB_COM_PORT != 0)
|
||||
static uint8_t UartTransport = DAP_UART_TRANSPORT_USB_COM_PORT;
|
||||
#else
|
||||
static uint8_t UartTransport = DAP_UART_TRANSPORT_NONE;
|
||||
#endif
|
||||
|
||||
// UART Flags
|
||||
static uint8_t UartConfigured = 0U;
|
||||
static uint8_t UartReceiveEnabled = 0U;
|
||||
static uint8_t UartTransmitEnabled = 0U;
|
||||
static uint8_t UartTransmitActive = 0U;
|
||||
|
||||
// UART TX Buffer
|
||||
static uint8_t UartTxBuf[DAP_UART_TX_BUFFER_SIZE];
|
||||
static volatile uint32_t UartTxIndexI = 0U;
|
||||
static volatile uint32_t UartTxIndexO = 0U;
|
||||
|
||||
// UART RX Buffer
|
||||
static uint8_t UartRxBuf[DAP_UART_RX_BUFFER_SIZE];
|
||||
static volatile uint32_t UartRxIndexI = 0U;
|
||||
static volatile uint32_t UartRxIndexO = 0U;
|
||||
|
||||
// Uart Errors
|
||||
static volatile uint8_t UartErrorRxDataLost = 0U;
|
||||
static volatile uint8_t UartErrorFraming = 0U;
|
||||
static volatile uint8_t UartErrorParity = 0U;
|
||||
|
||||
// UART Transmit
|
||||
static uint32_t UartTxNum = 0U;
|
||||
|
||||
// Function prototypes
|
||||
static uint8_t UART_Init (void);
|
||||
static void UART_Uninit (void);
|
||||
static uint8_t UART_Get_Status (void);
|
||||
static uint8_t UART_Receive_Enable (void);
|
||||
static uint8_t UART_Transmit_Enable (void);
|
||||
static void UART_Receive_Disable (void);
|
||||
static void UART_Transmit_Disable (void);
|
||||
static void UART_Receive_Flush (void);
|
||||
static void UART_Transmit_Flush (void);
|
||||
static void UART_Receive (void);
|
||||
static void UART_Transmit (void);
|
||||
|
||||
|
||||
// USART Driver Callback function
|
||||
// event: event mask
|
||||
static void USART_Callback (uint32_t event) {
|
||||
if (event & ARM_USART_EVENT_SEND_COMPLETE) {
|
||||
UartTxIndexO += UartTxNum;
|
||||
UartTransmitActive = 0U;
|
||||
UART_Transmit();
|
||||
}
|
||||
if (event & ARM_USART_EVENT_RECEIVE_COMPLETE) {
|
||||
UartRxIndexI += UART_RX_BLOCK_SIZE;
|
||||
UART_Receive();
|
||||
}
|
||||
if (event & ARM_USART_EVENT_RX_OVERFLOW) {
|
||||
UartErrorRxDataLost = 1U;
|
||||
}
|
||||
if (event & ARM_USART_EVENT_RX_FRAMING_ERROR) {
|
||||
UartErrorFraming = 1U;
|
||||
}
|
||||
if (event & ARM_USART_EVENT_RX_PARITY_ERROR) {
|
||||
UartErrorParity = 1U;
|
||||
}
|
||||
}
|
||||
|
||||
// Init UART
|
||||
// return: DAP_OK or DAP_ERROR
|
||||
static uint8_t UART_Init (void) {
|
||||
int32_t status;
|
||||
uint8_t ret = DAP_ERROR;
|
||||
|
||||
UartConfigured = 0U;
|
||||
UartReceiveEnabled = 0U;
|
||||
UartTransmitEnabled = 0U;
|
||||
UartTransmitActive = 0U;
|
||||
UartErrorRxDataLost = 0U;
|
||||
UartErrorFraming = 0U;
|
||||
UartErrorParity = 0U;
|
||||
UartTxIndexI = 0U;
|
||||
UartTxIndexO = 0U;
|
||||
UartRxIndexI = 0U;
|
||||
UartRxIndexO = 0U;
|
||||
UartTxNum = 0U;
|
||||
|
||||
status = pUSART->Initialize(USART_Callback);
|
||||
if (status == ARM_DRIVER_OK) {
|
||||
status = pUSART->PowerControl(ARM_POWER_FULL);
|
||||
}
|
||||
if (status == ARM_DRIVER_OK) {
|
||||
ret = DAP_OK;
|
||||
}
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
// Un-Init UART
|
||||
static void UART_Uninit (void) {
|
||||
UartConfigured = 0U;
|
||||
|
||||
pUSART->PowerControl(ARM_POWER_OFF);
|
||||
pUSART->Uninitialize();
|
||||
}
|
||||
|
||||
// Get UART Status
|
||||
// return: status
|
||||
static uint8_t UART_Get_Status (void) {
|
||||
uint8_t status = 0U;
|
||||
|
||||
if (UartReceiveEnabled != 0U) {
|
||||
status |= DAP_UART_STATUS_RX_ENABLED;
|
||||
}
|
||||
if (UartErrorRxDataLost != 0U) {
|
||||
UartErrorRxDataLost = 0U;
|
||||
status |= DAP_UART_STATUS_RX_DATA_LOST;
|
||||
}
|
||||
if (UartErrorFraming != 0U) {
|
||||
UartErrorFraming = 0U;
|
||||
status |= DAP_UART_STATUS_FRAMING_ERROR;
|
||||
}
|
||||
if (UartErrorParity != 0U) {
|
||||
UartErrorParity = 0U;
|
||||
status |= DAP_UART_STATUS_PARITY_ERROR;
|
||||
}
|
||||
if (UartTransmitEnabled != 0U) {
|
||||
status |= DAP_UART_STATUS_TX_ENABLED;
|
||||
}
|
||||
|
||||
return (status);
|
||||
}
|
||||
|
||||
// Enable UART Receive
|
||||
// return: DAP_OK or DAP_ERROR
|
||||
static uint8_t UART_Receive_Enable (void) {
|
||||
int32_t status;
|
||||
uint8_t ret = DAP_ERROR;
|
||||
|
||||
if (UartReceiveEnabled == 0U) {
|
||||
// Flush Buffers
|
||||
UartRxIndexI = 0U;
|
||||
UartRxIndexO = 0U;
|
||||
|
||||
UART_Receive();
|
||||
status = pUSART->Control(ARM_USART_CONTROL_RX, 1U);
|
||||
if (status == ARM_DRIVER_OK) {
|
||||
UartReceiveEnabled = 1U;
|
||||
ret = DAP_OK;
|
||||
}
|
||||
} else {
|
||||
ret = DAP_OK;
|
||||
}
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
// Enable UART Transmit
|
||||
// return: DAP_OK or DAP_ERROR
|
||||
static uint8_t UART_Transmit_Enable (void) {
|
||||
int32_t status;
|
||||
uint8_t ret = DAP_ERROR;
|
||||
|
||||
if (UartTransmitEnabled == 0U) {
|
||||
// Flush Buffers
|
||||
UartTransmitActive = 0U;
|
||||
UartTxIndexI = 0U;
|
||||
UartTxIndexO = 0U;
|
||||
UartTxNum = 0U;
|
||||
|
||||
status = pUSART->Control(ARM_USART_CONTROL_TX, 1U);
|
||||
if (status == ARM_DRIVER_OK) {
|
||||
UartTransmitEnabled = 1U;
|
||||
ret = DAP_OK;
|
||||
}
|
||||
} else {
|
||||
ret = DAP_OK;
|
||||
}
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
// Disable UART Receive
|
||||
static void UART_Receive_Disable (void) {
|
||||
if (UartReceiveEnabled != 0U) {
|
||||
pUSART->Control(ARM_USART_CONTROL_RX, 0U);
|
||||
pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U);
|
||||
UartReceiveEnabled = 0U;
|
||||
}
|
||||
}
|
||||
|
||||
// Disable UART Transmit
|
||||
static void UART_Transmit_Disable (void) {
|
||||
if (UartTransmitEnabled != 0U) {
|
||||
pUSART->Control(ARM_USART_ABORT_SEND, 0U);
|
||||
pUSART->Control(ARM_USART_CONTROL_TX, 0U);
|
||||
UartTransmitActive = 0U;
|
||||
UartTransmitEnabled = 0U;
|
||||
}
|
||||
}
|
||||
|
||||
// Flush UART Receive buffer
|
||||
static void UART_Receive_Flush (void) {
|
||||
pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U);
|
||||
UartRxIndexI = 0U;
|
||||
UartRxIndexO = 0U;
|
||||
if (UartReceiveEnabled != 0U) {
|
||||
UART_Receive();
|
||||
}
|
||||
}
|
||||
|
||||
// Flush UART Transmit buffer
|
||||
static void UART_Transmit_Flush (void) {
|
||||
pUSART->Control(ARM_USART_ABORT_SEND, 0U);
|
||||
UartTransmitActive = 0U;
|
||||
UartTxIndexI = 0U;
|
||||
UartTxIndexO = 0U;
|
||||
UartTxNum = 0U;
|
||||
}
|
||||
|
||||
// Receive data from target via UART
|
||||
static void UART_Receive (void) {
|
||||
uint32_t index;
|
||||
|
||||
index = UartRxIndexI & (DAP_UART_RX_BUFFER_SIZE - 1U);
|
||||
pUSART->Receive(&UartRxBuf[index], UART_RX_BLOCK_SIZE);
|
||||
}
|
||||
|
||||
// Transmit available data to target via UART
|
||||
static void UART_Transmit (void) {
|
||||
uint32_t count;
|
||||
uint32_t index;
|
||||
|
||||
count = UartTxIndexI - UartTxIndexO;
|
||||
index = UartTxIndexO & (DAP_UART_TX_BUFFER_SIZE - 1U);
|
||||
|
||||
if (count != 0U) {
|
||||
if ((index + count) <= DAP_UART_TX_BUFFER_SIZE) {
|
||||
UartTxNum = count;
|
||||
} else {
|
||||
UartTxNum = DAP_UART_TX_BUFFER_SIZE - index;
|
||||
}
|
||||
UartTransmitActive = 1U;
|
||||
pUSART->Send(&UartTxBuf[index], UartTxNum);
|
||||
}
|
||||
}
|
||||
|
||||
// Process UART Transport command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t UART_Transport (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t transport;
|
||||
uint8_t ret = DAP_ERROR;
|
||||
|
||||
transport = *request;
|
||||
switch (transport) {
|
||||
case DAP_UART_TRANSPORT_NONE:
|
||||
switch (UartTransport) {
|
||||
case DAP_UART_TRANSPORT_NONE:
|
||||
ret = DAP_OK;
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_USB_COM_PORT:
|
||||
#if (DAP_UART_USB_COM_PORT != 0)
|
||||
USB_COM_PORT_Activate(0U);
|
||||
UartTransport = DAP_UART_TRANSPORT_NONE;
|
||||
ret = DAP_OK;
|
||||
#endif
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_DAP_COMMAND:
|
||||
UART_Receive_Disable();
|
||||
UART_Transmit_Disable();
|
||||
UART_Uninit();
|
||||
UartTransport = DAP_UART_TRANSPORT_NONE;
|
||||
ret= DAP_OK;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_USB_COM_PORT:
|
||||
switch (UartTransport) {
|
||||
case DAP_UART_TRANSPORT_NONE:
|
||||
#if (DAP_UART_USB_COM_PORT != 0)
|
||||
if (USB_COM_PORT_Activate(1U) == 0U) {
|
||||
UartTransport = DAP_UART_TRANSPORT_USB_COM_PORT;
|
||||
ret = DAP_OK;
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_USB_COM_PORT:
|
||||
ret = DAP_OK;
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_DAP_COMMAND:
|
||||
UART_Receive_Disable();
|
||||
UART_Transmit_Disable();
|
||||
UART_Uninit();
|
||||
UartTransport = DAP_UART_TRANSPORT_NONE;
|
||||
#if (DAP_UART_USB_COM_PORT != 0)
|
||||
if (USB_COM_PORT_Activate(1U) == 0U) {
|
||||
UartTransport = DAP_UART_TRANSPORT_USB_COM_PORT;
|
||||
ret = DAP_OK;
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_DAP_COMMAND:
|
||||
switch (UartTransport) {
|
||||
case DAP_UART_TRANSPORT_NONE:
|
||||
ret = UART_Init();
|
||||
if (ret == DAP_OK) {
|
||||
UartTransport = DAP_UART_TRANSPORT_DAP_COMMAND;
|
||||
}
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_USB_COM_PORT:
|
||||
#if (DAP_UART_USB_COM_PORT != 0)
|
||||
USB_COM_PORT_Activate(0U);
|
||||
UartTransport = DAP_UART_TRANSPORT_NONE;
|
||||
#endif
|
||||
ret = UART_Init();
|
||||
if (ret == DAP_OK) {
|
||||
UartTransport = DAP_UART_TRANSPORT_DAP_COMMAND;
|
||||
}
|
||||
break;
|
||||
case DAP_UART_TRANSPORT_DAP_COMMAND:
|
||||
ret = DAP_OK;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
*response = ret;
|
||||
|
||||
return ((1U << 16) | 1U);
|
||||
}
|
||||
|
||||
// Process UART Configure command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t UART_Configure (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t control, status;
|
||||
uint32_t baudrate;
|
||||
int32_t result;
|
||||
|
||||
if (UartTransport != DAP_UART_TRANSPORT_DAP_COMMAND) {
|
||||
status = DAP_UART_CFG_ERROR_DATA_BITS |
|
||||
DAP_UART_CFG_ERROR_PARITY |
|
||||
DAP_UART_CFG_ERROR_STOP_BITS;
|
||||
baudrate = 0U; // baudrate error
|
||||
} else {
|
||||
|
||||
status = 0U;
|
||||
control = *request;
|
||||
baudrate = (uint32_t)(*(request+1) << 0) |
|
||||
(uint32_t)(*(request+2) << 8) |
|
||||
(uint32_t)(*(request+3) << 16) |
|
||||
(uint32_t)(*(request+4) << 24);
|
||||
|
||||
result = pUSART->Control(control |
|
||||
ARM_USART_MODE_ASYNCHRONOUS |
|
||||
ARM_USART_FLOW_CONTROL_NONE,
|
||||
baudrate);
|
||||
if (result == ARM_DRIVER_OK) {
|
||||
UartConfigured = 1U;
|
||||
} else {
|
||||
UartConfigured = 0U;
|
||||
switch (result) {
|
||||
case ARM_USART_ERROR_BAUDRATE:
|
||||
status = 0U;
|
||||
baudrate = 0U;
|
||||
break;
|
||||
case ARM_USART_ERROR_DATA_BITS:
|
||||
status = DAP_UART_CFG_ERROR_DATA_BITS;
|
||||
break;
|
||||
case ARM_USART_ERROR_PARITY:
|
||||
status = DAP_UART_CFG_ERROR_PARITY;
|
||||
break;
|
||||
case ARM_USART_ERROR_STOP_BITS:
|
||||
status = DAP_UART_CFG_ERROR_STOP_BITS;
|
||||
break;
|
||||
default:
|
||||
status = DAP_UART_CFG_ERROR_DATA_BITS |
|
||||
DAP_UART_CFG_ERROR_PARITY |
|
||||
DAP_UART_CFG_ERROR_STOP_BITS;
|
||||
baudrate = 0U;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
*response++ = status;
|
||||
*response++ = (uint8_t)(baudrate >> 0);
|
||||
*response++ = (uint8_t)(baudrate >> 8);
|
||||
*response++ = (uint8_t)(baudrate >> 16);
|
||||
*response = (uint8_t)(baudrate >> 24);
|
||||
|
||||
return ((5U << 16) | 5U);
|
||||
}
|
||||
|
||||
// Process UART Control command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t UART_Control (const uint8_t *request, uint8_t *response) {
|
||||
uint8_t control;
|
||||
uint8_t result;
|
||||
uint8_t ret = DAP_OK;
|
||||
|
||||
if (UartTransport != DAP_UART_TRANSPORT_DAP_COMMAND) {
|
||||
ret = DAP_ERROR;
|
||||
} else {
|
||||
|
||||
control = *request;
|
||||
|
||||
if ((control & DAP_UART_CONTROL_RX_DISABLE) != 0U) {
|
||||
// Receive disable
|
||||
UART_Receive_Disable();
|
||||
} else if ((control & DAP_UART_CONTROL_RX_ENABLE) != 0U) {
|
||||
// Receive enable
|
||||
if (UartConfigured != 0U) {
|
||||
result = UART_Receive_Enable();
|
||||
if (result != DAP_OK) {
|
||||
ret = DAP_ERROR;
|
||||
}
|
||||
} else {
|
||||
ret = DAP_ERROR;
|
||||
}
|
||||
}
|
||||
if ((control & DAP_UART_CONTROL_RX_BUF_FLUSH) != 0U) {
|
||||
UART_Receive_Flush();
|
||||
}
|
||||
|
||||
if ((control & DAP_UART_CONTROL_TX_DISABLE) != 0U) {
|
||||
// Transmit disable
|
||||
UART_Transmit_Disable();
|
||||
} else if ((control & DAP_UART_CONTROL_TX_ENABLE) != 0U) {
|
||||
// Transmit enable
|
||||
if (UartConfigured != 0U) {
|
||||
result = UART_Transmit_Enable();
|
||||
if (result != DAP_OK) {
|
||||
ret = DAP_ERROR;
|
||||
}
|
||||
} else {
|
||||
ret = DAP_ERROR;
|
||||
}
|
||||
}
|
||||
if ((control & DAP_UART_CONTROL_TX_BUF_FLUSH) != 0U) {
|
||||
UART_Transmit_Flush();
|
||||
}
|
||||
}
|
||||
|
||||
*response = ret;
|
||||
|
||||
return ((1U << 16) | 1U);
|
||||
}
|
||||
|
||||
// Process UART Status command and prepare response
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t UART_Status (uint8_t *response) {
|
||||
uint32_t rx_cnt, tx_cnt;
|
||||
uint32_t cnt;
|
||||
uint8_t status;
|
||||
|
||||
if ((UartTransport != DAP_UART_TRANSPORT_DAP_COMMAND) ||
|
||||
(UartConfigured == 0U)) {
|
||||
rx_cnt = 0U;
|
||||
tx_cnt = 0U;
|
||||
status = 0U;
|
||||
} else {
|
||||
|
||||
rx_cnt = UartRxIndexI - UartRxIndexO;
|
||||
rx_cnt += pUSART->GetRxCount();
|
||||
if (rx_cnt > (DAP_UART_RX_BUFFER_SIZE - (UART_RX_BLOCK_SIZE*2))) {
|
||||
// Overflow
|
||||
UartErrorRxDataLost = 1U;
|
||||
rx_cnt = (DAP_UART_RX_BUFFER_SIZE - (UART_RX_BLOCK_SIZE*2));
|
||||
UartRxIndexO = UartRxIndexI - rx_cnt;
|
||||
}
|
||||
|
||||
tx_cnt = UartTxIndexI - UartTxIndexO;
|
||||
cnt = pUSART->GetTxCount();
|
||||
if (UartTransmitActive != 0U) {
|
||||
tx_cnt -= cnt;
|
||||
}
|
||||
|
||||
status = UART_Get_Status();
|
||||
}
|
||||
|
||||
*response++ = status;
|
||||
*response++ = (uint8_t)(rx_cnt >> 0);
|
||||
*response++ = (uint8_t)(rx_cnt >> 8);
|
||||
*response++ = (uint8_t)(rx_cnt >> 16);
|
||||
*response++ = (uint8_t)(rx_cnt >> 24);
|
||||
*response++ = (uint8_t)(tx_cnt >> 0);
|
||||
*response++ = (uint8_t)(tx_cnt >> 8);
|
||||
*response++ = (uint8_t)(tx_cnt >> 16);
|
||||
*response = (uint8_t)(tx_cnt >> 24);
|
||||
|
||||
return ((0U << 16) | 9U);
|
||||
}
|
||||
|
||||
// Process UART Transfer command and prepare response
|
||||
// request: pointer to request data
|
||||
// response: pointer to response data
|
||||
// return: number of bytes in response (lower 16 bits)
|
||||
// number of bytes in request (upper 16 bits)
|
||||
uint32_t UART_Transfer (const uint8_t *request, uint8_t *response) {
|
||||
uint32_t rx_cnt, tx_cnt;
|
||||
uint32_t rx_num, tx_num;
|
||||
uint8_t *rx_data;
|
||||
const
|
||||
uint8_t *tx_data;
|
||||
uint32_t num;
|
||||
uint32_t index;
|
||||
uint8_t status;
|
||||
|
||||
if (UartTransport != DAP_UART_TRANSPORT_DAP_COMMAND) {
|
||||
status = 0U;
|
||||
rx_cnt = 0U;
|
||||
tx_cnt = 0U;
|
||||
} else {
|
||||
|
||||
// RX Data
|
||||
rx_cnt = ((uint32_t)(*(request+0) << 0) |
|
||||
(uint32_t)(*(request+1) << 8));
|
||||
|
||||
if (rx_cnt > (DAP_PACKET_SIZE - 6U)) {
|
||||
rx_cnt = (DAP_PACKET_SIZE - 6U);
|
||||
}
|
||||
rx_num = UartRxIndexI - UartRxIndexO;
|
||||
rx_num += pUSART->GetRxCount();
|
||||
if (rx_num > (DAP_UART_RX_BUFFER_SIZE - (UART_RX_BLOCK_SIZE*2))) {
|
||||
// Overflow
|
||||
UartErrorRxDataLost = 1U;
|
||||
rx_num = (DAP_UART_RX_BUFFER_SIZE - (UART_RX_BLOCK_SIZE*2));
|
||||
UartRxIndexO = UartRxIndexI - rx_num;
|
||||
}
|
||||
if (rx_cnt > rx_num) {
|
||||
rx_cnt = rx_num;
|
||||
}
|
||||
|
||||
rx_data = (response+5);
|
||||
index = UartRxIndexO & (DAP_UART_RX_BUFFER_SIZE - 1U);
|
||||
if ((index + rx_cnt) <= DAP_UART_RX_BUFFER_SIZE) {
|
||||
memcpy( rx_data, &UartRxBuf[index], rx_cnt);
|
||||
} else {
|
||||
num = DAP_UART_RX_BUFFER_SIZE - index;
|
||||
memcpy( rx_data, &UartRxBuf[index], num);
|
||||
memcpy(&rx_data[num], &UartRxBuf[0], rx_cnt - num);
|
||||
}
|
||||
UartRxIndexO += rx_cnt;
|
||||
|
||||
// TX Data
|
||||
tx_cnt = ((uint32_t)(*(request+2) << 0) |
|
||||
(uint32_t)(*(request+3) << 8));
|
||||
tx_data = (request+4);
|
||||
|
||||
if (tx_cnt > (DAP_PACKET_SIZE - 5U)) {
|
||||
tx_cnt = (DAP_PACKET_SIZE - 5U);
|
||||
}
|
||||
tx_num = UartTxIndexI - UartTxIndexO;
|
||||
num = pUSART->GetTxCount();
|
||||
if (UartTransmitActive != 0U) {
|
||||
tx_num -= num;
|
||||
}
|
||||
if (tx_cnt > (DAP_UART_TX_BUFFER_SIZE - tx_num)) {
|
||||
tx_cnt = (DAP_UART_TX_BUFFER_SIZE - tx_num);
|
||||
}
|
||||
|
||||
index = UartTxIndexI & (DAP_UART_TX_BUFFER_SIZE - 1U);
|
||||
if ((index + tx_cnt) <= DAP_UART_TX_BUFFER_SIZE) {
|
||||
memcpy(&UartTxBuf[index], tx_data, tx_cnt);
|
||||
} else {
|
||||
num = DAP_UART_TX_BUFFER_SIZE - index;
|
||||
memcpy(&UartTxBuf[index], tx_data, num);
|
||||
memcpy(&UartTxBuf[0], &tx_data[num], tx_cnt - num);
|
||||
}
|
||||
UartTxIndexI += tx_cnt;
|
||||
|
||||
if (UartTransmitActive == 0U) {
|
||||
UART_Transmit();
|
||||
}
|
||||
|
||||
status = UART_Get_Status();
|
||||
}
|
||||
|
||||
*response++ = status;
|
||||
*response++ = (uint8_t)(tx_cnt >> 0);
|
||||
*response++ = (uint8_t)(tx_cnt >> 8);
|
||||
*response++ = (uint8_t)(rx_cnt >> 0);
|
||||
*response = (uint8_t)(rx_cnt >> 8);
|
||||
|
||||
return (((4U + tx_cnt) << 16) | (5U + rx_cnt));
|
||||
}
|
||||
|
||||
#endif /* DAP_UART */
|
Reference in New Issue
Block a user