1
2
3
4
5
6
7
8 package it.imolinfo.jbi4corba.jbi.cxf;
9
10 import java.io.IOException;
11 import java.io.LineNumberReader;
12 import java.net.URL;
13 import java.util.HashSet;
14 import java.util.Set;
15 import java.util.Stack;
16
17 import org.apache.cxf.tools.corba.idlpreprocessor.DefineState;
18 import org.apache.cxf.tools.corba.idlpreprocessor.IncludeResolver;
19 import org.apache.cxf.tools.corba.idlpreprocessor.PreprocessingException;
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35 public final class Jbi4CorbaIdlPreprocessor
36
37
38
39
40 private static final int MAX_INCLUDE_DEPTH = 64;
41
42
43
44
45
46
47 private static final char PUSH = '1';
48
49
50
51
52
53
54 private static final char POP = '2';
55
56 private static final String LF = System.getProperty("line.separator");
57
58 private final IncludeResolver includeResolver;
59
60 private final Stack<Jbi4CorbaIncludeStackEntry> includeStack = new Stack<Jbi4CorbaIncludeStackEntry>();
61
62 private final Set<String> includeSet=new HashSet<String>();
63
64 private final Set<URL> idlSet=new HashSet<URL>();
65
66
67
68
69
70
71
72 private final Stack<Boolean> ifStack = new Stack<Boolean>();
73
74 private final DefineState defineState;
75
76 private int readPos;
77
78 private static final String ORBFNAME = "orb.idl";
79 private static final String IRFNAME = "ir.idl";
80
81
82
83
84
85
86
87
88
89
90 public Jbi4CorbaIdlPreprocessor(URL startURL, String startLocation,
91 IncludeResolver resolver, DefineState state) throws IOException {
92 this.includeResolver = resolver;
93 this.defineState = state;
94 pushInclude(startURL, startLocation);
95 fillBuffer();
96 }
97
98
99
100
101
102
103
104
105 private void pushInclude(URL url, String location) throws IOException {
106 final Jbi4CorbaIncludeStackEntry includeStackEntry = new Jbi4CorbaIncludeStackEntry(
107 url, location);
108 includeStack.push(includeStackEntry);
109
110 }
111
112
113
114 private void fillBuffer() throws IOException {
115 while (!includeStack.isEmpty()) {
116 LineNumberReader reader = getReader();
117 final int lineNo = reader.getLineNumber();
118 String line = reader.readLine();
119
120 if (line == null) {
121 popInclude();
122 continue;
123 }
124
125 if (!line.trim().startsWith("#")) {
126 continue;
127 }
128
129 final Jbi4CorbaIncludeStackEntry ise = includeStack.peek();
130 line = line.trim();
131
132 if (line.startsWith("#include") && (line.contains(ORBFNAME) || line.contains(IRFNAME))) {
133
134 if(!idlSet.contains(getCurrentURL())){
135 idlSet.add(getCurrentURL());
136 }
137
138 }
139
140 else if (line.startsWith("#include")) {
141 handleInclude(line, lineNo, ise);
142 }
143
144 }
145 }
146
147
148
149
150 private void handleInclude(String line, int lineNo,
151 final Jbi4CorbaIncludeStackEntry ise) throws IOException {
152
153 if (skips()) {
154
155 return;
156 }
157
158 if (includeStack.size() >= MAX_INCLUDE_DEPTH) {
159 throw new PreprocessingException(
160 "more than "
161 + MAX_INCLUDE_DEPTH
162 + " nested #includes - assuming infinite recursion, aborting",
163 ise.getURL(), lineNo);
164 }
165
166 String arg = line.replaceFirst("#include", "").trim();
167 if (arg.length() == 0) {
168 throw new PreprocessingException("#include without an argument",
169 ise.getURL(), lineNo);
170 }
171
172 char first = arg.charAt(0);
173 final int lastIdx = arg.length() - 1;
174 char last = arg.charAt(lastIdx);
175 if (arg.length() < 3 || !(first == '<' && last == '>')
176 && !(first == '"' && last == '"')) {
177 throw new PreprocessingException(
178 "argument for '#include' must be enclosed in '< >' or '\" \"'",
179 ise.getURL(), lineNo);
180 }
181 String spec = arg.substring(1, lastIdx);
182
183 URL include = (first == '<') ? includeResolver.findSystemInclude(spec)
184 : includeResolver.findUserInclude(spec);
185
186 if (include == null) {
187 throw new PreprocessingException("unable to resolve include '"
188 + spec + "'", ise.getURL(), lineNo);
189 }
190
191 pushInclude(include, spec);
192
193 if(!includeSet.contains(spec)){
194 includeSet.add(spec);
195 }
196
197 }
198
199 private void popInclude() throws IOException {
200 final Jbi4CorbaIncludeStackEntry poppedStackEntry = includeStack.pop();
201 try {
202 if (includeStack.size() > 0) {
203 final Jbi4CorbaIncludeStackEntry newTopEntry = includeStack
204 .peek();
205 final LineNumberReader reader = getReader();
206
207
208 }
209 } finally {
210 poppedStackEntry.getReader().close();
211 }
212 }
213
214 private boolean skips() {
215 if (ifStack.isEmpty()) {
216 return false;
217 }
218
219 return ifStack.peek();
220 }
221
222
223 private LineNumberReader getReader() {
224 Jbi4CorbaIncludeStackEntry topOfStack = includeStack.peek();
225 return topOfStack.getReader();
226 }
227
228 private URL getCurrentURL(){
229 Jbi4CorbaIncludeStackEntry topOfStack = includeStack.peek();
230 return topOfStack.getURL();
231 }
232
233
234
235
236
237
238 public Set<String> getIncludesPath() {
239 return includeSet;
240 }
241
242
243
244
245 public Set<URL> getIdlURL(){
246 return idlSet;
247 }
248
249 }