001    /* Copyright 2000, 2001, Compaq Computer Corporation */
002    
003    package javafe.reader;
004    
005    import java.io.IOException;
006    
007    import javafe.ast.CompilationUnit;
008    import javafe.ast.PrettyPrint;                  // Debugging methods only
009    
010    import javafe.genericfile.*;
011    
012    import javafe.parser.Lex;
013    import javafe.parser.Parse;
014    import javafe.parser.PragmaParser;
015    
016    import javafe.util.FileCorrelatedReader;
017    
018    /**
019     * A SrcReader is a {@link Reader} that reads in a {@link
020     * CompilationUnit} from a source file (.java files) using the
021     * <code>javafe.parser</code> package.
022     *
023     * <p> SrcReaders do not cache the results of their reading.
024     */
025    
026    public class SrcReader extends Reader
027    {
028        /***************************************************
029         *                                                 *
030         * Creation:                                       *
031         *                                                 *
032         **************************************************/
033    
034        //@ invariant readLex != null;
035        //@ spec_public
036        private Lex readLex;
037    
038        //@ invariant readParser != null;
039        //@ spec_public
040        private Parse readParser;
041    
042        public SrcReader() {
043            this(null);
044        }
045    
046        // p can be null
047        public SrcReader(PragmaParser p) {
048            readLex = new Lex(p, true);
049            readParser = new Parse();
050        }
051    
052    
053        /***************************************************
054         *                                                 *
055         * Reading:                                        *
056         *                                                 *
057         **************************************************/
058    
059        /**
060         * Attempt to read and parse a CompilationUnit from *source* target.
061         * Any errors encountered are reported via javafe.util.ErrorSet.
062         * Null is returned iff an error was encountered.<p>
063         *
064         *
065         * By default, we attempt to read only a spec (e.g., specOnly is set
066         * in the resulting CompilationUnit) to save time.  If avoidSpec is
067         * true, we always return a non-spec (if the file is a .java file).<p>
068         *
069         *
070         * The result of this function is not cached.<p>
071         *
072         * Target must be non-null.<p>
073         */
074        public CompilationUnit read(GenericFile target, boolean avoidSpec) {
075            javafe.util.Info.out("[parsing "
076                                 + (avoidSpec ? "" : "spec from ")
077                                 + target.getHumanName() + "]");
078            try {
079                FileCorrelatedReader input = new FileCorrelatedReader(target);
080                readLex.restart(input);
081            } catch (IOException e) {
082                javafe.util.ErrorSet.error("I/O error: " + e.getMessage());
083                return null;
084            }
085            if (avoidSpec && !target.getLocalName().endsWith(".java")) avoidSpec = false;
086            CompilationUnit result =
087                readParser.parseCompilationUnit(readLex, !avoidSpec);
088            readLex.close();
089            return result;
090        }
091    
092    
093        /***************************************************
094         *                                                 *
095         * Test methods:                                   *
096         *                                                 *
097         **************************************************/
098    
099        //@ requires \nonnullelements(args);
100        public static void main(String[] args) {
101            if (args.length != 1) {
102                System.err.println("SrcReader: <source filename>");
103                System.exit(1);
104            }
105    
106            GenericFile target = new NormalGenericFile(args[0]);
107            SrcReader reader = new SrcReader();
108    
109            CompilationUnit cu = reader.read(target, true);
110            if (cu != null)
111                PrettyPrint.inst.print( System.out, cu );
112        }
113    }