xref: /haiku/src/kits/tracker/AttributeStream.h (revision db41683495bfde817554415d14ae6f9cc91e77eb)
1 /*
2 Open Tracker License
3 
4 Terms and Conditions
5 
6 Copyright (c) 1991-2000, Be Incorporated. All rights reserved.
7 
8 Permission is hereby granted, free of charge, to any person obtaining a copy of
9 this software and associated documentation files (the "Software"), to deal in
10 the Software without restriction, including without limitation the rights to
11 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
12 of the Software, and to permit persons to whom the Software is furnished to do
13 so, subject to the following conditions:
14 
15 The above copyright notice and this permission notice applies to all licensees
16 and shall be included in all copies or substantial portions of the Software.
17 
18 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF TITLE, MERCHANTABILITY,
20 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 BE INCORPORATED BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF, OR IN CONNECTION
23 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 
25 Except as contained in this notice, the name of Be Incorporated shall not be
26 used in advertising or otherwise to promote the sale, use or other dealings in
27 this Software without prior written authorization from Be Incorporated.
28 
29 Tracker(TM), Be(R), BeOS(R), and BeIA(TM) are trademarks or registered trademarks
30 of Be Incorporated in the United States and other countries. Other brand product
31 names are registered trademarks or trademarks of their respective holders.
32 All rights reserved.
33 */
34 
35 //	attribute streams allow copying/filtering/transformation of attributes
36 //	between file and/or memory nodes
37 //
38 //	for example one can use constructs of nodes like:
39 //
40 // 	destinationNode << transformer << buffer << filter << sourceNode
41 //
42 //	transformer may for instance perform endian-swapping or offsetting of
43 //	a B_RECT attribute filter may withold certain attributes buffer is a
44 //	memory allocated snapshot of attributes, may be repeatedly streamed into
45 //	other files, buffers
46 //
47 //	In addition to the whacky (but usefull) << syntax, calls like Read, Write
48 //	are also available
49 #ifndef __ATTRIBUTE_STREAM__
50 #define __ATTRIBUTE_STREAM__
51 
52 
53 #include <Node.h>
54 #include <Rect.h>
55 #include <String.h>
56 #include <TypeConstants.h>
57 
58 #include <fs_attr.h>
59 
60 #include "ObjectList.h"
61 
62 
63 namespace BPrivate {
64 
65 struct AttributeTemplate {
66 	// used for read-only attribute source
67 	const char* fAttributeName;
68 	uint32 fAttributeType;
69 	off_t fSize;
70 	const char* fBits;
71 };
72 
73 
74 class AttributeInfo {
75 	// utility class for internal attribute description
76 public:
77 	AttributeInfo()
78 		{}
79 	AttributeInfo(const AttributeInfo &);
80 	AttributeInfo(const char*, attr_info);
81 	AttributeInfo(const char*, uint32, off_t);
82 
83 	void SetTo(const AttributeInfo &);
84 	void SetTo(const char*, attr_info);
85 	void SetTo(const char*, uint32, off_t);
86 	const char* Name() const;
87 	uint32 Type() const;
88 	off_t Size() const;
89 
90 private:
91 	BString fName;
92 	attr_info fInfo;
93 };
94 
95 
96 class AttributeStreamNode {
97 public:
98 	AttributeStreamNode();
99 	virtual ~AttributeStreamNode();
100 
101 	AttributeStreamNode &operator<<(AttributeStreamNode &source);
102 		// workhorse call
103 		// to the outside makes this node a part of the stream, passing on
104 		// any data it has, gets, transforms, doesn't filter out
105 		//
106 		// under the hood sets up streaming into the next node; hooking
107 		// up source and destination, forces the stream head to start
108 		// streaming
109 
110 	virtual void Rewind();
111 		// get ready to start all over again
112 	virtual void MakeEmpty() {}
113 		// remove any attributes the node may have
114 
115 	virtual off_t Contains(const char*, uint32);
116 		// returns size of attribute if found
117 
118 	virtual off_t Read(const char* name, const char* foreignName,
119 		uint32 type, off_t size, void* buffer, void (*swapFunc)(void*) = 0);
120 		// read from this node
121 	virtual off_t Write(const char* name, const char* foreignName,
122 		uint32 type, off_t size, const void* buffer);
123 		// write to this node
124 
125 	// work calls
126 	virtual bool Drive();
127 		// node at the head of the stream makes the entire stream
128 		// feed it
129 	virtual const AttributeInfo* Next();
130 		// give me the next attribute in the stream
131 	virtual const char* Get();
132 		// give me the data of the attribute in the stream that was just
133 		// returned by Next assumes there is a buffering node somewhere on the
134 		// way to the source, from which the resulting buffer is borrowed
135 	virtual bool Fill(char* buffer) const;
136 		// fill the buffer with data of the attribute in the stream that was
137 		// just returned by next <buffer> is big enough to hold the entire
138 		// attribute data
139 
140 	virtual bool CanFeed() const { return false; }
141 		// return true if can work as a source for the entire stream
142 
143 private:
144 	bool Start();
145 		// utility call, used to start up the stream by finding the ultimate
146 		// target of the stream and calling Drive on it
147 
148 	void Detach();
149 
150 protected:
151 	AttributeStreamNode* fReadFrom;
152 	AttributeStreamNode* fWriteTo;
153 };
154 
155 
156 class AttributeStreamFileNode : public AttributeStreamNode {
157 	// handles reading and writing attributes to and from the
158 	// stream
159 public:
160 	AttributeStreamFileNode();
161 	AttributeStreamFileNode(BNode*);
162 
163 	virtual void MakeEmpty();
164 	virtual void Rewind();
165 	virtual off_t Contains(const char* name, uint32 type);
166 	virtual off_t Read(const char* name, const char* foreignName, uint32 type,
167 		off_t size, void* buffer, void (*swapFunc)(void*) = 0);
168 	virtual off_t Write(const char* name, const char* foreignName, uint32 type,
169 		off_t size, const void* buffer);
170 
171 	void SetTo(BNode*);
172 
173 	BNode* Node()
174 		{ return fNode; }
175 
176 protected:
177 	virtual bool CanFeed() const { return true; }
178 
179 	virtual bool Drive();
180 		// give me all the attributes, I'll write them into myself
181 	virtual const AttributeInfo* Next();
182 		// return the info for the next attribute I can read for you
183 	virtual const char* Get();
184 	virtual bool Fill(char* buffer) const;
185 
186 private:
187 	AttributeInfo fCurrentAttr;
188 	BNode* fNode;
189 
190 	typedef AttributeStreamNode _inherited;
191 };
192 
193 
194 class AttributeStreamMemoryNode : public AttributeStreamNode {
195 	// in memory attribute buffer; can be both target of writing and source
196 	// of reading at the same time
197 public:
198 	AttributeStreamMemoryNode();
199 
200 	virtual void MakeEmpty();
201 	virtual off_t Contains(const char* name, uint32 type);
202 	virtual off_t Read(const char* name, const char* foreignName,
203 		uint32 type, off_t size, void* buffer, void (*swapFunc)(void*) = 0);
204 	virtual off_t Write(const char* name, const char* foreignName,
205 		uint32 type, off_t size, const void* buffer);
206 
207 protected:
208 	virtual bool CanFeed() const { return true; }
209 	virtual void Rewind();
210 	virtual bool Drive();
211 	virtual const AttributeInfo* Next();
212 	virtual const char* Get();
213 	virtual bool Fill(char* buffer) const;
214 
215 	class AttrNode {
216 	public:
217 		AttrNode(const char* name, uint32 type, off_t size, char* data)
218 			:	fAttr(name, type, size),
219 				fData(data)
220 			{
221 			}
222 
223 		~AttrNode()
224 			{
225 				delete [] fData;
226 			}
227 
228 		AttributeInfo fAttr;
229 		char* fData;
230 	};
231 
232 		// utility calls
233 	virtual AttrNode* BufferingGet();
234 	virtual AttrNode* BufferingGet(const char* name, uint32 type, off_t size);
235 	int32 Find(const char* name, uint32 type) const;
236 
237 private:
238 	BObjectList<AttrNode> fAttributes;
239 	int32 fCurrentIndex;
240 
241 	typedef AttributeStreamNode _inherited;
242 };
243 
244 
245 class AttributeStreamTemplateNode : public AttributeStreamNode {
246 	// in read-only memory attribute source
247 	// can only be used as a source for Next and Get
248 public:
249 	AttributeStreamTemplateNode(const AttributeTemplate*, int32 count);
250 
251 	virtual off_t Contains(const char* name, uint32 type);
252 
253 protected:
254 	virtual bool CanFeed() const { return true; }
255 	virtual void Rewind();
256 	virtual const AttributeInfo* Next();
257 	virtual const char* Get();
258 	virtual bool Fill(char* buffer) const;
259 
260 	int32 Find(const char* name, uint32 type) const;
261 
262 private:
263 	AttributeInfo fCurrentAttr;
264 	const AttributeTemplate* fAttributes;
265 	int32 fCurrentIndex;
266 	int32 fCount;
267 
268 	typedef AttributeStreamNode _inherited;
269 };
270 
271 
272 class AttributeStreamFilterNode : public AttributeStreamNode {
273 	// filter node may not pass thru specified attributes
274 public:
275 	AttributeStreamFilterNode()
276 		{}
277 	virtual off_t Contains(const char* name, uint32 type);
278 	virtual off_t Read(const char* name, const char* foreignName,
279 		uint32 type, off_t size, void* buffer, void (*swapFunc)(void*) = 0);
280 	virtual off_t Write(const char* name, const char* foreignName,
281 		uint32 type, off_t size, const void* buffer);
282 
283 protected:
284 	virtual bool Reject(const char* name, uint32 type, off_t size);
285 		// override to implement filtering
286 	virtual const AttributeInfo* Next();
287 
288 private:
289 	typedef AttributeStreamNode _inherited;
290 };
291 
292 
293 class NamesToAcceptAttrFilter : public AttributeStreamFilterNode {
294 	// filter node that only passes thru attributes that match
295 	// a list of names
296 public:
297 	NamesToAcceptAttrFilter(const char**);
298 
299 protected:
300 	virtual bool Reject(const char* name, uint32 type, off_t size);
301 
302 private:
303 	const char** fNameList;
304 };
305 
306 
307 class SelectiveAttributeTransformer : public AttributeStreamNode {
308 	// node applies a transformation on specified attributes
309 public:
310 	SelectiveAttributeTransformer(const char* attributeName,
311 		bool (*)(const char*, uint32 , off_t , void*, void*), void* params);
312 	virtual ~SelectiveAttributeTransformer();
313 
314 	virtual off_t Read(const char* name, const char* foreignName, uint32 type,
315 		off_t size, void* buffer, void (*swapFunc)(void*) = 0);
316 
317 	virtual void Rewind();
318 
319 protected:
320 	virtual bool WillTransform(const char* name, uint32 type, off_t size,
321 		const char* data) const;
322 		// override to implement filtering, should only return true if
323 		// transformation will occur
324 	virtual char* CopyAndApplyTransformer(const char* name, uint32 type,
325 		off_t size, const char* data);
326 		// makes a copy of data
327 	virtual bool ApplyTransformer(const char* name, uint32 type, off_t size,
328 		char* data);
329 		// transforms in place
330 	virtual const AttributeInfo* Next();
331 	virtual const char* Get();
332 
333 private:
334 	AttributeInfo fCurrentAttr;
335 	const char* fAttributeNameToTransform;
336 	bool (*fTransformFunc)(const char*, uint32 , off_t , void*, void*);
337 	void* fTransformParams;
338 
339 	BObjectList<char> fTransformedBuffers;
340 
341 	typedef AttributeStreamNode _inherited;
342 };
343 
344 
345 template <class Type>
346 class AttributeStreamConstValue : public AttributeStreamNode {
347 public:
348 	AttributeStreamConstValue(const char* name, uint32 attributeType,
349 		Type value);
350 
351 protected:
352 	virtual bool CanFeed() const { return true; }
353 	virtual void Rewind() { fRewound = true; }
354 	virtual const AttributeInfo* Next();
355 	virtual const char* Get();
356 	virtual bool Fill(char* buffer) const;
357 
358 	int32 Find(const char* name, uint32 type) const;
359 
360 private:
361 	AttributeInfo fAttr;
362 	Type fValue;
363 	bool fRewound;
364 
365 	typedef AttributeStreamNode _inherited;
366 };
367 
368 
369 template<class Type>
370 AttributeStreamConstValue<Type>::AttributeStreamConstValue(const char* name,
371 	uint32 attributeType, Type value)
372 	:	fAttr(name, attributeType, sizeof(Type)),
373 		fValue(value),
374 		fRewound(true)
375 {
376 }
377 
378 
379 template<class Type>
380 const AttributeInfo*
381 AttributeStreamConstValue<Type>::Next()
382 {
383 	if (!fRewound)
384 		return NULL;
385 
386 	fRewound = false;
387 	return &fAttr;
388 }
389 
390 
391 template<class Type>
392 const char*
393 AttributeStreamConstValue<Type>::Get()
394 {
395 	return (const char*)&fValue;
396 }
397 
398 
399 template<class Type>
400 bool
401 AttributeStreamConstValue<Type>::Fill(char* buffer) const
402 {
403 	memcpy(buffer, &fValue, sizeof(Type));
404 	return true;
405 }
406 
407 
408 template<class Type>
409 int32
410 AttributeStreamConstValue<Type>::Find(const char* name, uint32 type) const
411 {
412 	if (strcmp(fAttr.Name(), name) == 0 && type == fAttr.Type())
413 		return 0;
414 
415 	return -1;
416 }
417 
418 
419 class AttributeStreamBoolValue : public AttributeStreamConstValue<bool> {
420 public:
421 	AttributeStreamBoolValue(const char* name, bool value)
422 		:	AttributeStreamConstValue<bool>(name, B_BOOL_TYPE, value)
423 		{}
424 };
425 
426 
427 class AttributeStreamInt32Value : public AttributeStreamConstValue<int32> {
428 public:
429 	AttributeStreamInt32Value(const char* name, int32 value)
430 		:	AttributeStreamConstValue<int32>(name, B_INT32_TYPE, value)
431 		{}
432 };
433 
434 
435 class AttributeStreamInt64Value : public AttributeStreamConstValue<int64> {
436 public:
437 	AttributeStreamInt64Value(const char* name, int64 value)
438 		:	AttributeStreamConstValue<int64>(name, B_INT64_TYPE, value)
439 		{}
440 };
441 
442 
443 class AttributeStreamRectValue : public AttributeStreamConstValue<BRect> {
444 public:
445 	AttributeStreamRectValue(const char* name, BRect value)
446 		:	AttributeStreamConstValue<BRect>(name, B_RECT_TYPE, value)
447 		{}
448 };
449 
450 
451 class AttributeStreamFloatValue : public AttributeStreamConstValue<float> {
452 public:
453 	AttributeStreamFloatValue(const char* name, float value)
454 		:	AttributeStreamConstValue<float>(name, B_FLOAT_TYPE, value)
455 		{}
456 };
457 
458 } // namespace BPrivate
459 
460 using namespace BPrivate;
461 
462 #endif
463