We have added chsprint to implement a minimal @p sprintf() like functionality with
output to a string.
Your feed back is appreciated.
How do I attach a patch file? I am getting The extension " " is not allowed for everything I have tried.
From 8a4411d184dc884a9a3e03a1a7fa54356d6d0dbd Mon Sep 17 00:00:00 2001
From: Timothy Webster <tdwebste@gmail.com>
Date: Sun, 1 Dec 2013 23:33:22 -0500
Subject: [PATCH] chibios sprint
chsprintf
This function implements a minimal @p sprintf() like functionality with
output to a string.
---
os/various/chprintf.c | 176 ++++++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 176 insertions(+)
diff --git a/os/various/chprintf.c b/os/various/chprintf.c
index 5d3d38e..0960eaa 100644
--- a/os/various/chprintf.c
+++ b/os/various/chprintf.c
@@ -259,4 +259,180 @@ unsigned_common:
}
}
+/**
+ * @brief Formatted string function.
+ * @details This function implements a minimal @p sprintf() like functionality
+ * with output to a string.
+ * The general parameters format is: %[-][width|*][.precision|*][l|L]p.
+ * The following parameter types (p) are supported:
+ * - <b>x</b> hexadecimal integer.
+ * - <b>X</b> hexadecimal long.
+ * - <b>o</b> octal integer.
+ * - <b>O</b> octal long.
+ * - <b>d</b> decimal signed integer.
+ * - <b>D</b> decimal signed long.
+ * - <b>u</b> decimal unsigned integer.
+ * - <b>U</b> decimal unsigned long.
+ * - <b>c</b> character.
+ * - <b>s</b> string.
+ * .
+ *
+ * @param[in] buf pointer to a string buffer
+ * @param[in] fmt formatting string
+ */
+void chsprintf(char *buf, const char *fmt, ...) {
+ va_list ap;
+ char *p, *s, c, filler;
+ int i, precision, width;
+ bool_t is_long, left_align;
+ long l;
+#if CHPRINTF_USE_FLOAT
+ float f;
+ char tmpbuf[2*MAX_FILLER + 1];
+#else
+ char tmpbuf[MAX_FILLER + 1];
+#endif
+
+ va_start(ap, fmt);
+ while (TRUE) {
+ c = *fmt++;
+ if (c == 0) {
+ va_end(ap);
+ *(buf++) = 0;
+ return;
+ }
+ if (c != '%') {
+ *(buf++) = (uint8_t)c;
+ continue;
+ }
+ p = tmpbuf;
+ s = tmpbuf;
+ left_align = FALSE;
+ if (*fmt == '-') {
+ fmt++;
+ left_align = TRUE;
+ }
+ filler = ' ';
+ if (*fmt == '.') {
+ fmt++;
+ filler = '0';
+ }
+ width = 0;
+ while (TRUE) {
+ c = *fmt++;
+ if (c >= '0' && c <= '9')
+ c -= '0';
+ else if (c == '*')
+ c = va_arg(ap, int);
+ else
+ break;
+ width = width * 10 + c;
+ }
+ precision = 0;
+ if (c == '.') {
+ while (TRUE) {
+ c = *fmt++;
+ if (c >= '0' && c <= '9')
+ c -= '0';
+ else if (c == '*')
+ c = va_arg(ap, int);
+ else
+ break;
+ precision *= 10;
+ precision += c;
+ }
+ }
+ /* Long modifier.*/
+ if (c == 'l' || c == 'L') {
+ is_long = TRUE;
+ if (*fmt)
+ c = *fmt++;
+ }
+ else
+ is_long = (c >= 'A') && (c <= 'Z');
+
+ /* Command decoding.*/
+ switch (c) {
+ case 'c':
+ filler = ' ';
+ *p++ = va_arg(ap, int);
+ break;
+ case 's':
+ filler = ' ';
+ if ((s = va_arg(ap, char *)) == 0)
+ s = "(null)";
+ if (precision == 0)
+ precision = 32767;
+ for (p = s; *p && (--precision >= 0); p++)
+ ;
+ break;
+ case 'D':
+ case 'd':
+ case 'I':
+ case 'i':
+ if (is_long)
+ l = va_arg(ap, long);
+ else
+ l = va_arg(ap, int);
+ if (l < 0) {
+ *p++ = '-';
+ l = -l;
+ }
+ p = ltoa(p, l, 10);
+ break;
+#if CHPRINTF_USE_FLOAT
+ case 'f':
+ f = (float) va_arg(ap, double);
+ if (f < 0) {
+ *p++ = '-';
+ f = -f;
+ }
+ p = ftoa(p, f);
+ break;
+#endif
+ case 'X':
+ case 'x':
+ c = 16;
+ goto unsigned_common;
+ case 'U':
+ case 'u':
+ c = 10;
+ goto unsigned_common;
+ case 'O':
+ case 'o':
+ c = 8;
+unsigned_common:
+ if (is_long)
+ l = va_arg(ap, unsigned long);
+ else
+ l = va_arg(ap, unsigned int);
+ p = ltoa(p, l, c);
+ break;
+ default:
+ *p++ = c;
+ break;
+ }
+ i = (int)(p - s);
+ if ((width -= i) < 0)
+ width = 0;
+ if (left_align == FALSE)
+ width = -width;
+ if (width < 0) {
+ if (*s == '-' && filler == '0') {
+ *(buf++) = (uint8_t)*s++;
+ i--;
+ }
+ do
+ *(buf++) = (uint8_t)filler;
+ while (++width != 0);
+ }
+ while (--i >= 0)
+ *(buf++) = (uint8_t)*s++;
+
+ while (width) {
+ *(buf++) = (uint8_t)filler;
+ width--;
+ }
+ }
+}
/** @} */
--
1.8.1.2
chsprintf minimal @p sprintf() patch
Moderators: RoccoMarco, barthess
- Giovanni
- Site Admin
- Posts: 14458
- Joined: Wed May 27, 2009 8:48 am
- Location: Salerno, Italy
- Has thanked: 1076 times
- Been thanked: 922 times
- Contact:
Re: chsprintf minimal @p sprintf() patch
Hi,
I need to verify if there is an easier way to implement chsprintf(), duplicating all the code looks a bit wasteful. Probably it is possible to create a string writer implementing a stream and using the normal chprintf() for printing.
Giovanni
I need to verify if there is an easier way to implement chsprintf(), duplicating all the code looks a bit wasteful. Probably it is possible to create a string writer implementing a stream and using the normal chprintf() for printing.
Giovanni
- Giovanni
- Site Admin
- Posts: 14458
- Joined: Wed May 27, 2009 8:48 am
- Location: Salerno, Italy
- Has thanked: 1076 times
- Been thanked: 922 times
- Contact:
Re: chsprintf minimal @p sprintf() patch
Hi,
I added an alternate implementation of chsnprintf() that uses memstreams internally. Note the "N", I prefer this variant for safety reasons.
Please let me go if it works for you.
Giovanni
I added an alternate implementation of chsnprintf() that uses memstreams internally. Note the "N", I prefer this variant for safety reasons.
Please let me go if it works for you.
Giovanni
Re: chsprintf minimal @p sprintf() patch
Thx
Which release repository did you add it to? 2.6 or 2.7.
We are still on 2.6, But we are looking to migrate to 2.7
Which release repository did you add it to? 2.6 or 2.7.
We are still on 2.6, But we are looking to migrate to 2.7
- Giovanni
- Site Admin
- Posts: 14458
- Joined: Wed May 27, 2009 8:48 am
- Location: Salerno, Italy
- Has thanked: 1076 times
- Been thanked: 922 times
- Contact:
Re: chsprintf minimal @p sprintf() patch
Hi,
Both, it will be in 2.6.2 and 2.7.0.
Note that 2.7.0 probably will never be released and replaced by the 3.0.0 branch. Everything is going in 2.6.2 anyway.
Giovanni
Both, it will be in 2.6.2 and 2.7.0.
Note that 2.7.0 probably will never be released and replaced by the 3.0.0 branch. Everything is going in 2.6.2 anyway.
Giovanni
Re: chsprintf minimal @p sprintf() patch
I know I am missing something easy.
git grep include -- 'chprintf.[ch]'
chprintf.c:#include "ch.h"
chprintf.c:#include "chprintf.h"
chprintf.c:#include "memstreams.h"
chprintf.h:#include <stdarg.h>
chprintf.c:297: undefined reference to `msObjectInit'
ideas?
git grep include -- 'chprintf.[ch]'
chprintf.c:#include "ch.h"
chprintf.c:#include "chprintf.h"
chprintf.c:#include "memstreams.h"
chprintf.h:#include <stdarg.h>
chprintf.c:297: undefined reference to `msObjectInit'
ideas?
Re: chsprintf minimal @p sprintf() patch
Forgot to add
$(CHIBIOS)/os/various/memstreams.c \
to my Makefile.
$(CHIBIOS)/os/various/memstreams.c \
to my Makefile.
Who is online
Users browsing this forum: No registered users and 12 guests