package c99.driver;

import java.io.FileInputStream;

import c99.CompilerOptions;
import c99.DummyErrorReporter;
import c99.ISourceRange;
import c99.parser.SymTable;
import c99.parser.pp.PPLexer;
import c99.parser.pp.Prepr;

public class Preprocessor
{
public static void main ( String[] args )
{
  try
  {
    boolean cpp = true;
    boolean toks = false;
    String fileName = null;

    for ( String arg : args )
    {
      if ("--toks".equals( arg ))
      {
        toks = true;
        cpp = false;
      }
      else if ("--no-toks".equals( arg ))
        toks = false;
      else if ("--cpp".equals( arg ))
        cpp = true;
      else if ("--no-cpp".equals( arg ))
        cpp = false;
      else if (arg.startsWith( "-"))
      {
        System.err.println( "**fatal: unknown command line option '"+arg +"'" );
        System.exit(1);
      }
      else
      {
        if (fileName != null)
        {
          System.err.println( "**fatal: More than one input filename specified" );
          System.exit(1);
        }
        fileName = arg;
      }
    }

    if (fileName == null)
    {
      System.err.println( "**fatal: No input filename specified" );
      System.exit(1);
    }

    DummyErrorReporter reporter = new DummyErrorReporter();
    SymTable symTable = new SymTable();
    CompilerOptions opts = new CompilerOptions();
    Prepr pp = new Prepr( opts, reporter, fileName, new FileInputStream( fileName ), symTable );

    String lastFile = "";
    int lastLine = -1;
    PPLexer.Token tok;
    while ((tok = pp.nextToken()).code() != PPLexer.Code.EOF)
    {
      if (!tok.getFileName().equals( lastFile ))
      {
        if (cpp) System.out.format(  "\n# %d %s\n", tok.getLine1(), Prepr.genString(tok.getFileName()) );
        lastLine = tok.getLine1();
      }
      else if (tok.getLine1() != lastLine)
      {
        if (tok.getLine1() - lastLine <= 10)
        {
          do
            if (cpp) System.out.println();
          while (++lastLine < tok.getLine1());
        }
        else
          if (cpp) System.out.format( "\n# %d\n", tok.getLine1() );
        lastLine = tok.getLine1();
      }

      lastFile = tok.getFileName();

      if (cpp) tok.output( System.out );
      if (toks) System.out.println( tok );
    }
  }
  catch (Exception e)
  {
    e.printStackTrace();
  }
}
} // class

@@ -1523,71 +1523,67 @@
     
-while ((tok = pp.nextToken()).code() != PPLexer.Code.EOF)%0A    %7B
+boolean nl = true;%0A    do%0A    %7B%0A      tok = pp.nextToken();
 %0A   
@@ -1644,32 +1644,105 @@
         if (cpp)
+%0A        %7B%0A          if (!nl)%0A            System.out.println();%0A         
  System.out.form
@@ -1747,18 +1747,16 @@
 rmat(  %22
-%5Cn
 # %25d %25s%5C
@@ -1809,24 +1809,55 @@
 eName()) );%0A
+          nl = true;%0A        %7D%0A
         last
@@ -2002,24 +2002,36 @@
          do%0A
+          %7B%0A
             
@@ -2053,32 +2053,67 @@
 .out.println();%0A
+            nl = true;%0A          %7D%0A
           while 
@@ -2170,34 +2170,125 @@
 lse%0A        
-  if (cpp)
+%7B%0A          if (cpp)%0A          %7B%0A            if (!nl)%0A              System.out.println();%0A           
  System.out.
@@ -2296,18 +2296,16 @@
 ormat( %22
-%5Cn
 # %25d%5Cn%22,
@@ -2319,24 +2319,69 @@
 tLine1() );%0A
+            nl = true;%0A          %7D%0A        %7D%0A
         last
@@ -2467,83 +2467,497 @@
 cpp)
- tok.output( System.out );%0A      if (toks) System.out.println( tok );%0A    %7D
+%0A      %7B%0A        if (tok.code() == PPLexer.Code.NEWLINE)%0A        %7B%0A          System.out.println();%0A          nl = true;%0A          ++lastLine;%0A        %7D%0A        else%0A        %7B%0A          if (nl)%0A          %7B%0A            for ( int i = 1, col = tok.getCol1(); i %3C col; ++i )%0A              System.out.print( ' ' );%0A          %7D%0A          tok.output( System.out );%0A          nl = false;%0A        %7D%0A      %7D%0A      if (toks) System.out.println( tok );%0A    %7D%0A    while (tok.code() != PPLexer.Code.EOF);
 %0A  %7D

improve generating of preprocessed source