ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/rxvt-unicode/src/rxvtutil.h
Revision: 1.26
Committed: Tue Jan 31 16:57:35 2006 UTC (18 years, 4 months ago) by root
Content type: text/plain
Branch: MAIN
CVS Tags: rel-7_6, rel-7_7
Changes since 1.25: +1 -1 lines
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 #ifndef RXVT_UTIL_H
2     #define RXVT_UTIL_H
3    
4 root 1.19 #include <cstdlib>
5 root 1.4 #include <cstring>
6    
7 root 1.15 #define PP_CONCAT_(a, b) a ## b
8     #define PP_CONCAT(a, b) PP_CONCAT_(a, b)
9     #define PP_STRINGIFY_(a) #a
10     #define PP_STRINGIFY(a) PP_STRINGIFY_(a)
11    
12 root 1.22 // actually, some gcc-3.x versions work, too
13     #define HAVE_GCC_BUILTINS (__GNUC__ >= 4)
14    
15 root 1.24 #ifndef __attribute__
16     # if __GNUC__
17     # if (__GNUC__ == 2 && __GNUC_MINOR__ < 5) || (__GNUC__ < 2)
18     # define __attribute__(x)
19     # endif
20     # endif
21     # define __attribute__(x)
22     #endif
23    
24     #define NORETURN __attribute__ ((noreturn))
25     #define UNUSED __attribute__ ((unused))
26     #define CONST __attribute__ ((const))
27    
28     // increases code size unless -fno-enforce-eh-specs
29     #if __GNUC__
30     # define NOTHROW
31     # define THROW(x)
32     #else
33     # define NOTHROW throw()
34     # define THROW(x) throw x
35     #endif
36    
37 root 1.1 extern class byteorder {
38     static unsigned int e; // at least 32 bits
39     public:
40     byteorder ();
41    
42     static bool big_endian () { return e == 0x11223344; };
43     static bool network () { return e == 0x11223344; };
44     static bool little_endian () { return e == 0x44332211; };
45     static bool vax () { return e == 0x44332211; };
46     } byteorder;
47    
48 root 1.16 // various utility functions
49 root 1.13 template<typename T, typename U> static inline T min (T a, U b) { return a < (T)b ? a : (T)b; }
50     template<typename T, typename U> static inline void min_it (T &a, U b) { a = a < (T)b ? a : (T)b; }
51     template<typename T, typename U> static inline T max (T a, U b) { return a > (T)b ? a : (T)b; }
52     template<typename T, typename U> static inline void max_it (T &a, U b) { a = a > (T)b ? a : (T)b; }
53    
54     template<typename T, typename U, typename V> static inline T clamp (T v, U a, V b) { return v < (T)a ? a : v >(T)b ? b : v; }
55     template<typename T, typename U, typename V> static inline void clamp_it (T &v, U a, V b) { v = v < (T)a ? a : v >(T)b ? b : v; }
56    
57 root 1.14 template<typename T, typename U> static inline void swap (T& a, U& b) { T t=a; a=(T)b; b=(U)t; }
58 root 1.8
59 root 1.25 template<typename T> static inline T squared_diff (T a, T b) { return (a-b)*(a-b); }
60    
61 root 1.21 // linear interpolation
62     template<typename T, typename U, typename P>
63     static inline
64     T lerp (T a, U b, P p)
65     {
66 root 1.26 return (long(a) * long(100 - p) + long(b) * long(p) + 50) / 100;
67 root 1.21 }
68    
69 root 1.22 // some bit functions, xft fuck me plenty
70     #if HAVE_GCC_BUILTINS
71 root 1.24 static inline int ctz (unsigned int x) CONST { return __builtin_ctz (x); }
72     static inline int popcount (unsigned int x) CONST { return __builtin_popcount (x); }
73 root 1.22 #else
74     // count trailing zero bits and count # of one bits
75 root 1.24 int ctz (unsigned int x) CONST;
76     int popcount (unsigned int x) CONST;
77 root 1.22 #endif
78    
79 root 1.11 // in range including end
80     #define IN_RANGE_INC(val,beg,end) \
81 root 1.9 ((unsigned int)(val) - (unsigned int)(beg) <= (unsigned int)(end) - (unsigned int)(beg))
82 root 1.1
83 root 1.11 // in range excluding end
84     #define IN_RANGE_EXC(val,beg,end) \
85     ((unsigned int)(val) - (unsigned int)(beg) < (unsigned int)(end) - (unsigned int)(beg))
86    
87 root 1.16 // makes dynamically allocated objects zero-initialised
88 root 1.4 struct zero_initialized {
89     void *operator new (size_t s);
90     void operator delete (void *p, size_t s);
91     };
92    
93     /* simplevec taken (and heavily modified), from:
94     *
95     * MICO --- a free CORBA implementation
96     * Copyright (C) 1997-98 Kay Roemer & Arno Puder
97     */
98     template<class T>
99     struct simplevec {
100     typedef T* iterator;
101     typedef const T* const_iterator;
102     typedef unsigned long size_type;
103    
104     private:
105     size_type _last, _size;
106     T *_buf;
107    
108     public:
109     const_iterator begin () const
110     {
111 root 1.8 return &_buf[0];
112 root 1.4 }
113     iterator begin ()
114     {
115 root 1.8 return &_buf[0];
116 root 1.4 }
117     const_iterator end () const
118     {
119 root 1.8 return &_buf[_last];
120 root 1.4 }
121     iterator end ()
122     {
123 root 1.8 return &_buf[_last];
124 root 1.4 }
125     size_type capacity () const
126     {
127 root 1.8 return _size;
128 root 1.4 }
129     size_type size () const
130     {
131 root 1.8 return _last;
132 root 1.4 }
133    
134     private:
135     static T *alloc (size_type n)
136     {
137 root 1.8 return (T *)::operator new ((size_t) (n * sizeof (T)));
138 root 1.4 }
139     static void dealloc (T *buf)
140     {
141 root 1.8 if (buf)
142     ::operator delete (buf);
143 root 1.4 }
144    
145     void reserve (iterator where, size_type n)
146     {
147 root 1.8 if (_last + n <= _size) {
148     memmove (where+n, where, (end ()-where)*sizeof (T));
149     } else {
150     size_type sz = _last+n;
151     sz = (_size == 0) ? max (sz, 5) : max (sz, 2*_size);
152     T *nbuf = alloc (sz);
153     if (_buf) {
154     memcpy (nbuf, begin (), (where-begin ())*sizeof (T));
155     memcpy (nbuf + (where-begin ()) + n, where,
156     (end ()-where)*sizeof (T));
157     dealloc (_buf);
158     }
159     _buf = nbuf;
160     _size = sz;
161     }
162 root 1.4 }
163    
164     public:
165     void reserve (size_type sz)
166     {
167 root 1.8 if (_size < sz) {
168     sz = (_size == 0) ? max (sz, 5) : max (sz, 2*_size);
169     T *nbuf = alloc (sz);
170     if (_buf) {
171     memcpy (nbuf, begin (), size ()*sizeof (T));
172     dealloc (_buf);
173     }
174     _buf = nbuf;
175     _size = sz;
176     }
177 root 1.4 }
178     simplevec ()
179     : _last(0), _size(0), _buf(0)
180     {
181     }
182     simplevec (size_type n, const T& t = T ())
183     : _last(0), _size(0), _buf(0)
184     {
185 root 1.8 insert (begin (), n, t);
186 root 1.4 }
187     simplevec (const_iterator first, const_iterator last)
188     : _last(0), _size(0), _buf(0)
189     {
190 root 1.8 insert (begin (), first, last);
191 root 1.4 }
192     simplevec (const simplevec<T> &v)
193     : _last(0), _size(0), _buf(0)
194     {
195 root 1.8 reserve (v._last);
196     memcpy (_buf, v.begin (), v.size ()*sizeof (T));
197     _last = v._last;
198 root 1.4 }
199     simplevec<T> &operator= (const simplevec<T> &v)
200     {
201 root 1.8 if (this != &v) {
202     _last = 0;
203     reserve (v._last);
204     memcpy (_buf, v.begin (), v.size ()*sizeof (T));
205     _last = v._last;
206     }
207 root 1.4 return *this;
208     }
209     ~simplevec ()
210     {
211 root 1.8 dealloc (_buf);
212 root 1.4 }
213     const T &front () const
214     {
215 root 1.8 //ministl_assert (size () > 0);
216     return _buf[0];
217 root 1.4 }
218     T &front ()
219     {
220 root 1.8 //ministl_assert (size () > 0);
221     return _buf[0];
222 root 1.4 }
223     const T &back () const
224     {
225 root 1.8 //ministl_assert (size () > 0);
226     return _buf[_last-1];
227 root 1.4 }
228     T &back ()
229     {
230 root 1.8 //ministl_assert (size () > 0);
231     return _buf[_last-1];
232 root 1.4 }
233     bool empty () const
234     {
235 root 1.8 return _last == 0;
236 root 1.4 }
237     void clear ()
238     {
239 root 1.8 _last = 0;
240 root 1.4 }
241     void push_back (const T &t)
242     {
243 root 1.8 reserve (_last+1);
244     *end () = t;
245     ++_last;
246 root 1.4 }
247     void push_back (T &t)
248     {
249 root 1.8 reserve (_last+1);
250     *end () = t;
251     ++_last;
252 root 1.4 }
253     void pop_back ()
254     {
255 root 1.8 //ministl_assert (size () > 0);
256     --_last;
257 root 1.4 }
258     const T &operator[] (size_type idx) const
259     {
260 root 1.8 //ministl_assert (idx < size ());
261     return _buf[idx];
262 root 1.4 }
263     T &operator[] (size_type idx)
264     {
265 root 1.8 //ministl_assert (idx < size ());
266     return _buf[idx];
267 root 1.4 }
268     iterator insert (iterator pos, const T &t)
269     {
270 root 1.8 //ministl_assert (pos <= end ());
271     long at = pos - begin ();
272     reserve (pos, 1);
273     pos = begin ()+at;
274     *pos = t;
275     ++_last;
276     return pos;
277 root 1.4 }
278     iterator insert (iterator pos, const_iterator first, const_iterator last)
279     {
280     //ministl_assert (pos <= end ());
281 root 1.8 long n = last - first;
282     long at = pos - begin ();
283     if (n > 0) {
284     reserve (pos, n);
285     pos = begin ()+at;
286     memcpy (pos, first, (last-first)*sizeof (T));
287     _last += n;
288     }
289     return pos;
290 root 1.4 }
291     iterator insert (iterator pos, size_type n, const T &t)
292     {
293     //ministl_assert (pos <= end ());
294 root 1.8 long at = pos - begin ();
295     if (n > 0) {
296     reserve (pos, n);
297     pos = begin ()+at;
298     for (int i = 0; i < n; ++i)
299     pos[i] = t;
300     _last += n;
301     }
302     return pos;
303 root 1.4 }
304     void erase (iterator first, iterator last)
305     {
306 root 1.8 if (last != first) {
307 root 1.18 memmove (first, last, (end () - last) * sizeof (T));
308 root 1.8 _last -= last - first;
309     }
310 root 1.4 }
311     void erase (iterator pos)
312     {
313     if (pos != end ()) {
314 root 1.18 memmove (pos, pos+1, (end () - (pos+1)) * sizeof (T));
315 root 1.4 --_last;
316     }
317     }
318 root 1.8 void swap (simplevec<T> &t)
319     {
320     ::swap(_last, t._last);
321     ::swap(_size, t._size);
322     ::swap(_buf, t._buf);
323     }
324 root 1.4 };
325    
326     template<class T>
327     bool operator== (const simplevec<T> &v1, const simplevec<T> &v2)
328     {
329     if (v1.size () != v2.size ())
330 root 1.8 return false;
331 root 1.4 return !v1.size () || !memcmp (&v1[0], &v2[0], v1.size ()*sizeof (T));
332     }
333    
334     template<class T>
335     bool operator< (const simplevec<T> &v1, const simplevec<T> &v2)
336     {
337     unsigned long minlast = min (v1.size (), v2.size ());
338     for (unsigned long i = 0; i < minlast; ++i) {
339     if (v1[i] < v2[i])
340 root 1.8 return true;
341     if (v2[i] < v1[i])
342     return false;
343 root 1.4 }
344     return v1.size () < v2.size ();
345     }
346    
347 root 1.1
348     template<typename T>
349     struct vector : simplevec<T>
350     { };
351    
352     #if 0
353     template<typename T>
354     struct rxvt_vec : simplevec<void *> {
355     typedef T *iterator;
356    
357     void push_back (T d) { simplevec<void *>::push_back ((void *)d); }
358     T pop_back () { return (T*)simplevec<void *>::pop_back (); }
359     void erase (int i) { erase (begin () + i); }
360     void erase (iterator i) { simplevec<void *>::erase ((void **)i); }
361     iterator begin () const { return (iterator)simplevec<void *>::begin (); }
362     iterator end () const { return (iterator)simplevec<void *>::end (); }
363     T &operator [] (int i) { return * (T *) (& ((* (simplevec<void *> *)this)[i])); }
364     const T &operator [] (int i) const { return * (const T *) (& ((* (const simplevec<void *> *)this)[i])); }
365     };
366     #endif
367    
368     template <typename I, typename T>
369     I find (I first, I last, const T& value)
370     {
371     while (first != last && *first != value)
372     ++first;
373    
374     return first;
375     }
376    
377     template<typename T>
378     struct auto_ptr {
379     T *p;
380    
381     auto_ptr () : p (0) { }
382     auto_ptr (T *a) : p (a) { }
383    
384     auto_ptr (auto_ptr<T> &a)
385     {
386     p = a.p;
387     a.p = 0;
388     }
389    
390     template<typename A>
391     auto_ptr (auto_ptr<A> &a)
392     {
393     p = a.p;
394     a.p = 0;
395     }
396    
397     ~auto_ptr ()
398     {
399     delete p;
400     }
401    
402     // void because it makes sense in our context
403     void operator = (T *a)
404     {
405     delete p;
406     p = a;
407     }
408    
409     void operator = (auto_ptr &a)
410     {
411     *this = a.p;
412     a.p = 0;
413     }
414    
415     template<typename A>
416     void operator = (auto_ptr<A> &a)
417     {
418     *this = a.p;
419     a.p = 0;
420     }
421    
422     operator T * () const { return p; }
423    
424     T *operator -> () const { return p; }
425     T &operator * () const { return *p; }
426    
427     T *get ()
428     {
429     T *r = p;
430     p = 0;
431     return r;
432     }
433     };
434    
435     typedef auto_ptr<char> auto_str;
436    
437     struct stringvec : simplevec<char *>
438     {
439     ~stringvec ()
440     {
441     for (char **c = begin (); c != end (); c++)
442 root 1.19 free (*c);
443 root 1.1 }
444     };
445 root 1.3
446 root 1.20 // return a very temporary (and never deallocated) buffer. keep small.
447     void *rxvt_temp_buf (int len);
448    
449     template<typename T>
450 root 1.24 static inline T *
451 root 1.20 rxvt_temp_buf (int len)
452     {
453     return (T *)rxvt_temp_buf (len * sizeof (T));
454     }
455    
456 root 1.1 #endif
457