1 /********************************************************************* 2 * SEGGER Microcontroller GmbH * 3 * The Embedded Experts * 4 ********************************************************************** 5 * * 6 * (c) 1995 - 2018 SEGGER Microcontroller GmbH * 7 * * 8 * www.segger.com Support: [email protected] * 9 * * 10 ********************************************************************** 11 * * 12 * SEGGER RTT * Real Time Transfer for embedded targets * 13 * * 14 ********************************************************************** 15 * * 16 * All rights reserved. * 17 * * 18 * SEGGER strongly recommends to not make any changes * 19 * to or modify the source code of this software in order to stay * 20 * compatible with the RTT protocol and J-Link. * 21 * * 22 * Redistribution and use in source and binary forms, with or * 23 * without modification, are permitted provided that the following * 24 * conditions are met: * 25 * * 26 * o Redistributions of source code must retain the above copyright * 27 * notice, this list of conditions and the following disclaimer. * 28 * * 29 * o Redistributions in binary form must reproduce the above * 30 * copyright notice, this list of conditions and the following * 31 * disclaimer in the documentation and/or other materials provided * 32 * with the distribution. * 33 * * 34 * o Neither the name of SEGGER Microcontroller GmbH * 35 * nor the names of its contributors may be used to endorse or * 36 * promote products derived from this software without specific * 37 * prior written permission. * 38 * * 39 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND * 40 * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, * 41 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF * 42 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * 43 * DISCLAIMED. IN NO EVENT SHALL SEGGER Microcontroller BE LIABLE FOR * 44 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * 45 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT * 46 * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; * 47 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * 48 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * 49 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE * 50 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH * 51 * DAMAGE. * 52 * * 53 ********************************************************************** 54 ---------------------------END-OF-HEADER------------------------------ 55 File : SEGGER_RTT_Syscalls_SES.c 56 Purpose : Reimplementation of printf, puts and __getchar using RTT 57 in SEGGER Embedded Studio. 58 To use RTT for printf output, include this file in your 59 application. 60 Revision: $Rev: 12804 $ 61 ---------------------------------------------------------------------- 62 */ 63 #if (defined __SES_ARM) || (defined __CROSSWORKS_ARM) 64 65 #include "SEGGER_RTT.h" 66 #include <stdarg.h> 67 #include <stdio.h> 68 #include "limits.h" 69 #include "__libc.h" 70 #include "__vfprintf.h" 71 72 /********************************************************************* 73 * 74 * Defines, configurable 75 * 76 ********************************************************************** 77 */ 78 // 79 // Select string formatting implementation. 80 // 81 // RTT printf formatting 82 // - Configurable stack usage. (SEGGER_RTT_PRINTF_BUFFER_SIZE in SEGGER_RTT_Conf.h) 83 // - No maximum string length. 84 // - Limited conversion specifiers and flags. (See SEGGER_RTT_printf.c) 85 // Standard library printf formatting 86 // - Configurable formatting capabilities. 87 // - Full conversion specifier and flag support. 88 // - Maximum string length has to be known or (slightly) slower character-wise output. 89 // 90 // #define PRINTF_USE_SEGGER_RTT_FORMATTING 0 // Use standard library formatting 91 // #define PRINTF_USE_SEGGER_RTT_FORMATTING 1 // Use RTT formatting 92 // 93 #ifndef PRINTF_USE_SEGGER_RTT_FORMATTING 94 #define PRINTF_USE_SEGGER_RTT_FORMATTING 0 95 #endif 96 // 97 // If using standard library formatting, 98 // select maximum output string buffer size or character-wise output. 99 // 100 // #define PRINTF_BUFFER_SIZE 0 // Use character-wise output 101 // #define PRINTF_BUFFER_SIZE 128 // Default maximum string length 102 // 103 #ifndef PRINTF_BUFFER_SIZE 104 #define PRINTF_BUFFER_SIZE 128 105 #endif 106 107 #if PRINTF_USE_SEGGER_RTT_FORMATTING // Use SEGGER RTT formatting implementation 108 /********************************************************************* 109 * 110 * Function prototypes 111 * 112 ********************************************************************** 113 */ 114 int SEGGER_RTT_vprintf(unsigned BufferIndex, const char * sFormat, va_list * pParamList); 115 116 /********************************************************************* 117 * 118 * Global functions, printf 119 * 120 ********************************************************************** 121 */ 122 /********************************************************************* 123 * 124 * printf() 125 * 126 * Function description 127 * print a formatted string using RTT and SEGGER RTT formatting. 128 */ 129 int printf(const char *fmt,...) { 130 int n; 131 va_list args; 132 133 va_start (args, fmt); 134 n = SEGGER_RTT_vprintf(0, fmt, &args); 135 va_end(args); 136 return n; 137 } 138 139 #elif PRINTF_BUFFER_SIZE == 0 // Use standard library formatting with character-wise output 140 141 /********************************************************************* 142 * 143 * Static functions 144 * 145 ********************************************************************** 146 */ 147 static int _putchar(int x, __printf_tag_ptr ctx) { 148 (void)ctx; 149 SEGGER_RTT_Write(0, (char *)&x, 1); 150 return x; 151 } 152 153 /********************************************************************* 154 * 155 * Global functions, printf 156 * 157 ********************************************************************** 158 */ 159 /********************************************************************* 160 * 161 * printf() 162 * 163 * Function description 164 * print a formatted string character-wise, using RTT and standard 165 * library formatting. 166 */ 167 int printf(const char *fmt, ...) { 168 int n; 169 va_list args; 170 __printf_t iod; 171 172 va_start(args, fmt); 173 iod.string = 0; 174 iod.maxchars = INT_MAX; 175 iod.output_fn = _putchar; 176 SEGGER_RTT_LOCK(); 177 n = __vfprintf(&iod, fmt, args); 178 SEGGER_RTT_UNLOCK(); 179 va_end(args); 180 return n; 181 } 182 183 #else // Use standard library formatting with static buffer 184 185 /********************************************************************* 186 * 187 * Global functions, printf 188 * 189 ********************************************************************** 190 */ 191 /********************************************************************* 192 * 193 * printf() 194 * 195 * Function description 196 * print a formatted string using RTT and standard library formatting. 197 */ 198 int printf(const char *fmt,...) { 199 int n; 200 char aBuffer[PRINTF_BUFFER_SIZE]; 201 va_list args; 202 203 va_start (args, fmt); 204 n = vsnprintf(aBuffer, sizeof(aBuffer), fmt, args); 205 if (n > (int)sizeof(aBuffer)) { 206 SEGGER_RTT_Write(0, aBuffer, sizeof(aBuffer)); 207 } else if (n > 0) { 208 SEGGER_RTT_Write(0, aBuffer, n); 209 } 210 va_end(args); 211 return n; 212 } 213 #endif 214 215 /********************************************************************* 216 * 217 * Global functions 218 * 219 ********************************************************************** 220 */ 221 /********************************************************************* 222 * 223 * puts() 224 * 225 * Function description 226 * print a string using RTT. 227 */ 228 int puts(const char *s) { 229 return SEGGER_RTT_WriteString(0, s); 230 } 231 232 /********************************************************************* 233 * 234 * __putchar() 235 * 236 * Function description 237 * Write one character via RTT. 238 */ 239 int __putchar(int x, __printf_tag_ptr ctx) { 240 (void)ctx; 241 SEGGER_RTT_Write(0, (char *)&x, 1); 242 return x; 243 } 244 245 /********************************************************************* 246 * 247 * __getchar() 248 * 249 * Function description 250 * Wait for and get a character via RTT. 251 */ 252 int __getchar() { 253 return SEGGER_RTT_WaitKey(); 254 } 255 256 #endif 257 /****** End Of File *************************************************/ 258