fac30bbc8cdbeaf91d2281626976c1a6330d523e
[shibboleth/cpp-xmltooling.git] / xmltooling / char_traits.h
1 /*
2  *  Copyright 2001-2009 Internet2
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 /**
18  * @file xmltooling/char_traits.h
19  *
20  * Traits template for basic_string<unsigned short> instantiation on strict compilers.
21  */
22
23 #ifndef __xmltooling_chartraits_h__
24 #define __xmltooling_chartraits_h__
25
26 #include <xmltooling/base.h>
27
28 #include <cstring>
29 #include <algorithm>
30
31 namespace xmltooling {
32
33   /// @cond OFF
34
35   template <class _CharT>
36     struct _Char_types
37     {
38       typedef unsigned long   int_type;
39       typedef std::streampos  pos_type;
40       typedef std::streamoff  off_type;
41       typedef std::mbstate_t  state_type;
42     };
43
44
45   template<typename _CharT>
46     struct char_traits
47     {
48       typedef _CharT                                    char_type;
49       typedef typename _Char_types<_CharT>::int_type    int_type;
50       typedef typename _Char_types<_CharT>::pos_type    pos_type;
51       typedef typename _Char_types<_CharT>::off_type    off_type;
52       typedef typename _Char_types<_CharT>::state_type  state_type;
53
54       static void
55       assign(char_type& __c1, const char_type& __c2)
56       { __c1 = __c2; }
57
58       static bool
59       eq(const char_type& __c1, const char_type& __c2)
60       { return __c1 == __c2; }
61
62       static bool
63       lt(const char_type& __c1, const char_type& __c2)
64       { return __c1 < __c2; }
65
66       static int
67       compare(const char_type* __s1, const char_type* __s2, std::size_t __n);
68
69       static std::size_t
70       length(const char_type* __s);
71
72       static const char_type*
73       find(const char_type* __s, std::size_t __n, const char_type& __a);
74
75       static char_type*
76       move(char_type* __s1, const char_type* __s2, std::size_t __n);
77
78       static char_type*
79       copy(char_type* __s1, const char_type* __s2, std::size_t __n);
80
81       static char_type*
82       assign(char_type* __s, std::size_t __n, char_type __a);
83
84       static char_type
85       to_char_type(const int_type& __c)
86       { return static_cast<char_type>(__c); }
87
88       static int_type
89       to_int_type(const char_type& __c)
90       { return static_cast<int_type>(__c); }
91
92       static bool
93       eq_int_type(const int_type& __c1, const int_type& __c2)
94       { return __c1 == __c2; }
95
96       static int_type
97       eof()
98       { return static_cast<int_type>(EOF); }
99
100       static int_type
101       not_eof(const int_type& __c)
102       { return !eq_int_type(__c, eof()) ? __c : to_int_type(char_type()); }
103     };
104
105   template<typename _CharT>
106     int
107     char_traits<_CharT>::
108     compare(const char_type* __s1, const char_type* __s2, std::size_t __n)
109     {
110       for (size_t __i = 0; __i < __n; ++__i)
111     if (lt(__s1[__i], __s2[__i]))
112       return -1;
113     else if (lt(__s2[__i], __s1[__i]))
114       return 1;
115       return 0;
116     }
117
118   template<typename _CharT>
119     std::size_t
120     char_traits<_CharT>::
121     length(const char_type* __p)
122     {
123       std::size_t __i = 0;
124       while (!eq(__p[__i], char_type()))
125         ++__i;
126       return __i;
127     }
128
129   template<typename _CharT>
130     const typename char_traits<_CharT>::char_type*
131     char_traits<_CharT>::
132     find(const char_type* __s, std::size_t __n, const char_type& __a)
133     {
134       for (std::size_t __i = 0; __i < __n; ++__i)
135         if (eq(__s[__i], __a))
136           return __s + __i;
137       return 0;
138     }
139
140   template<typename _CharT>
141     typename char_traits<_CharT>::char_type*
142     char_traits<_CharT>::
143     move(char_type* __s1, const char_type* __s2, std::size_t __n)
144     {
145       return static_cast<_CharT*>(std::memmove(__s1, __s2,
146                            __n * sizeof(char_type)));
147     }
148
149   template<typename _CharT>
150     typename char_traits<_CharT>::char_type*
151     char_traits<_CharT>::
152     copy(char_type* __s1, const char_type* __s2, std::size_t __n)
153     {
154       std::copy(__s2, __s2 + __n, __s1);
155       return __s1;
156     }
157
158   template<typename _CharT>
159     typename char_traits<_CharT>::char_type*
160     char_traits<_CharT>::
161     assign(char_type* __s, std::size_t __n, char_type __a)
162     {
163       std::fill_n(__s, __n, __a);
164       return __s;
165     }
166
167     /// @endcond
168 }
169
170 #endif // __xmltooling_chartraits_h__