This is the mail archive of the mailing list for the newlib project.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: selective linking of floating point support for *printf / *scanf

On 24 October 2014 09:06, Thomas Preud'homme <> wrote:
>> From: [] On
>> Behalf Of Joseph S. Myers
>> I'm not clear if you're proposing such a patch for review, but note:
> Yep but not yet for inclusion as I'm waiting to see if this would suit the use case of avr people.

Sorry for the late reply, I was on vacation, and then I meant to flesh
out a suitable
solution for the macro/hook problem to test it, but the more I think
about it, the more
questions arise how this is best structured...

First, the interface of your hook: you say it returns a bool, but that
bool is not used.
You leave the case to fall through to the default case, thus emitting
the expression unchanged.
For my purposes, I have to change the expression.
Note how my original patch had:

+ exp = copy_node (exp);
+ CALL_EXPR_FN (exp) = build_addr (decl, current_function_decl);

I don't think changing the existing expression
destructively is safe, so the return value should be the - possibly
changed - expression.
You can just explain in the hook description that this return value
may be changed and/or
additional target-specific output may be emitted.

The auto-float-io option description dos not match what I intended the
hook to do on the
avr.  The idea was to have standard behaviour as default, i.e. printf
knows about float, and
have the hook change the function name to the integer-specific
function if the arguments
don't mention float and the function is not a v* function.
So, if we want to have a versatile hook and describe the option
specifically, it should be
a target option.  OTOH, that complicate the implementation of a
generic hook even more...

>> (a) you mean DEF_EXT_LIB_BUILTIN (since asprintf and vasprintf aren't in
>> ISO C);
> Ok.
>> (b) please don't add new target macros such as
>> something is defined in tm_defines and used in architecture-
>> independent
>> code, it's effectively a target macro), find a way to implement these as
>> hooks instead.

targhooks.c is not entirely target-independent code, so on one level
we could say it's
OK to customize it with macros, and we don't want to stuff the target
vector with a gazillion
settings that only very few targets use, but OTOH, if one target has
multiple libraries,
it might want multile variants of this hook.  In fact, having
sub-hooks for that hook wouldn't
work if they were POD-kind hooks, and way overcomplicate the target if
they weren't...

Considering we mean to move to C++, making the hook a template seems the proper
thing to do.  Prima facie I would say it should be templated on the
two strings that you
want to use.  However, C++ won't allow to use string literals as
template parameters.
So you need to stuff the strings as return values into class member functions.
Which means that there has to be a class definition somewhere in tm.h
... which, unfortunately,
we can't expand in the same macro that is used to assigning the
function instantiation to the
target vector element initializer, because you can't have a class
definition in a template
argument, nor can you have a statement expression outside of functions.
So we need two macros, one to define the class, one to provide the
function pointer for
the target vector element.

To illustrate, here are a few snippets of code that do TemPlated Printing
of input/output string, in parts meant model code for hook(?) include file,
builtins.c:expand_builtin code, and target vector (hook) setting:

==> tpp.h <==
extern "C" void printf (const char *fmt, ...);

template<typename t>
void print_str (void)
  t dummy;
  printf ("%s\n",;
  printf ("%s\n", dummy.out());

#define PRINT_STR_DEF(S1,S2) \
  class __FILE__##inout##S1##S2\
  { \
    public: \
    const char *in (void) { return #S1; } \
    const char *out (void) { return #S2; } \

#define PRINT_STR(S1,S2) print_str<__FILE__##inout##S1##S2>

extern void (*fp) (void);

==> <==
#include "tpp.h"

int main (void)
  return 0;

==> <==
#include "tpp.h"

void (*fp) (void) = PRINT_STR(scanf,printf);

Now, are we actually OK with having a template in an include file?  I
think C++11 has extern templates, but then, that's probably too new
for our purposes.
Would we want to use an existing include file, or a new special-purpose one?

Also, that '__FILE__' is not actually expanded - I think we have to
hand to through some more macro invocations to expand it.
And then the expansion will cause trouble with quotes and the dot from
the filename...
But how should clashes between multiple such classes be avoided?  That
would happen if your hook is actually a wrapper to use
different template instantiations of the generic templated hook
depending on the subtarget - should the port writer use namespaces

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]