[LLVMdev] Extracting all BasicBlocks of a Function into new Function

Bram Adams bram.adams at ugent.be
Thu Oct 5 05:46:35 PDT 2006


Hi,

Chris Lattner wrote:
> All the non-vastart calls can be anywhere.  va_end in particular codegens 
> to a noop on all targets llvm currently supports, fwiw.
>   
Things go well, except for the following (pathological?) C program:

int va_double_sum(int count,...){
  int i,sum=0;
  va_list ap;

  va_start(ap,count);
  for(i=0;i<count;i++){
    sum+=va_arg(ap,int);
  }
  va_end(ap);

  va_start(ap,count);/* same vararg opened twice!!! */
  for(i=0;i<count;i++){
    sum+=va_arg(ap,int);
  }
  va_end(ap);

  return sum;
}

The problematic issue here is that the va_list is opened and used twice, 
which should work according to GCC. If I convert the program's LLVM 
bytecode to the following pseudo-bytecode:

int va_double_sum(int count,...){
  /*declare va_list*/
  /*llvm.va_start va_list*/
  /*call extracted_sum(count,va_list)*/
  /*llvm.va_end va_list*/
}

int extracted_sum(int count,/*vararg-argument*/){
  /*see original va_double_sum WITHOUT the llvm.va_start's and 
llvm.va_end's and WITH all uses of the original va_list replaced with 
the extra vararg-argument*/
}

Apparently, the problem is how to "rewind" the vararg-argument back to 
its first element when the second loop is reached, as it seems that the 
code just continues at position count and beyond, resulting in overflow.

I'm not sure whether this code snippet is valid ANSI C, and if it is, 
one probably shouldn't use this approach, but I'm just curious to know 
how (and if) this problem could be solved.

Kind regards,

Bram Adams
GH-SEL, INTEC, Ghent University (Belgium)



More information about the llvm-dev mailing list