Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
SWO.c
00001 /* 00002 * Copyright (c) 2013-2017 ARM Limited. All rights reserved. 00003 * 00004 * SPDX-License-Identifier: Apache-2.0 00005 * 00006 * Licensed under the Apache License, Version 2.0 (the License); you may 00007 * not use this file except in compliance with the License. 00008 * You may obtain a copy of the License at 00009 * 00010 * www.apache.org/licenses/LICENSE-2.0 00011 * 00012 * Unless required by applicable law or agreed to in writing, software 00013 * distributed under the License is distributed on an AS IS BASIS, WITHOUT 00014 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00015 * See the License for the specific language governing permissions and 00016 * limitations under the License. 00017 * 00018 * ---------------------------------------------------------------------- 00019 * 00020 * $Date: 1. December 2017 00021 * $Revision: V2.0.0 00022 * 00023 * Project: CMSIS-DAP Source 00024 * Title: SWO.c CMSIS-DAP SWO I/O 00025 * 00026 *---------------------------------------------------------------------------*/ 00027 00028 #include "DAP_config.h" 00029 #include "DAP.h" 00030 #if (SWO_UART != 0) 00031 #include "Driver_USART.h" 00032 #endif 00033 #if (SWO_STREAM != 0) 00034 #include "cmsis_os2.h" 00035 #endif 00036 00037 #if (SWO_STREAM != 0) 00038 #ifdef DAP_FW_V1 00039 #error "SWO Streaming Trace not supported in DAP V1!" 00040 #endif 00041 #endif 00042 00043 #if (SWO_UART != 0) 00044 00045 #ifndef SWO_USART_PORT 00046 #define SWO_USART_PORT 0 /* USART Port Number */ 00047 #endif 00048 00049 // USART Driver 00050 #define _USART_Driver_(n) Driver_USART##n 00051 #define USART_Driver_(n) _USART_Driver_(n) 00052 extern ARM_DRIVER_USART USART_Driver_(SWO_USART_PORT); 00053 #define pUSART (&USART_Driver_(SWO_USART_PORT)) 00054 00055 static uint8_t USART_Ready = 0U; 00056 00057 #endif /* (SWO_UART != 0) */ 00058 00059 00060 #if ((SWO_UART != 0) || (SWO_MANCHESTER != 0)) 00061 00062 00063 #define SWO_STREAM_TIMEOUT 50U /* Stream timeout in ms */ 00064 00065 #define USB_BLOCK_SIZE 512U /* USB Block Size */ 00066 #define TRACE_BLOCK_SIZE 64U /* Trace Block Size (2^n: 32...512) */ 00067 00068 // Trace State 00069 static uint8_t TraceTransport = 0U; /* Trace Transport */ 00070 static uint8_t TraceMode = 0U; /* Trace Mode */ 00071 static uint8_t TraceStatus = 0U; /* Trace Status without Errors */ 00072 static uint8_t TraceError[2] = {0U, 0U}; /* Trace Error flags (banked) */ 00073 static uint8_t TraceError_n = 0U; /* Active Trace Error bank */ 00074 00075 // Trace Buffer 00076 static uint8_t TraceBuf[SWO_BUFFER_SIZE]; /* Trace Buffer (must be 2^n) */ 00077 static volatile uint32_t TraceIndexI = 0U; /* Incoming Trace Index */ 00078 static volatile uint32_t TraceIndexO = 0U; /* Outgoing Trace Index */ 00079 static volatile uint8_t TraceUpdate; /* Trace Update Flag */ 00080 static uint32_t TraceBlockSize; /* Current Trace Block Size */ 00081 00082 #if (TIMESTAMP_CLOCK != 0U) 00083 // Trace Timestamp 00084 static volatile struct { 00085 uint32_t index; 00086 uint32_t tick; 00087 } TraceTimestamp; 00088 #endif 00089 00090 // Trace Helper functions 00091 static void ClearTrace (void); 00092 static void ResumeTrace (void); 00093 static uint32_t GetTraceCount (void); 00094 static uint8_t GetTraceStatus (void); 00095 static void SetTraceError (uint8_t flag); 00096 00097 #if (SWO_STREAM != 0) 00098 extern osThreadId_t SWO_ThreadId; 00099 static volatile uint8_t TransferBusy = 0U; /* Transfer Busy Flag */ 00100 static uint32_t TransferSize; /* Current Transfer Size */ 00101 #endif 00102 00103 00104 #if (SWO_UART != 0) 00105 00106 // USART Driver Callback function 00107 // event: event mask 00108 static void USART_Callback (uint32_t event) { 00109 uint32_t index_i; 00110 uint32_t index_o; 00111 uint32_t count; 00112 uint32_t num; 00113 00114 if (event & ARM_USART_EVENT_RECEIVE_COMPLETE) { 00115 #if (TIMESTAMP_CLOCK != 0U) 00116 TraceTimestamp.tick = TIMESTAMP_GET(); 00117 #endif 00118 index_o = TraceIndexO; 00119 index_i = TraceIndexI; 00120 index_i += TraceBlockSize; 00121 TraceIndexI = index_i; 00122 #if (TIMESTAMP_CLOCK != 0U) 00123 TraceTimestamp.index = index_i; 00124 #endif 00125 num = TRACE_BLOCK_SIZE - (index_i & (TRACE_BLOCK_SIZE - 1U)); 00126 count = index_i - index_o; 00127 if (count <= (SWO_BUFFER_SIZE - num)) { 00128 index_i &= SWO_BUFFER_SIZE - 1U; 00129 TraceBlockSize = num; 00130 pUSART->Receive(&TraceBuf[index_i], num); 00131 } else { 00132 TraceStatus = DAP_SWO_CAPTURE_ACTIVE | DAP_SWO_CAPTURE_PAUSED; 00133 } 00134 TraceUpdate = 1U; 00135 #if (SWO_STREAM != 0) 00136 if (TraceTransport == 2U) { 00137 if (count >= (USB_BLOCK_SIZE - (index_o & (USB_BLOCK_SIZE - 1U)))) { 00138 osThreadFlagsSet(SWO_ThreadId, 1U); 00139 } 00140 } 00141 #endif 00142 } 00143 if (event & ARM_USART_EVENT_RX_OVERFLOW) { 00144 SetTraceError(DAP_SWO_BUFFER_OVERRUN); 00145 } 00146 if (event & (ARM_USART_EVENT_RX_BREAK | 00147 ARM_USART_EVENT_RX_FRAMING_ERROR | 00148 ARM_USART_EVENT_RX_PARITY_ERROR)) { 00149 SetTraceError(DAP_SWO_STREAM_ERROR); 00150 } 00151 } 00152 00153 // Enable or disable UART SWO Mode 00154 // enable: enable flag 00155 // return: 1 - Success, 0 - Error 00156 __WEAK uint32_t UART_SWO_Mode (uint32_t enable) { 00157 int32_t status; 00158 00159 USART_Ready = 0U; 00160 00161 if (enable != 0U) { 00162 status = pUSART->Initialize(USART_Callback); 00163 if (status != ARM_DRIVER_OK) { 00164 return (0U); 00165 } 00166 status = pUSART->PowerControl(ARM_POWER_FULL); 00167 if (status != ARM_DRIVER_OK) { 00168 pUSART->Uninitialize(); 00169 return (0U); 00170 } 00171 } else { 00172 pUSART->Control(ARM_USART_CONTROL_RX, 0U); 00173 pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U); 00174 pUSART->PowerControl(ARM_POWER_OFF); 00175 pUSART->Uninitialize(); 00176 } 00177 return (1U); 00178 } 00179 00180 // Configure UART SWO Baudrate 00181 // baudrate: requested baudrate 00182 // return: actual baudrate or 0 when not configured 00183 __WEAK uint32_t UART_SWO_Baudrate (uint32_t baudrate) { 00184 int32_t status; 00185 uint32_t index; 00186 uint32_t num; 00187 00188 if (baudrate > SWO_UART_MAX_BAUDRATE) { 00189 baudrate = SWO_UART_MAX_BAUDRATE; 00190 } 00191 00192 if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) { 00193 pUSART->Control(ARM_USART_CONTROL_RX, 0U); 00194 if (pUSART->GetStatus().rx_busy) { 00195 TraceIndexI += pUSART->GetRxCount(); 00196 pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U); 00197 } 00198 } 00199 00200 status = pUSART->Control(ARM_USART_MODE_ASYNCHRONOUS | 00201 ARM_USART_DATA_BITS_8 | 00202 ARM_USART_PARITY_NONE | 00203 ARM_USART_STOP_BITS_1, 00204 baudrate); 00205 00206 if (status == ARM_DRIVER_OK) { 00207 USART_Ready = 1U; 00208 } else { 00209 USART_Ready = 0U; 00210 return (0U); 00211 } 00212 00213 if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) { 00214 if ((TraceStatus & DAP_SWO_CAPTURE_PAUSED) == 0U) { 00215 index = TraceIndexI & (SWO_BUFFER_SIZE - 1U); 00216 num = TRACE_BLOCK_SIZE - (index & (TRACE_BLOCK_SIZE - 1U)); 00217 TraceBlockSize = num; 00218 pUSART->Receive(&TraceBuf[index], num); 00219 } 00220 pUSART->Control(ARM_USART_CONTROL_RX, 1U); 00221 } 00222 00223 return (baudrate); 00224 } 00225 00226 // Control UART SWO Capture 00227 // active: active flag 00228 // return: 1 - Success, 0 - Error 00229 __WEAK uint32_t UART_SWO_Control (uint32_t active) { 00230 int32_t status; 00231 00232 if (active) { 00233 if (!USART_Ready) { 00234 return (0U); 00235 } 00236 TraceBlockSize = 1U; 00237 status = pUSART->Receive(&TraceBuf[0], 1U); 00238 if (status != ARM_DRIVER_OK) { 00239 return (0U); 00240 } 00241 status = pUSART->Control(ARM_USART_CONTROL_RX, 1U); 00242 if (status != ARM_DRIVER_OK) { 00243 return (0U); 00244 } 00245 } else { 00246 pUSART->Control(ARM_USART_CONTROL_RX, 0U); 00247 if (pUSART->GetStatus().rx_busy) { 00248 TraceIndexI += pUSART->GetRxCount(); 00249 pUSART->Control(ARM_USART_ABORT_RECEIVE, 0U); 00250 } 00251 } 00252 return (1U); 00253 } 00254 00255 // Start UART SWO Capture 00256 // buf: pointer to buffer for capturing 00257 // num: number of bytes to capture 00258 __WEAK void UART_SWO_Capture (uint8_t *buf, uint32_t num) { 00259 TraceBlockSize = num; 00260 pUSART->Receive(buf, num); 00261 } 00262 00263 // Get UART SWO Pending Trace Count 00264 // return: number of pending trace data bytes 00265 __WEAK uint32_t UART_SWO_GetCount (void) { 00266 uint32_t count; 00267 00268 if (pUSART->GetStatus().rx_busy) { 00269 count = pUSART->GetRxCount(); 00270 } else { 00271 count = 0U; 00272 } 00273 return (count); 00274 } 00275 00276 #endif /* (SWO_UART != 0) */ 00277 00278 00279 #if (SWO_MANCHESTER != 0) 00280 00281 // Enable or disable Manchester SWO Mode 00282 // enable: enable flag 00283 // return: 1 - Success, 0 - Error 00284 __WEAK uint32_t Manchester_SWO_Mode (uint32_t enable) { 00285 return (0U); 00286 } 00287 00288 // Configure Manchester SWO Baudrate 00289 // baudrate: requested baudrate 00290 // return: actual baudrate or 0 when not configured 00291 __WEAK uint32_t Manchester_SWO_Baudrate (uint32_t baudrate) { 00292 return (0U); 00293 } 00294 00295 // Control Manchester SWO Capture 00296 // active: active flag 00297 // return: 1 - Success, 0 - Error 00298 __WEAK uint32_t Manchester_SWO_Control (uint32_t active) { 00299 return (0U); 00300 } 00301 00302 // Start Manchester SWO Capture 00303 // buf: pointer to buffer for capturing 00304 // num: number of bytes to capture 00305 __WEAK void Manchester_SWO_Capture (uint8_t *buf, uint32_t num) { 00306 } 00307 00308 // Get Manchester SWO Pending Trace Count 00309 // return: number of pending trace data bytes 00310 __WEAK uint32_t Manchester_SWO_GetCount (void) { 00311 } 00312 00313 #endif /* (SWO_MANCHESTER != 0) */ 00314 00315 00316 // Clear Trace Errors and Data 00317 static void ClearTrace (void) { 00318 00319 #if (SWO_STREAM != 0) 00320 if (TraceTransport == 2U) { 00321 if (TransferBusy != 0U) { 00322 SWO_AbortTransfer(); 00323 TransferBusy = 0U; 00324 } 00325 } 00326 #endif 00327 00328 TraceError[0] = 0U; 00329 TraceError[1] = 0U; 00330 TraceError_n = 0U; 00331 TraceIndexI = 0U; 00332 TraceIndexO = 0U; 00333 00334 #if (TIMESTAMP_CLOCK != 0U) 00335 TraceTimestamp.index = 0U; 00336 TraceTimestamp.tick = 0U; 00337 #endif 00338 } 00339 00340 // Resume Trace Capture 00341 static void ResumeTrace (void) { 00342 uint32_t index_i; 00343 uint32_t index_o; 00344 00345 if (TraceStatus == (DAP_SWO_CAPTURE_ACTIVE | DAP_SWO_CAPTURE_PAUSED)) { 00346 index_i = TraceIndexI; 00347 index_o = TraceIndexO; 00348 if ((index_i - index_o) < SWO_BUFFER_SIZE) { 00349 index_i &= SWO_BUFFER_SIZE - 1U; 00350 switch (TraceMode) { 00351 #if (SWO_UART != 0) 00352 case DAP_SWO_UART: 00353 TraceStatus = DAP_SWO_CAPTURE_ACTIVE; 00354 UART_SWO_Capture(&TraceBuf[index_i], 1U); 00355 break; 00356 #endif 00357 #if (SWO_MANCHESTER != 0) 00358 case DAP_SWO_MANCHESTER: 00359 TraceStatus = DAP_SWO_CAPTURE_ACTIVE; 00360 Manchester_SWO_Capture(&TraceBuf[index_i], 1U); 00361 break; 00362 #endif 00363 default: 00364 break; 00365 } 00366 } 00367 } 00368 } 00369 00370 // Get Trace Count 00371 // return: number of available data bytes in trace buffer 00372 static uint32_t GetTraceCount (void) { 00373 uint32_t count; 00374 00375 if (TraceStatus == DAP_SWO_CAPTURE_ACTIVE) { 00376 do { 00377 TraceUpdate = 0U; 00378 count = TraceIndexI - TraceIndexO; 00379 switch (TraceMode) { 00380 #if (SWO_UART != 0) 00381 case DAP_SWO_UART: 00382 count += UART_SWO_GetCount(); 00383 break; 00384 #endif 00385 #if (SWO_MANCHESTER != 0) 00386 case DAP_SWO_MANCHESTER: 00387 count += Manchester_SWO_GetCount(); 00388 break; 00389 #endif 00390 default: 00391 break; 00392 } 00393 } while (TraceUpdate != 0U); 00394 } else { 00395 count = TraceIndexI - TraceIndexO; 00396 } 00397 00398 return (count); 00399 } 00400 00401 // Get Trace Status (clear Error flags) 00402 // return: Trace Status (Active flag and Error flags) 00403 static uint8_t GetTraceStatus (void) { 00404 uint8_t status; 00405 uint32_t n; 00406 00407 n = TraceError_n; 00408 TraceError_n ^= 1U; 00409 status = TraceStatus | TraceError[n]; 00410 TraceError[n] = 0U; 00411 00412 return (status); 00413 } 00414 00415 // Set Trace Error flag(s) 00416 // flag: error flag(s) to set 00417 static void SetTraceError (uint8_t flag) { 00418 TraceError[TraceError_n] |= flag; 00419 } 00420 00421 00422 // Process SWO Transport command and prepare response 00423 // request: pointer to request data 00424 // response: pointer to response data 00425 // return: number of bytes in response (lower 16 bits) 00426 // number of bytes in request (upper 16 bits) 00427 uint32_t SWO_Transport (const uint8_t *request, uint8_t *response) { 00428 uint8_t transport; 00429 uint32_t result; 00430 00431 if ((TraceStatus & DAP_SWO_CAPTURE_ACTIVE) == 0U) { 00432 transport = *request; 00433 switch (transport) { 00434 case 0U: 00435 case 1U: 00436 #if (SWO_STREAM != 0) 00437 case 2U: 00438 #endif 00439 TraceTransport = transport; 00440 result = 1U; 00441 break; 00442 default: 00443 result = 0U; 00444 break; 00445 } 00446 } else { 00447 result = 0U; 00448 } 00449 00450 if (result != 0U) { 00451 *response = DAP_OK; 00452 } else { 00453 *response = DAP_ERROR; 00454 } 00455 00456 return ((1U << 16) | 1U); 00457 } 00458 00459 00460 // Process SWO Mode command and prepare response 00461 // request: pointer to request data 00462 // response: pointer to response data 00463 // return: number of bytes in response (lower 16 bits) 00464 // number of bytes in request (upper 16 bits) 00465 uint32_t SWO_Mode (const uint8_t *request, uint8_t *response) { 00466 uint8_t mode; 00467 uint32_t result; 00468 00469 mode = *request; 00470 00471 switch (TraceMode) { 00472 #if (SWO_UART != 0) 00473 case DAP_SWO_UART: 00474 UART_SWO_Mode(0U); 00475 break; 00476 #endif 00477 #if (SWO_MANCHESTER != 0) 00478 case DAP_SWO_MANCHESTER: 00479 Manchester_SWO_Mode(0U); 00480 break; 00481 #endif 00482 default: 00483 break; 00484 } 00485 00486 switch (mode) { 00487 case DAP_SWO_OFF: 00488 result = 1U; 00489 break; 00490 #if (SWO_UART != 0) 00491 case DAP_SWO_UART: 00492 result = UART_SWO_Mode(1U); 00493 break; 00494 #endif 00495 #if (SWO_MANCHESTER != 0) 00496 case DAP_SWO_MANCHESTER: 00497 result = Manchester_SWO_Mode(1U); 00498 break; 00499 #endif 00500 default: 00501 result = 0U; 00502 break; 00503 } 00504 if (result != 0U) { 00505 TraceMode = mode; 00506 } else { 00507 TraceMode = DAP_SWO_OFF; 00508 } 00509 00510 TraceStatus = 0U; 00511 00512 if (result != 0U) { 00513 *response = DAP_OK; 00514 } else { 00515 *response = DAP_ERROR; 00516 } 00517 00518 return ((1U << 16) | 1U); 00519 } 00520 00521 00522 // Process SWO Baudrate command and prepare response 00523 // request: pointer to request data 00524 // response: pointer to response data 00525 // return: number of bytes in response (lower 16 bits) 00526 // number of bytes in request (upper 16 bits) 00527 uint32_t SWO_Baudrate (const uint8_t *request, uint8_t *response) { 00528 uint32_t baudrate; 00529 00530 baudrate = (uint32_t)(*(request+0) << 0) | 00531 (uint32_t)(*(request+1) << 8) | 00532 (uint32_t)(*(request+2) << 16) | 00533 (uint32_t)(*(request+3) << 24); 00534 00535 switch (TraceMode) { 00536 #if (SWO_UART != 0) 00537 case DAP_SWO_UART: 00538 baudrate = UART_SWO_Baudrate(baudrate); 00539 break; 00540 #endif 00541 #if (SWO_MANCHESTER != 0) 00542 case DAP_SWO_MANCHESTER: 00543 baudrate = Manchester_SWO_Baudrate(baudrate); 00544 break; 00545 #endif 00546 default: 00547 baudrate = 0U; 00548 break; 00549 } 00550 00551 if (baudrate == 0U) { 00552 TraceStatus = 0U; 00553 } 00554 00555 *response++ = (uint8_t)(baudrate >> 0); 00556 *response++ = (uint8_t)(baudrate >> 8); 00557 *response++ = (uint8_t)(baudrate >> 16); 00558 *response = (uint8_t)(baudrate >> 24); 00559 00560 return ((4U << 16) | 4U); 00561 } 00562 00563 00564 // Process SWO Control command and prepare response 00565 // request: pointer to request data 00566 // response: pointer to response data 00567 // return: number of bytes in response (lower 16 bits) 00568 // number of bytes in request (upper 16 bits) 00569 uint32_t SWO_Control (const uint8_t *request, uint8_t *response) { 00570 uint8_t active; 00571 uint32_t result; 00572 00573 active = *request & DAP_SWO_CAPTURE_ACTIVE; 00574 00575 if (active != (TraceStatus & DAP_SWO_CAPTURE_ACTIVE)) { 00576 if (active) { 00577 ClearTrace(); 00578 } 00579 switch (TraceMode) { 00580 #if (SWO_UART != 0) 00581 case DAP_SWO_UART: 00582 result = UART_SWO_Control(active); 00583 break; 00584 #endif 00585 #if (SWO_MANCHESTER != 0) 00586 case DAP_SWO_MANCHESTER: 00587 result = Manchester_SWO_Control(active); 00588 break; 00589 #endif 00590 default: 00591 result = 0U; 00592 break; 00593 } 00594 if (result != 0U) { 00595 TraceStatus = active; 00596 #if (SWO_STREAM != 0) 00597 if (TraceTransport == 2U) { 00598 osThreadFlagsSet(SWO_ThreadId, 1U); 00599 } 00600 #endif 00601 } 00602 } else { 00603 result = 1U; 00604 } 00605 00606 if (result != 0U) { 00607 *response = DAP_OK; 00608 } else { 00609 *response = DAP_ERROR; 00610 } 00611 00612 return ((1U << 16) | 1U); 00613 } 00614 00615 00616 // Process SWO Status command and prepare response 00617 // response: pointer to response data 00618 // return: number of bytes in response 00619 uint32_t SWO_Status (uint8_t *response) { 00620 uint8_t status; 00621 uint32_t count; 00622 00623 status = GetTraceStatus(); 00624 count = GetTraceCount(); 00625 00626 *response++ = status; 00627 *response++ = (uint8_t)(count >> 0); 00628 *response++ = (uint8_t)(count >> 8); 00629 *response++ = (uint8_t)(count >> 16); 00630 *response = (uint8_t)(count >> 24); 00631 00632 return (5U); 00633 } 00634 00635 00636 // Process SWO Extended Status command and prepare response 00637 // request: pointer to request data 00638 // response: pointer to response data 00639 // return: number of bytes in response (lower 16 bits) 00640 // number of bytes in request (upper 16 bits) 00641 uint32_t SWO_ExtendedStatus (const uint8_t *request, uint8_t *response) { 00642 uint8_t cmd; 00643 uint8_t status; 00644 uint32_t count; 00645 #if (TIMESTAMP_CLOCK != 0U) 00646 uint32_t index; 00647 uint32_t tick; 00648 #endif 00649 uint32_t num; 00650 00651 num = 0U; 00652 cmd = *request; 00653 00654 if (cmd & 0x01U) { 00655 status = GetTraceStatus(); 00656 *response++ = status; 00657 num += 1U; 00658 } 00659 00660 if (cmd & 0x02U) { 00661 count = GetTraceCount(); 00662 *response++ = (uint8_t)(count >> 0); 00663 *response++ = (uint8_t)(count >> 8); 00664 *response++ = (uint8_t)(count >> 16); 00665 *response++ = (uint8_t)(count >> 24); 00666 num += 4U; 00667 } 00668 00669 #if (TIMESTAMP_CLOCK != 0U) 00670 if (cmd & 0x04U) { 00671 do { 00672 TraceUpdate = 0U; 00673 index = TraceTimestamp.index; 00674 tick = TraceTimestamp.tick; 00675 } while (TraceUpdate != 0U); 00676 *response++ = (uint8_t)(index >> 0); 00677 *response++ = (uint8_t)(index >> 8); 00678 *response++ = (uint8_t)(index >> 16); 00679 *response++ = (uint8_t)(index >> 24); 00680 *response++ = (uint8_t)(tick >> 0); 00681 *response++ = (uint8_t)(tick >> 8); 00682 *response++ = (uint8_t)(tick >> 16); 00683 *response++ = (uint8_t)(tick >> 24); 00684 num += 4U; 00685 } 00686 #endif 00687 00688 return ((1U << 16) | num); 00689 } 00690 00691 00692 // Process SWO Data command and prepare response 00693 // request: pointer to request data 00694 // response: pointer to response data 00695 // return: number of bytes in response (lower 16 bits) 00696 // number of bytes in request (upper 16 bits) 00697 uint32_t SWO_Data (const uint8_t *request, uint8_t *response) { 00698 uint8_t status; 00699 uint32_t count; 00700 uint32_t index; 00701 uint32_t n, i; 00702 00703 status = GetTraceStatus(); 00704 count = GetTraceCount(); 00705 00706 if (TraceTransport == 1U) { 00707 n = (uint32_t)(*(request+0) << 0) | 00708 (uint32_t)(*(request+1) << 8); 00709 if (n > (DAP_PACKET_SIZE - 4U)) { 00710 n = DAP_PACKET_SIZE - 4U; 00711 } 00712 if (count > n) { 00713 count = n; 00714 } 00715 } else { 00716 count = 0U; 00717 } 00718 00719 *response++ = status; 00720 *response++ = (uint8_t)(count >> 0); 00721 *response++ = (uint8_t)(count >> 8); 00722 00723 if (TraceTransport == 1U) { 00724 index = TraceIndexO; 00725 for (i = index, n = count; n; n--) { 00726 i &= SWO_BUFFER_SIZE - 1U; 00727 *response++ = TraceBuf[i++]; 00728 } 00729 TraceIndexO = index + count; 00730 ResumeTrace(); 00731 } 00732 00733 return ((2U << 16) | (3U + count)); 00734 } 00735 00736 00737 #if (SWO_STREAM != 0) 00738 00739 // SWO Data Transfer complete callback 00740 void SWO_TransferComplete (void) { 00741 TraceIndexO += TransferSize; 00742 TransferBusy = 0U; 00743 ResumeTrace(); 00744 osThreadFlagsSet(SWO_ThreadId, 1U); 00745 } 00746 00747 // SWO Thread 00748 __NO_RETURN void SWO_Thread (void *argument) { 00749 uint32_t timeout; 00750 uint32_t flags; 00751 uint32_t count; 00752 uint32_t index; 00753 uint32_t i, n; 00754 (void) argument; 00755 00756 timeout = osWaitForever; 00757 00758 for (;;) { 00759 flags = osThreadFlagsWait(1U, osFlagsWaitAny, timeout); 00760 if (TraceStatus & DAP_SWO_CAPTURE_ACTIVE) { 00761 timeout = SWO_STREAM_TIMEOUT; 00762 } else { 00763 timeout = osWaitForever; 00764 flags = osFlagsErrorTimeout; 00765 } 00766 if (TransferBusy == 0U) { 00767 count = GetTraceCount(); 00768 if (count != 0U) { 00769 index = TraceIndexO & (SWO_BUFFER_SIZE - 1U); 00770 n = SWO_BUFFER_SIZE - index; 00771 if (count > n) { 00772 count = n; 00773 } 00774 if (flags != osFlagsErrorTimeout) { 00775 i = index & (USB_BLOCK_SIZE - 1U); 00776 if (i == 0U) { 00777 count &= ~(USB_BLOCK_SIZE - 1U); 00778 } else { 00779 n = USB_BLOCK_SIZE - i; 00780 if (count >= n) { 00781 count = n; 00782 } else { 00783 count = 0U; 00784 } 00785 } 00786 } 00787 if (count != 0U) { 00788 TransferSize = count; 00789 TransferBusy = 1U; 00790 SWO_QueueTransfer(&TraceBuf[index], count); 00791 } 00792 } 00793 } 00794 } 00795 } 00796 00797 #endif /* (SWO_STREAM != 0) */ 00798 00799 00800 #endif /* ((SWO_UART != 0) || (SWO_MANCHESTER != 0)) */
Generated on Tue Jul 12 2022 15:37:24 by
1.7.2