Hi,
The attached file was compiled with:
msp430-gcc -O2 -mmcu=msp430x149 -mforce-hw-mul -Wall -c vprfrd.c -o
vprfrd.o
The code won't run correctly compiled with this optimization, -O works
ok.
I do not have facility to use gdb on it (running a ppc host) so would
appreciate someone defining TEST (line 40)
within the module and seeing where it fails.
(this module is part of the nesos FSM operating system.)
Many Thanks
Bernie Mentink.
/******************** MODULE INFO ****************************/
/*
** File name : vprfrd.c
*/
/* AUTHOR : Jan Erik Nilsen */
/* DATE : Tue Feb 06 11:36:06 1996 */
/* VERSION : 1.0 */
/*
** Compiler : ANSI C
** Contents : a quick reduced function to make a
** printf with given output destination.
**
** DESCRIPTION :
**
** the following conversion characters are supported:
** %[<prefix>]<frmc>
**
** <prefix> :- 'h' | 'l'
** <frmc> :- 'd' | 'i' | 'u' | 'o' | 'x' | 'X' | 'y' | 'c' | 's'
**
** d :- decimal
** i :- decimal
** u :- decimal, unsigned
** o :- octal, unsigned
** x :- hexadecimal, unsigned 0xfeedface
** X :- hexadecimal, unsigned 0xFEEDFACE
** y :- binary, unsigned
** c :- character
** s :- string
**
** Global var : None
** Re-entrent : Yes
**
*/
#include <stdarg.h>
/* ------ User defined extensions --------------------- */
/* #define TEST 1 */
/* ------------------------------------------------------ */
#define T_STRING 0x8000
#define T_LONG 0x4000
#define T_SHORT 0x2000
#define T_INT 0x1000
#define T_BIGX 0x100
#define T_SIGNED 0x200
/* ----- Local prototypes ------------------------------- */
static void putulnum(void (*printchar)(int ch), unsigned long val, int base);
/* ----- Test program if TEST defined ----------------------- */
#ifdef TEST
/* ------- Prototype ----- */
void vprfrd(void (*printchar)(int ch), char *format, va_list ap);
#include <stdio.h>
#include <stdlib.h>
void printfrd(char *format, ...);
char ibuf[200];
char *ibufp;
void main(int argc, char **argv)
{
argc = argc; argv = argv;
printfrd("-1,-1,0xFFFF,0xFFFF uxux: %u %x %u %x\n",
-1, -1, 0xFFFF, 0xFFFF);
printfrd("-32, 64, 0x8e, 0x8E: %d %u %x %X\n", -32, 64, 0x8E, 0x8E);
printfrd("-32, 64, 0x800000: %ld %lu %lx\n", -32L, 64L, 0x800000L);
printfrd("max unsigned long: %ld %lu %lx\n",
0xFFFFFFFFL,0xFFFFFFFFL,0xFFFFFFFFL);
printfrd("0xFEEDFACE: %lx %lX %lo\n %ly\n",
0xFEEDFACE, 0xFEEDFACE, 0xFEEDFACE, 0xFEEDFACE);
printfrd("string char JeN: %s %c%c%c\n", "Dette er", 'J','e','N');
printfrd("NULL string: %s\n", NULL);
printfrd("Bye.\n");
exit(0);
}
void putcinstr(int ch)
{
*ibufp++ = (char)ch;
}
void printfrd(char *format, ...)
{
va_list argPtr;
va_start(argPtr, format);
ibufp = &ibuf[0];
vprfrd(putcinstr,format,argPtr);
*ibufp++ = 0;
va_end(argPtr);
printf("%s", &ibuf[0]);
}
#endif
/* --------- The function ---------------- */
void vprfrd(void (*printchar)(int ch), char *format, va_list ap)
{
int fch;
unsigned int b, uint_max;
long l;
char *scp = (char *)0;
while ((fch = *format++) != 0) {
if (fch != '%') (*printchar)(fch);
else {
b = 0;
fch = *format++;
if (fch == 'l') {
fch = *format++;
switch (fch) {
case 'd':
case 'i': b = T_LONG + T_SIGNED + 10;
break;
case 'u': b = T_LONG + 10;
break;
case 'o': b = T_LONG + 8;
break;
case 'x': b = T_LONG + 16;
break;
case 'X': b = T_LONG + T_BIGX + 16;
break;
case 'y': b = T_LONG + 2;
break;
default: (*printchar)('l'); (*printchar)(fch);
}
}
else if (fch == 'h') {
fch = *format++;
switch (fch) {
case 'd':
case 'i': b = T_SHORT + T_SIGNED + 10;
break;
case 'u': b = T_SHORT + 10;
break;
case 'o': b = T_SHORT + 8;
break;
case 'x': b = T_SHORT + 16;
break;
case 'X': b = T_SHORT + T_BIGX + 16;
break;
case 'y': b = T_SHORT + 2;
break;
default: (*printchar)('h'); (*printchar)(fch);
}
}
else {
switch (fch) {
case 'd':
case 'i': b = T_INT + T_SIGNED + 10;
break;
case 'u': b = T_INT + 10;
break;
case 'o': b = T_INT + 8;
break;
case 'x': b = T_INT + 16;
break;
case 'X': b = T_INT + T_BIGX + 16;
break;
case 'y': b = T_INT + 2;
break;
case 'c': (*printchar)(va_arg(ap,int));
break;
case 's': scp = va_arg(ap,char*);
b = T_STRING;
break;
default: (*printchar)(fch);
}
}
if (b & T_STRING) {
if (!scp) scp = "(NULL)";
while (*scp) (*printchar)(*scp++);
}
if (b & (T_LONG | T_SHORT | T_INT)) {
if (b & T_LONG) l = va_arg(ap,long);
else if (b & T_SHORT) l = (long)va_arg(ap,int);
else l = (long)va_arg(ap,int);
if (b & T_SIGNED) {
if (l < 0) { l = -l; (*printchar)('-'); }
}
if (b & T_SHORT) l &= 0xFFFF;
if (b & T_INT) {
uint_max = (unsigned int)(-1);
l &= (long)uint_max;
}
putulnum(printchar, (unsigned long)l, b & (T_BIGX | 0x1F));
}
} /* else format */
} /* while */
}
/*
** put unsigned long in any base to output string
*/
static void putulnum(void (*printchar)(int ch), unsigned long val, int base)
{
if (val >= (base & 0x1F)) putulnum(printchar, val / (base & 0x1F), base);
val = val % (base & 0x1F);
(*printchar)(val + ((val > 9)? ((base & T_BIGX)? ('A' - 10) : ('a' - 10))
: '0'));
}
#ifndef VPRFRD_H
#define VPRFRD_H
extern void vprfrd(void (*printchar)(int ch), char *format, va_list ap);
#endif