annotate src/share/vm/adlc/filebuff.cpp @ 6972:bd7a7ce2e264

6830717: replay of compilations would help with debugging Summary: When java process crashed in compiler thread, repeat the compilation process will help finding root cause. This is done with using SA dump application class data and replay data from core dump, then use debug version of jvm to recompile the problematic java method. Reviewed-by: kvn, twisti, sspitsyn Contributed-by: yumin.qi@oracle.com
author minqi
date Mon, 12 Nov 2012 14:03:53 -0800
parents f95d63e2154a
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
2 * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
a61af66fc99e Initial load
duke
parents:
diff changeset
4 *
a61af66fc99e Initial load
duke
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
a61af66fc99e Initial load
duke
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
a61af66fc99e Initial load
duke
parents:
diff changeset
7 * published by the Free Software Foundation.
a61af66fc99e Initial load
duke
parents:
diff changeset
8 *
a61af66fc99e Initial load
duke
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
a61af66fc99e Initial load
duke
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a61af66fc99e Initial load
duke
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a61af66fc99e Initial load
duke
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
a61af66fc99e Initial load
duke
parents:
diff changeset
13 * accompanied this code).
a61af66fc99e Initial load
duke
parents:
diff changeset
14 *
a61af66fc99e Initial load
duke
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
a61af66fc99e Initial load
duke
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
a61af66fc99e Initial load
duke
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
a61af66fc99e Initial load
duke
parents:
diff changeset
18 *
1552
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
20 * or visit www.oracle.com if you need additional information or have any
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
21 * questions.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
22 *
a61af66fc99e Initial load
duke
parents:
diff changeset
23 */
a61af66fc99e Initial load
duke
parents:
diff changeset
24
a61af66fc99e Initial load
duke
parents:
diff changeset
25 // FILEBUFF.CPP - Routines for handling a parser file buffer
a61af66fc99e Initial load
duke
parents:
diff changeset
26 #include "adlc.hpp"
a61af66fc99e Initial load
duke
parents:
diff changeset
27
603
dbbe28fc66b5 6778669: Patch from Red Hat -- fixes compilation errors
twisti
parents: 470
diff changeset
28 using namespace std;
dbbe28fc66b5 6778669: Patch from Red Hat -- fixes compilation errors
twisti
parents: 470
diff changeset
29
0
a61af66fc99e Initial load
duke
parents:
diff changeset
30 //------------------------------FileBuff---------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
31 // Create a new parsing buffer
a61af66fc99e Initial load
duke
parents:
diff changeset
32 FileBuff::FileBuff( BufferedFile *fptr, ArchDesc& archDesc) : _fp(fptr), _AD(archDesc) {
a61af66fc99e Initial load
duke
parents:
diff changeset
33 _err = fseek(_fp->_fp, 0, SEEK_END); // Seek to end of file
a61af66fc99e Initial load
duke
parents:
diff changeset
34 if (_err) {
a61af66fc99e Initial load
duke
parents:
diff changeset
35 file_error(SEMERR, 0, "File seek error reading input file");
a61af66fc99e Initial load
duke
parents:
diff changeset
36 exit(1); // Exit on seek error
a61af66fc99e Initial load
duke
parents:
diff changeset
37 }
a61af66fc99e Initial load
duke
parents:
diff changeset
38 _filepos = ftell(_fp->_fp); // Find offset of end of file
a61af66fc99e Initial load
duke
parents:
diff changeset
39 _bufferSize = _filepos + 5; // Filepos points to last char, so add padding
a61af66fc99e Initial load
duke
parents:
diff changeset
40 _err = fseek(_fp->_fp, 0, SEEK_SET); // Reset to beginning of file
a61af66fc99e Initial load
duke
parents:
diff changeset
41 if (_err) {
a61af66fc99e Initial load
duke
parents:
diff changeset
42 file_error(SEMERR, 0, "File seek error reading input file\n");
a61af66fc99e Initial load
duke
parents:
diff changeset
43 exit(1); // Exit on seek error
a61af66fc99e Initial load
duke
parents:
diff changeset
44 }
a61af66fc99e Initial load
duke
parents:
diff changeset
45 _filepos = ftell(_fp->_fp); // Reset current file position
415
4d9884b01ba6 6754519: don't emit flag fixup for NaN when condition being tested doesn't need it
never
parents: 0
diff changeset
46 _linenum = 0;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
47
a61af66fc99e Initial load
duke
parents:
diff changeset
48 _bigbuf = new char[_bufferSize]; // Create buffer to hold text for parser
a61af66fc99e Initial load
duke
parents:
diff changeset
49 if( !_bigbuf ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
50 file_error(SEMERR, 0, "Buffer allocation failed\n");
a61af66fc99e Initial load
duke
parents:
diff changeset
51 exit(1); // Exit on allocation failure
a61af66fc99e Initial load
duke
parents:
diff changeset
52 }
605
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
53 *_bigbuf = '\n'; // Lead with a sentinel newline
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
54 _buf = _bigbuf+1; // Skip sentinel
0
a61af66fc99e Initial load
duke
parents:
diff changeset
55 _bufmax = _buf; // Buffer is empty
605
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
56 _bufeol = _bigbuf; // _bufeol points at sentinel
0
a61af66fc99e Initial load
duke
parents:
diff changeset
57 _filepos = -1; // filepos is in sync with _bufeol
a61af66fc99e Initial load
duke
parents:
diff changeset
58 _bufoff = _offset = 0L; // Offset at file start
a61af66fc99e Initial load
duke
parents:
diff changeset
59
a61af66fc99e Initial load
duke
parents:
diff changeset
60 _bufmax += fread(_buf, 1, _bufferSize-2, _fp->_fp); // Fill buffer & set end value
a61af66fc99e Initial load
duke
parents:
diff changeset
61 if (_bufmax == _buf) {
a61af66fc99e Initial load
duke
parents:
diff changeset
62 file_error(SEMERR, 0, "File read error, no input read\n");
a61af66fc99e Initial load
duke
parents:
diff changeset
63 exit(1); // Exit on read error
a61af66fc99e Initial load
duke
parents:
diff changeset
64 }
605
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
65 *_bufmax = '\n'; // End with a sentinel new-line
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
66 *(_bufmax+1) = '\0'; // Then end with a sentinel NULL
0
a61af66fc99e Initial load
duke
parents:
diff changeset
67 }
a61af66fc99e Initial load
duke
parents:
diff changeset
68
a61af66fc99e Initial load
duke
parents:
diff changeset
69 //------------------------------~FileBuff--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
70 // Nuke the FileBuff
a61af66fc99e Initial load
duke
parents:
diff changeset
71 FileBuff::~FileBuff() {
a61af66fc99e Initial load
duke
parents:
diff changeset
72 delete _bigbuf;
a61af66fc99e Initial load
duke
parents:
diff changeset
73 }
a61af66fc99e Initial load
duke
parents:
diff changeset
74
a61af66fc99e Initial load
duke
parents:
diff changeset
75 //------------------------------get_line----------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
76 char *FileBuff::get_line(void) {
a61af66fc99e Initial load
duke
parents:
diff changeset
77 char *retval;
a61af66fc99e Initial load
duke
parents:
diff changeset
78
a61af66fc99e Initial load
duke
parents:
diff changeset
79 // Check for end of file & return NULL
a61af66fc99e Initial load
duke
parents:
diff changeset
80 if (_bufeol >= _bufmax) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
81
415
4d9884b01ba6 6754519: don't emit flag fixup for NaN when condition being tested doesn't need it
never
parents: 0
diff changeset
82 _linenum++;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
83 retval = ++_bufeol; // return character following end of previous line
605
98cb887364d3 6810672: Comment typos
twisti
parents: 603
diff changeset
84 if (*retval == '\0') return NULL; // Check for EOF sentinel
0
a61af66fc99e Initial load
duke
parents:
diff changeset
85 // Search for newline character which must end each line
a61af66fc99e Initial load
duke
parents:
diff changeset
86 for(_filepos++; *_bufeol != '\n'; _bufeol++)
a61af66fc99e Initial load
duke
parents:
diff changeset
87 _filepos++; // keep filepos in sync with _bufeol
a61af66fc99e Initial load
duke
parents:
diff changeset
88 // _bufeol & filepos point at end of current line, so return pointer to start
a61af66fc99e Initial load
duke
parents:
diff changeset
89 return retval;
a61af66fc99e Initial load
duke
parents:
diff changeset
90 }
a61af66fc99e Initial load
duke
parents:
diff changeset
91
a61af66fc99e Initial load
duke
parents:
diff changeset
92 //------------------------------FileBuffRegion---------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
93 // Create a new region in a FileBuff.
a61af66fc99e Initial load
duke
parents:
diff changeset
94 FileBuffRegion::FileBuffRegion( FileBuff* bufr, int soln, int ln,
a61af66fc99e Initial load
duke
parents:
diff changeset
95 int off, int len)
a61af66fc99e Initial load
duke
parents:
diff changeset
96 : _bfr(bufr), _sol(soln), _line(ln), _offset(off), _length(len) {
a61af66fc99e Initial load
duke
parents:
diff changeset
97 _next = NULL; // No chained regions
a61af66fc99e Initial load
duke
parents:
diff changeset
98 }
a61af66fc99e Initial load
duke
parents:
diff changeset
99
a61af66fc99e Initial load
duke
parents:
diff changeset
100 //------------------------------~FileBuffRegion--------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
101 // Delete the entire linked list of buffer regions.
a61af66fc99e Initial load
duke
parents:
diff changeset
102 FileBuffRegion::~FileBuffRegion() {
a61af66fc99e Initial load
duke
parents:
diff changeset
103 if( _next ) delete _next;
a61af66fc99e Initial load
duke
parents:
diff changeset
104 }
a61af66fc99e Initial load
duke
parents:
diff changeset
105
a61af66fc99e Initial load
duke
parents:
diff changeset
106 //------------------------------copy-------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
107 // Deep copy a FileBuffRegion
a61af66fc99e Initial load
duke
parents:
diff changeset
108 FileBuffRegion *FileBuffRegion::copy() {
a61af66fc99e Initial load
duke
parents:
diff changeset
109 if( !this ) return NULL; // The empty buffer region
a61af66fc99e Initial load
duke
parents:
diff changeset
110 FileBuffRegion *br = new FileBuffRegion(_bfr,_sol,_line,_offset,_length);
a61af66fc99e Initial load
duke
parents:
diff changeset
111 if( _next ) br->_next = _next->copy();
a61af66fc99e Initial load
duke
parents:
diff changeset
112 return br;
a61af66fc99e Initial load
duke
parents:
diff changeset
113 }
a61af66fc99e Initial load
duke
parents:
diff changeset
114
a61af66fc99e Initial load
duke
parents:
diff changeset
115 //------------------------------merge------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
116 // Merge another buffer region into this buffer region. Make overlapping areas
a61af66fc99e Initial load
duke
parents:
diff changeset
117 // become a single region. Remove (delete) the input FileBuffRegion.
a61af66fc99e Initial load
duke
parents:
diff changeset
118 // Since the buffer regions are sorted by file offset, this is a varient of a
a61af66fc99e Initial load
duke
parents:
diff changeset
119 // "sorted-merge" running in linear time.
a61af66fc99e Initial load
duke
parents:
diff changeset
120 FileBuffRegion *FileBuffRegion::merge( FileBuffRegion *br ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
121 if( !br ) return this; // Merging nothing
a61af66fc99e Initial load
duke
parents:
diff changeset
122 if( !this ) return br; // Merging into nothing
a61af66fc99e Initial load
duke
parents:
diff changeset
123
a61af66fc99e Initial load
duke
parents:
diff changeset
124 assert( _bfr == br->_bfr, "" ); // Check for pointer-equivalent buffers
a61af66fc99e Initial load
duke
parents:
diff changeset
125
a61af66fc99e Initial load
duke
parents:
diff changeset
126 if( _offset < br->_offset ) { // "this" starts before "br"
a61af66fc99e Initial load
duke
parents:
diff changeset
127 if( _offset+_length < br->_offset ) { // "this" ends before "br"
a61af66fc99e Initial load
duke
parents:
diff changeset
128 if( _next ) _next->merge( br ); // Merge with remainder of list
a61af66fc99e Initial load
duke
parents:
diff changeset
129 else _next = br; // No more in this list; just append.
a61af66fc99e Initial load
duke
parents:
diff changeset
130 } else { // Regions overlap.
a61af66fc99e Initial load
duke
parents:
diff changeset
131 int l = br->_offset + br->_length - _offset;
a61af66fc99e Initial load
duke
parents:
diff changeset
132 if( l > _length ) _length = l; // Pick larger region
a61af66fc99e Initial load
duke
parents:
diff changeset
133 FileBuffRegion *nr = br->_next; // Get rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
134 br->_next = NULL; // Remove indication of rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
135 delete br; // Delete this region (it's been subsumed).
a61af66fc99e Initial load
duke
parents:
diff changeset
136 if( nr ) merge( nr ); // Merge with rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
137 } // End of if regions overlap or not.
a61af66fc99e Initial load
duke
parents:
diff changeset
138 } else { // "this" starts after "br"
a61af66fc99e Initial load
duke
parents:
diff changeset
139 if( br->_offset+br->_length < _offset ) { // "br" ends before "this"
a61af66fc99e Initial load
duke
parents:
diff changeset
140 FileBuffRegion *nr = new FileBuffRegion(_bfr,_sol,_line,_offset,_length);
a61af66fc99e Initial load
duke
parents:
diff changeset
141 nr->_next = _next; // Structure copy "this" guy to "nr"
a61af66fc99e Initial load
duke
parents:
diff changeset
142 *this = *br; // Structure copy "br" over "this".
a61af66fc99e Initial load
duke
parents:
diff changeset
143 br->_next = NULL; // Remove indication of rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
144 delete br; // Delete this region (it's been copied)
a61af66fc99e Initial load
duke
parents:
diff changeset
145 merge( nr ); // Finish merging
a61af66fc99e Initial load
duke
parents:
diff changeset
146 } else { // Regions overlap.
a61af66fc99e Initial load
duke
parents:
diff changeset
147 int l = _offset + _length - br->_offset;
a61af66fc99e Initial load
duke
parents:
diff changeset
148 if( l > _length ) _length = l; // Pick larger region
a61af66fc99e Initial load
duke
parents:
diff changeset
149 _offset = br->_offset; // Start with earlier region
a61af66fc99e Initial load
duke
parents:
diff changeset
150 _sol = br->_sol; // Also use earlier line start
a61af66fc99e Initial load
duke
parents:
diff changeset
151 _line = br->_line; // Also use earlier line
a61af66fc99e Initial load
duke
parents:
diff changeset
152 FileBuffRegion *nr = br->_next; // Get rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
153 br->_next = NULL; // Remove indication of rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
154 delete br; // Delete this region (it's been subsumed).
a61af66fc99e Initial load
duke
parents:
diff changeset
155 if( nr ) merge( nr ); // Merge with rest of region
a61af66fc99e Initial load
duke
parents:
diff changeset
156 } // End of if regions overlap or not.
a61af66fc99e Initial load
duke
parents:
diff changeset
157 }
a61af66fc99e Initial load
duke
parents:
diff changeset
158 return this;
a61af66fc99e Initial load
duke
parents:
diff changeset
159 }
a61af66fc99e Initial load
duke
parents:
diff changeset
160
a61af66fc99e Initial load
duke
parents:
diff changeset
161 //------------------------------expandtab--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
162 static int expandtab( ostream &os, int off, char c, char fill1, char fill2 ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
163 if( c == '\t' ) { // Tab?
a61af66fc99e Initial load
duke
parents:
diff changeset
164 do os << fill1; // Expand the tab; Output space
a61af66fc99e Initial load
duke
parents:
diff changeset
165 while( (++off) & 7 ); // Expand to tab stop
a61af66fc99e Initial load
duke
parents:
diff changeset
166 } else { // Normal character
a61af66fc99e Initial load
duke
parents:
diff changeset
167 os << fill2; // Display normal character
a61af66fc99e Initial load
duke
parents:
diff changeset
168 off++; // Increment "cursor" offset
a61af66fc99e Initial load
duke
parents:
diff changeset
169 }
a61af66fc99e Initial load
duke
parents:
diff changeset
170 return off;
a61af66fc99e Initial load
duke
parents:
diff changeset
171 }
a61af66fc99e Initial load
duke
parents:
diff changeset
172
a61af66fc99e Initial load
duke
parents:
diff changeset
173 //------------------------------printline--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
174 // Print and highlite a region of a line. Return the amount of highliting left
a61af66fc99e Initial load
duke
parents:
diff changeset
175 // to do (i.e. highlite length minus length of line).
a61af66fc99e Initial load
duke
parents:
diff changeset
176 static int printline( ostream& os, const char *fname, int line,
a61af66fc99e Initial load
duke
parents:
diff changeset
177 const char *_sol, int skip, int len ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
178
a61af66fc99e Initial load
duke
parents:
diff changeset
179 // Display the entire tab-expanded line
a61af66fc99e Initial load
duke
parents:
diff changeset
180 os << fname << ":" << line << ": ";
a61af66fc99e Initial load
duke
parents:
diff changeset
181 const char *t = strchr(_sol,'\n')+1; // End of line
a61af66fc99e Initial load
duke
parents:
diff changeset
182 int off = 0; // Cursor offset for tab expansion
a61af66fc99e Initial load
duke
parents:
diff changeset
183 const char *s = _sol; // Nice string pointer
a61af66fc99e Initial load
duke
parents:
diff changeset
184 while( t-s ) { // Display whole line
a61af66fc99e Initial load
duke
parents:
diff changeset
185 char c = *s++; // Get next character to display
a61af66fc99e Initial load
duke
parents:
diff changeset
186 off = expandtab(os,off,c,' ',c);
a61af66fc99e Initial load
duke
parents:
diff changeset
187 }
a61af66fc99e Initial load
duke
parents:
diff changeset
188
a61af66fc99e Initial load
duke
parents:
diff changeset
189 // Display the tab-expanded skippings before underlining.
a61af66fc99e Initial load
duke
parents:
diff changeset
190 os << fname << ":" << line << ": ";
a61af66fc99e Initial load
duke
parents:
diff changeset
191 off = 0; // Cursor offset for tab expansion
a61af66fc99e Initial load
duke
parents:
diff changeset
192 s = _sol; // Restart string pointer
a61af66fc99e Initial load
duke
parents:
diff changeset
193
a61af66fc99e Initial load
duke
parents:
diff changeset
194 // Start underlining.
a61af66fc99e Initial load
duke
parents:
diff changeset
195 if( skip != -1 ) { // The no-start-indicating flag
a61af66fc99e Initial load
duke
parents:
diff changeset
196 const char *u = _sol+skip; // Amount to skip
a61af66fc99e Initial load
duke
parents:
diff changeset
197 while( u-s ) // Display skipped part
a61af66fc99e Initial load
duke
parents:
diff changeset
198 off = expandtab(os,off,*s++,' ',' ');
a61af66fc99e Initial load
duke
parents:
diff changeset
199 os << '^'; // Start region
a61af66fc99e Initial load
duke
parents:
diff changeset
200 off++; // Moved cursor
a61af66fc99e Initial load
duke
parents:
diff changeset
201 len--; // 1 less char to do
a61af66fc99e Initial load
duke
parents:
diff changeset
202 if( *s++ == '\t' ) // Starting character is a tab?
a61af66fc99e Initial load
duke
parents:
diff changeset
203 off = expandtab(os,off,'\t','-','^');
a61af66fc99e Initial load
duke
parents:
diff changeset
204 }
a61af66fc99e Initial load
duke
parents:
diff changeset
205
a61af66fc99e Initial load
duke
parents:
diff changeset
206 // Long region doesn't end on this line
a61af66fc99e Initial load
duke
parents:
diff changeset
207 int llen = (int)(t-s); // Length of line, minus what's already done
a61af66fc99e Initial load
duke
parents:
diff changeset
208 if( len > llen ) { // Doing entire rest of line?
a61af66fc99e Initial load
duke
parents:
diff changeset
209 while( t-s ) // Display rest of line
a61af66fc99e Initial load
duke
parents:
diff changeset
210 off = expandtab(os,off,*s++,'-','-');
a61af66fc99e Initial load
duke
parents:
diff changeset
211 os << '\n'; // EOL
a61af66fc99e Initial load
duke
parents:
diff changeset
212 return len-llen; // Return what's not yet done.
a61af66fc99e Initial load
duke
parents:
diff changeset
213 }
a61af66fc99e Initial load
duke
parents:
diff changeset
214
a61af66fc99e Initial load
duke
parents:
diff changeset
215 // Region does end on this line. This code fails subtly if the region ends
a61af66fc99e Initial load
duke
parents:
diff changeset
216 // in a tab character.
a61af66fc99e Initial load
duke
parents:
diff changeset
217 int i;
a61af66fc99e Initial load
duke
parents:
diff changeset
218 for( i=1; i<len; i++ ) // Underline just what's needed
a61af66fc99e Initial load
duke
parents:
diff changeset
219 off = expandtab(os,off,*s++,'-','-');
a61af66fc99e Initial load
duke
parents:
diff changeset
220 if( i == len ) os << '^'; // Mark end of region
a61af66fc99e Initial load
duke
parents:
diff changeset
221 os << '\n'; // End of marked line
603
dbbe28fc66b5 6778669: Patch from Red Hat -- fixes compilation errors
twisti
parents: 470
diff changeset
222 return 0; // All done
0
a61af66fc99e Initial load
duke
parents:
diff changeset
223 }
a61af66fc99e Initial load
duke
parents:
diff changeset
224
a61af66fc99e Initial load
duke
parents:
diff changeset
225 //------------------------------print------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
226 //std::ostream& operator<< ( std::ostream& os, FileBuffRegion &br ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
227 ostream& operator<< ( ostream& os, FileBuffRegion &br ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
228 if( &br == NULL ) return os; // The empty buffer region
a61af66fc99e Initial load
duke
parents:
diff changeset
229 FileBuffRegion *brp = &br; // Pointer to region
a61af66fc99e Initial load
duke
parents:
diff changeset
230 while( brp ) { // While have chained regions
a61af66fc99e Initial load
duke
parents:
diff changeset
231 brp->print(os); // Print region
a61af66fc99e Initial load
duke
parents:
diff changeset
232 brp = brp->_next; // Chain to next
a61af66fc99e Initial load
duke
parents:
diff changeset
233 }
a61af66fc99e Initial load
duke
parents:
diff changeset
234 return os; // Return final stream
a61af66fc99e Initial load
duke
parents:
diff changeset
235 }
a61af66fc99e Initial load
duke
parents:
diff changeset
236
a61af66fc99e Initial load
duke
parents:
diff changeset
237 //------------------------------print------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
238 // Print the FileBuffRegion to a stream. FileBuffRegions are printed with the
a61af66fc99e Initial load
duke
parents:
diff changeset
239 // filename and line number to the left, and complete text lines to the right.
a61af66fc99e Initial load
duke
parents:
diff changeset
240 // Selected portions (portions of a line actually in the FileBuffRegion are
a61af66fc99e Initial load
duke
parents:
diff changeset
241 // underlined. Ellipses are used for long multi-line regions.
a61af66fc99e Initial load
duke
parents:
diff changeset
242 //void FileBuffRegion::print( std::ostream& os ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
243 void FileBuffRegion::print( ostream& os ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
244 if( !this ) return; // Nothing to print
a61af66fc99e Initial load
duke
parents:
diff changeset
245 char *s = _bfr->get_line();
a61af66fc99e Initial load
duke
parents:
diff changeset
246 int skip = (int)(_offset - _sol); // Amount to skip to start of data
a61af66fc99e Initial load
duke
parents:
diff changeset
247 int len = printline( os, _bfr->_fp->_name, _line, s, skip, _length );
a61af66fc99e Initial load
duke
parents:
diff changeset
248
a61af66fc99e Initial load
duke
parents:
diff changeset
249 if( !len ) return; // All done; exit
a61af66fc99e Initial load
duke
parents:
diff changeset
250
a61af66fc99e Initial load
duke
parents:
diff changeset
251 // Here we require at least 2 lines
a61af66fc99e Initial load
duke
parents:
diff changeset
252 int off1 = _length - len + skip; // Length of line 1
a61af66fc99e Initial load
duke
parents:
diff changeset
253 int off2 = off1 + _sol; // Offset to start of line 2
a61af66fc99e Initial load
duke
parents:
diff changeset
254 char *s2 = _bfr->get_line(); // Start of line 2
a61af66fc99e Initial load
duke
parents:
diff changeset
255 char *s3 = strchr( s2, '\n' )+1; // Start of line 3 (unread)
a61af66fc99e Initial load
duke
parents:
diff changeset
256 if( len <= (s3-s2) ) { // It all fits on the next line
a61af66fc99e Initial load
duke
parents:
diff changeset
257 printline( os, _bfr->_fp->_name, _line+1, s2, -1, len ); // Print&underline
a61af66fc99e Initial load
duke
parents:
diff changeset
258 return;
a61af66fc99e Initial load
duke
parents:
diff changeset
259 }
a61af66fc99e Initial load
duke
parents:
diff changeset
260
a61af66fc99e Initial load
duke
parents:
diff changeset
261 // Here we require at least 3 lines
a61af66fc99e Initial load
duke
parents:
diff changeset
262 int off3 = off2 + (int)(s3-s2); // Offset to start of line 3
a61af66fc99e Initial load
duke
parents:
diff changeset
263 s3 = _bfr->get_line(); // Start of line 3 (read)
a61af66fc99e Initial load
duke
parents:
diff changeset
264 const char *s4 = strchr( s3, '\n' )+1;// Start of line 4 (unread)
a61af66fc99e Initial load
duke
parents:
diff changeset
265 if( len < (s4-s3) ) { // It all fits on the next 2 lines
a61af66fc99e Initial load
duke
parents:
diff changeset
266 s2 = _bfr->get_line();
a61af66fc99e Initial load
duke
parents:
diff changeset
267 len = printline( os, _bfr->_fp->_name, _line+1, s2, -1, len ); // Line 2
a61af66fc99e Initial load
duke
parents:
diff changeset
268 s3 = _bfr->get_line();
a61af66fc99e Initial load
duke
parents:
diff changeset
269 printline( os, _bfr->_fp->_name, _line+2, s3, -1, len ); // Line 3
a61af66fc99e Initial load
duke
parents:
diff changeset
270 return;
a61af66fc99e Initial load
duke
parents:
diff changeset
271 }
a61af66fc99e Initial load
duke
parents:
diff changeset
272
a61af66fc99e Initial load
duke
parents:
diff changeset
273 // Here we require at least 4 lines.
a61af66fc99e Initial load
duke
parents:
diff changeset
274 // Print only the 1st and last line, with ellipses in middle.
a61af66fc99e Initial load
duke
parents:
diff changeset
275 os << "...\n"; // The ellipses
a61af66fc99e Initial load
duke
parents:
diff changeset
276 int cline = _line+1; // Skipped 2 lines
a61af66fc99e Initial load
duke
parents:
diff changeset
277 do { // Do until find last line
a61af66fc99e Initial load
duke
parents:
diff changeset
278 len -= (int)(s3-s2); // Remove length of line
a61af66fc99e Initial load
duke
parents:
diff changeset
279 cline++; // Next line
a61af66fc99e Initial load
duke
parents:
diff changeset
280 s2 = _bfr->get_line(); // Get next line from end of this line
a61af66fc99e Initial load
duke
parents:
diff changeset
281 s3 = strchr( s2, '\n' ) + 1;// Get end of next line
a61af66fc99e Initial load
duke
parents:
diff changeset
282 } while( len > (s3-s2) ); // Repeat until last line
a61af66fc99e Initial load
duke
parents:
diff changeset
283 printline( os, _bfr->_fp->_name, cline, s2, -1, len ); // Print & underline
a61af66fc99e Initial load
duke
parents:
diff changeset
284 }
a61af66fc99e Initial load
duke
parents:
diff changeset
285
a61af66fc99e Initial load
duke
parents:
diff changeset
286 //------------------------------file_error-------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
287 void FileBuff::file_error(int flag, int linenum, const char *fmt, ...)
a61af66fc99e Initial load
duke
parents:
diff changeset
288 {
a61af66fc99e Initial load
duke
parents:
diff changeset
289 va_list args;
a61af66fc99e Initial load
duke
parents:
diff changeset
290
a61af66fc99e Initial load
duke
parents:
diff changeset
291 va_start(args, fmt);
a61af66fc99e Initial load
duke
parents:
diff changeset
292 switch (flag) {
a61af66fc99e Initial load
duke
parents:
diff changeset
293 case 0: _AD._warnings += _AD.emit_msg(0, flag, linenum, fmt, args);
a61af66fc99e Initial load
duke
parents:
diff changeset
294 case 1: _AD._syntax_errs += _AD.emit_msg(0, flag, linenum, fmt, args);
a61af66fc99e Initial load
duke
parents:
diff changeset
295 case 2: _AD._semantic_errs += _AD.emit_msg(0, flag, linenum, fmt, args);
a61af66fc99e Initial load
duke
parents:
diff changeset
296 default: assert(0, ""); break;
a61af66fc99e Initial load
duke
parents:
diff changeset
297 }
a61af66fc99e Initial load
duke
parents:
diff changeset
298 va_end(args);
a61af66fc99e Initial load
duke
parents:
diff changeset
299 _AD._no_output = 1;
a61af66fc99e Initial load
duke
parents:
diff changeset
300 }