1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 package org.metricshub.wbem.sblim.slp.internal.msg;
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46 import java.io.ByteArrayOutputStream;
47 import java.util.ArrayList;
48 import java.util.Iterator;
49 import java.util.List;
50 import org.metricshub.wbem.sblim.slp.ServiceLocationAttribute;
51 import org.metricshub.wbem.sblim.slp.ServiceType;
52 import org.metricshub.wbem.sblim.slp.ServiceURL;
53 import org.metricshub.wbem.sblim.slp.internal.AttributeHandler;
54 import org.metricshub.wbem.sblim.slp.internal.Convert;
55 import org.metricshub.wbem.sblim.slp.internal.TRC;
56
57
58
59
60
61 public class SLPOutputStream {
62 private static final int MAX_FIELD_SIZE = 65535;
63
64 private static final byte[] EMPTY_BYTES = new byte[0];
65
66 private ByteArrayOutputStream iOutStr = new ByteArrayOutputStream();
67
68 private int iStreamLimit;
69
70
71
72
73 public SLPOutputStream() {
74 this(Integer.MAX_VALUE);
75 }
76
77
78
79
80
81
82 public SLPOutputStream(int pStreamLimit) {
83 this.iStreamLimit = pStreamLimit <= 0 ? Integer.MAX_VALUE : pStreamLimit;
84 }
85
86
87
88
89
90
91 public int size() {
92 return this.iOutStr.size();
93 }
94
95
96
97
98
99
100 public int freeSpace() {
101 return this.iStreamLimit - this.iOutStr.size();
102 }
103
104
105
106
107
108
109 public byte[] toByteArray() {
110 return this.iOutStr.toByteArray();
111 }
112
113
114
115
116
117
118
119 public boolean write(byte[] pBytes) {
120 if (freeSpace() < pBytes.length) return false;
121 writeNoChk(pBytes);
122 return true;
123 }
124
125
126
127
128
129
130
131 public boolean write(ServiceType pServType) {
132 if (pServType == null) return write((String) null);
133 return write(pServType.toString());
134 }
135
136
137
138
139 public static final int URL_HDR_LENGTH = 6;
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155 public boolean write(ServiceURL pURL) {
156
157 String urlStr = pURL.toString();
158 byte[] urlStrBytes = Convert.getBytes(urlStr);
159 if (freeSpace() < URL_HDR_LENGTH + urlStrBytes.length) return false;
160 writeNoChk8(0);
161 writeNoChk16(pURL.getLifetime());
162 writeNoChk16(urlStrBytes.length);
163 writeNoChk(urlStrBytes);
164 writeNoChk8(0);
165 return true;
166 }
167
168
169
170
171
172
173
174 @SuppressWarnings("null")
175 public boolean writeURLList(List<?> pURLList) {
176 int cnt = pURLList == null ? 0 : pURLList.size();
177 if (cnt == 0) return write16(cnt);
178 SLPOutputStream tmpStr = new SLPOutputStream();
179 int i;
180 for (i = 0; i < cnt; i++) {
181 tmpStr.write((ServiceURL) pURLList.get(i));
182 if (freeSpace() < tmpStr.size() + 2) break;
183 }
184 writeNoChk16(i);
185 writeNoChk(tmpStr.toByteArray());
186 return i == cnt;
187 }
188
189
190
191
192
193
194
195 public boolean writeServTypeList(List<?> pServTypeList) {
196 return writeServTypeList(pServTypeList == null ? null : pServTypeList.iterator());
197 }
198
199
200
201
202
203
204
205 public boolean writeServTypeList(Iterator<?> pServTypeItr) {
206 if (pServTypeItr == null) return writeStringList((Iterator<String>) null);
207 ArrayList<String> servTypeList = new ArrayList<String>();
208 while (pServTypeItr.hasNext()) servTypeList.add(((ServiceType) pServTypeItr.next()).toString());
209 return writeStringList(servTypeList);
210 }
211
212
213
214
215
216
217
218 public boolean writeAttributeList(List<?> pAttrList) {
219 return writeAttributeList(pAttrList == null ? null : pAttrList.iterator());
220 }
221
222
223
224
225
226
227
228 public boolean writeAttributeList(Iterator<?> pAttrItr) {
229 if (pAttrItr == null) return writeStringList((Iterator<String>) null);
230 ArrayList<String> attrStrList = new ArrayList<String>();
231 while (pAttrItr.hasNext()) attrStrList.add(
232 AttributeHandler.buildString((ServiceLocationAttribute) pAttrItr.next())
233 );
234 return writeStringList(attrStrList, null);
235 }
236
237
238
239
240
241
242
243 public boolean writeAuthBlockList(List<?> pAuthBlockList) {
244 int cnt = pAuthBlockList == null ? 0 : pAuthBlockList.size();
245 if (cnt != 0) TRC.error("Handling of non empty authentication block list is not implemented!");
246 return write8(0);
247 }
248
249
250
251
252
253
254
255 public boolean write(String pStr) {
256 return write(pStr, Convert.DEFAULT_RESERVED);
257 }
258
259
260
261
262
263
264
265
266 public boolean write(String pStr, String pReservedChars) {
267 byte[] bytes = pStr == null ? EMPTY_BYTES : Convert.getBytes(Convert.escape(pStr, pReservedChars));
268 if (bytes.length > MAX_FIELD_SIZE) return false;
269 if (freeSpace() < bytes.length + 2) return false;
270 writeNoChk16(bytes.length);
271 writeNoChk(bytes);
272 return true;
273 }
274
275
276
277
278
279
280
281 public boolean writeStringList(List<String> pStrList) {
282 return writeStringList(pStrList == null ? null : pStrList.iterator());
283 }
284
285
286
287
288
289
290
291 public boolean writeStringList(Iterator<String> pStrListItr) {
292 return writeStringList(pStrListItr, Convert.DEFAULT_RESERVED);
293 }
294
295
296
297
298
299
300
301
302 public boolean writeStringList(List<String> pStrList, String pReservedChars) {
303 return writeStringList(pStrList == null ? null : pStrList.iterator(), pReservedChars);
304 }
305
306
307
308
309
310
311
312
313 public boolean writeStringList(Iterator<String> pStrListItr, String pReservedChars) {
314 ByteArrayOutputStream listByteStr = new ByteArrayOutputStream();
315 boolean first = true;
316 boolean allWritten = true;
317 if (pStrListItr != null) while (pStrListItr.hasNext()) {
318 StringBuffer strBuf = new StringBuffer();
319 String listItemStr = Convert.escape(pStrListItr.next(), pReservedChars);
320 if (first) {
321 first = false;
322 } else {
323 strBuf.append(',');
324 }
325 strBuf.append(listItemStr);
326 byte[] listItemBytes = Convert.getBytes(strBuf.toString());
327 int currentSize = listByteStr.size() + listItemBytes.length;
328 if (currentSize > MAX_FIELD_SIZE || currentSize + 2 > freeSpace()) {
329 allWritten = false;
330 break;
331 }
332 listByteStr.write(listItemBytes, 0, listItemBytes.length);
333 }
334 byte[] listBytes = listByteStr.toByteArray();
335 writeNoChk16(listBytes.length);
336 writeNoChk(listBytes);
337 return allWritten;
338 }
339
340
341
342
343
344
345
346 public boolean write8(int pValue) {
347 if (freeSpace() < 1) return false;
348 writeNoChk8(pValue);
349 return true;
350 }
351
352
353
354
355
356
357
358 public boolean write16(int pValue) {
359 if (freeSpace() < 2) return false;
360 writeNoChk16(pValue);
361 return true;
362 }
363
364
365
366
367
368
369
370 public boolean write24(int pValue) {
371 if (freeSpace() < 3) return false;
372 writeNoChk24(pValue);
373 return true;
374 }
375
376
377
378
379
380
381
382 public boolean write32(long pValue) {
383 if (freeSpace() < 4) return false;
384 writeNoChk32(pValue);
385 return true;
386 }
387
388
389
390
391
392
393 public void writeNoChk(byte[] pBytes) {
394 this.iOutStr.write(pBytes, 0, pBytes.length);
395 }
396
397
398
399
400
401
402 public void writeNoChk8(int pValue) {
403 this.iOutStr.write(pValue);
404 }
405
406
407
408
409
410
411 public void writeNoChk16(int pValue) {
412 this.iOutStr.write((pValue >> 8) & 0xff);
413 this.iOutStr.write((pValue & 0xff));
414 }
415
416
417
418
419
420
421 public void writeNoChk24(int pValue) {
422 this.iOutStr.write((pValue >> 16) & 0xff);
423 writeNoChk16(pValue);
424 }
425
426
427
428
429
430
431 public void writeNoChk32(long pValue) {
432 this.iOutStr.write((int) ((pValue >> 24) & 0xff));
433 writeNoChk24((int) pValue);
434 }
435 }