Thanks for the ideas. I'm considering range checking and staying with the %f format...something like:
void dig4_float_to_7seg(float val, unsigned char dp, unsigned char term, unsigned char *buf)
Code:
volatile int len; volatile int cnt; char flt_buf[15] = {0}; /* Limit the float size. This will help protect the buffer for %f format */ if ((val < -9999.5F) || (val > 9999.5F)) { dig4_float_to_7seg_err(&buf[0]); return; } /* No deeper than 1/100s resolution */ if ((val < 0.0F) && (val > -0.01F)) { dig4_float_to_7seg_err(&buf[0]); return; } if ((val < 0.01F) && (val > 0.0F)) { dig4_float_to_7seg_err(&buf[0]); return; } /* Load the float into a string. For small numbers (near zero), %f will * get the first significant digit for both .1 and .0 formats. */ __DI(); /* Showing tenths */ if (dp == 1U) { cnt = sprintf(&flt_buf[0], "%-10.1f", val); /* Override term! */ term = 0U; } /* No tenths */ else { /*lint -e{559} */ cnt = sprintf(&flt_buf[0], "%-10.0f", val); } __EI(); I experimented with the %g using significnat digit counts; however, I'm trying to write the "driver" generic for ints and floats for a 4-segment display with whole number and 1/10 display options. I failed to find a way to strip of the tenths (like %-10.0f does) for %g as it is based on significant digits. The fact that I currently am leting sprintf handle negative numbers as well does complicate the range checking a bit as I have to allow zero AND watch out for small numbers and I guess I could pass a variable to indiate the sign (TBD).
I analyzed printf.c but I was hoping you could elaborate on the use of vsprintf and ensuring that the buffer does not overrun...
I envision soemthing like:Code:
char buffer[15];int vspf(char *fmt, ...){ va_list argptr; int cnt; va_start(argptr, fmt); cnt = vsprintf(buffer, fmt, argptr); va_end(argptr); return(cnt);}int main(void){ float fnumber = 90.0F; vspf("%-10.1f", fnumber); printf("%s\n", buffer); return 0;}
Exactly how do I ensure buffer is not overrun? Also, just to clarify...based on your earlier comments there is no reason to protect sprintf with __DI()/__EI(). I never did use it in the isr I just wanted to understand its capabilities.
Thanks again!