Re: a nifty feature for c preprocessor

2011-12-31 Thread Robert Dewar

On 12/31/2011 4:44 AM, R A wrote:


alright, here's another example why eval is a good idea:

#define A   17
#define B   153
#define N1  ((A + B)/2)  /* intended was (17 + 153)/2 */

#undef  A
#define A   230
#define N2  ((A + B)/2) /* intended was (230 + 153)/2 */


Bad example, this is a misuse of the preprocessor in any case!


Bogus gcc.c-torture/execute/20071018-1.c testcase?

2011-12-31 Thread Mark Kettenis
Execution of the test randomly fails for me on OpenBSD/amd64.  Looking
at the code, it seems it is doing an out-of-bounds array access.  For
refernce I've copied the code of the testcase below.  As you can see
there's a foo(0) call in main().  Therefore

  struct foo **upper = &as->x[rank * 8 - 1];

becomes

  struct foo **upper = &as->x[-1];

so upper points to an address before the malloc()'ed memory.  Then
when the code does

  *upper = 0;

this generates a SIGSEGV, if the malloc()'ed memory happens to lie
right at the start of a page.  I suppose that may never happen on some
platforms (Linux?) since many malloc() implementations will use the
start of a page for their own bookkeeping.

I don't really understand what the testcase is testing.  Richard, can
you perhaps shed some light on this?

Thanks,

Mark

---

extern void abort(void);

struct foo {
  int rank;
  char *name;
};

struct mem {
  struct foo *x[4];
};

void __attribute__((noinline)) bar(struct foo **f)
{
  *f = __builtin_malloc(sizeof(struct foo));
}
struct foo * foo(int rank)
{
  void *x = __builtin_malloc(sizeof(struct mem));
  struct mem *as = x;
  struct foo **upper = &as->x[rank * 8 - 1];
  *upper = 0;
  bar(upper);
  return *upper;
}

int main()
{
  if (foo(0) == 0)
abort ();
  return 0;
}


RE: a nifty feature for c preprocessor

2011-12-31 Thread R A

alright, here's another example why eval is a good idea:

#define A   17
#define B   153
#define N1  ((A + B)/2)  /* intended was (17 + 153)/2 */

#undef  A
#define A   230
#define N2  ((A + B)/2) /* intended was (230 + 153)/2 */

printf("%u %u", N1, N2);


sure, you can assign N1 to a static const, say N1_var, then invoke that in when 
printf is finally called. or simply print N1, then after the undef print N2.
but what if we have to use both N1 and N2 in the same conditional expression?? 
everybody should be aware by now that there's a lot of ugly dependencies in cpp.

but for a *fairly complex*(1) conditional directives, spanning several files, 
you have to call the macros all at the same time and not one one-by-one. to get 
around it (if possible) is to employ an even more complex system of defs and 
conditionals... or you can use external scripts to generate the codes. but like 
i said, these could just be small snippets of codes, where having scripts is 
un-minimalistic.
eval takes away all the ugliness.

(1) by fairly complex, i mean one that doesn't really merit a script/macro 
processors to be written.

alright, if i can't convince the developers, would a maintainer (or anybody 
that knosw their way around libcpp) please help me out on how to get started my 
port for the feature... i actually don't like the idea of writing a plugin.