OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-stable/] [gcc-4.5.1/] [libstdc++-v3/] [config/] [locale/] [generic/] [codecvt_members.cc] - Blame information for rev 859

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 424 jeremybenn
// std::codecvt implementation details, generic version -*- C++ -*-
2
 
3
// Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2009
4
// Free Software Foundation, Inc.
5
//
6
// This file is part of the GNU ISO C++ Library.  This library is free
7
// software; you can redistribute it and/or modify it under the
8
// terms of the GNU General Public License as published by the
9
// Free Software Foundation; either version 3, or (at your option)
10
// any later version.
11
 
12
// This library is distributed in the hope that it will be useful,
13
// but WITHOUT ANY WARRANTY; without even the implied warranty of
14
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
// GNU General Public License for more details.
16
 
17
// Under Section 7 of GPL version 3, you are granted additional
18
// permissions described in the GCC Runtime Library Exception, version
19
// 3.1, as published by the Free Software Foundation.
20
 
21
// You should have received a copy of the GNU General Public License and
22
// a copy of the GCC Runtime Library Exception along with this program;
23
// see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
24
// <http://www.gnu.org/licenses/>.
25
 
26
//
27
// ISO C++ 14882: 22.2.1.5 - Template class codecvt
28
//
29
 
30
// Written by Benjamin Kosnik <bkoz@redhat.com>
31
 
32
#include <locale>
33
#include <cstdlib>  // For MB_CUR_MAX
34
#include <climits>  // For MB_LEN_MAX
35
#include <cstring>
36
 
37
_GLIBCXX_BEGIN_NAMESPACE(std)
38
 
39
  // Specializations.
40
#ifdef _GLIBCXX_USE_WCHAR_T
41
  codecvt_base::result
42
  codecvt<wchar_t, char, mbstate_t>::
43
  do_out(state_type& __state, const intern_type* __from,
44
         const intern_type* __from_end, const intern_type*& __from_next,
45
         extern_type* __to, extern_type* __to_end,
46
         extern_type*& __to_next) const
47
  {
48
    result __ret = ok;
49
    // The conversion must be done using a temporary destination buffer
50
    // since it is not possible to pass the size of the buffer to wcrtomb
51
    state_type __tmp_state(__state);
52
 
53
    // The conversion must be done by calling wcrtomb in a loop rather
54
    // than using wcsrtombs because wcsrtombs assumes that the input is
55
    // zero-terminated.
56
 
57
    // Either we can upper bound the total number of external characters to
58
    // something smaller than __to_end - __to or the conversion must be done
59
    // using a temporary destination buffer since it is not possible to
60
    // pass the size of the buffer to wcrtomb
61
    if (MB_CUR_MAX * (__from_end - __from) - (__to_end - __to) <= 0)
62
      while (__from < __from_end)
63
        {
64
          const size_t __conv = wcrtomb(__to, *__from, &__tmp_state);
65
          if (__conv == static_cast<size_t>(-1))
66
            {
67
              __ret = error;
68
              break;
69
            }
70
          __state = __tmp_state;
71
          __to += __conv;
72
          __from++;
73
        }
74
    else
75
      {
76
        extern_type __buf[MB_LEN_MAX];
77
        while (__from < __from_end && __to < __to_end)
78
          {
79
            const size_t __conv = wcrtomb(__buf, *__from, &__tmp_state);
80
            if (__conv == static_cast<size_t>(-1))
81
              {
82
                __ret = error;
83
                break;
84
              }
85
            else if (__conv > static_cast<size_t>(__to_end - __to))
86
              {
87
                __ret = partial;
88
                break;
89
              }
90
 
91
            memcpy(__to, __buf, __conv);
92
            __state = __tmp_state;
93
            __to += __conv;
94
            __from++;
95
          }
96
      }
97
 
98
    if (__ret == ok && __from < __from_end)
99
      __ret = partial;
100
 
101
    __from_next = __from;
102
    __to_next = __to;
103
    return __ret;
104
  }
105
 
106
  codecvt_base::result
107
  codecvt<wchar_t, char, mbstate_t>::
108
  do_in(state_type& __state, const extern_type* __from,
109
        const extern_type* __from_end, const extern_type*& __from_next,
110
        intern_type* __to, intern_type* __to_end,
111
        intern_type*& __to_next) const
112
  {
113
    result __ret = ok;
114
    // This temporary state object is neccessary so __state won't be modified
115
    // if [__from, __from_end) is a partial multibyte character.
116
    state_type __tmp_state(__state);
117
 
118
    // Conversion must be done by calling mbrtowc in a loop rather than
119
    // by calling mbsrtowcs because mbsrtowcs assumes that the input
120
    // sequence is zero-terminated.
121
    while (__from < __from_end && __to < __to_end)
122
      {
123
        size_t __conv = mbrtowc(__to, __from, __from_end - __from,
124
                                &__tmp_state);
125
        if (__conv == static_cast<size_t>(-1))
126
          {
127
            __ret = error;
128
            break;
129
          }
130
        else if (__conv == static_cast<size_t>(-2))
131
          {
132
            // It is unclear what to return in this case (see DR 382).
133
            __ret = partial;
134
            break;
135
          }
136
        else if (__conv == 0)
137
          {
138
            // XXX Probably wrong for stateful encodings
139
            __conv = 1;
140
            *__to = L'\0';
141
          }
142
 
143
        __state = __tmp_state;
144
        __to++;
145
        __from += __conv;
146
      }
147
 
148
    // It is not clear that __from < __from_end implies __ret != ok
149
    // (see DR 382).
150
    if (__ret == ok && __from < __from_end)
151
      __ret = partial;
152
 
153
    __from_next = __from;
154
    __to_next = __to;
155
    return __ret;
156
  }
157
 
158
  int
159
  codecvt<wchar_t, char, mbstate_t>::
160
  do_encoding() const throw()
161
  {
162
    // XXX This implementation assumes that the encoding is
163
    // stateless and is either single-byte or variable-width.
164
    int __ret = 0;
165
    if (MB_CUR_MAX == 1)
166
      __ret = 1;
167
    return __ret;
168
  }
169
 
170
  int
171
  codecvt<wchar_t, char, mbstate_t>::
172
  do_max_length() const throw()
173
  {
174
    // XXX Probably wrong for stateful encodings.
175
    int __ret = MB_CUR_MAX;
176
    return __ret;
177
  }
178
 
179
  int
180
  codecvt<wchar_t, char, mbstate_t>::
181
  do_length(state_type& __state, const extern_type* __from,
182
            const extern_type* __end, size_t __max) const
183
  {
184
    int __ret = 0;
185
    state_type __tmp_state(__state);
186
 
187
    while (__from < __end && __max)
188
      {
189
        size_t __conv = mbrtowc(NULL, __from, __end - __from, &__tmp_state);
190
        if (__conv == static_cast<size_t>(-1))
191
          {
192
            // Invalid source character
193
            break;
194
          }
195
        else if (__conv == static_cast<size_t>(-2))
196
          {
197
            // Remainder of input does not form a complete destination
198
            // character.
199
            break;
200
          }
201
        else if (__conv == 0)
202
          {
203
            // XXX Probably wrong for stateful encodings
204
            __conv = 1;
205
          }
206
 
207
        __state = __tmp_state;
208
        __from += __conv;
209
        __ret += __conv;
210
        __max--;
211
      }
212
 
213
    return __ret;
214
  }
215
#endif
216
 
217
_GLIBCXX_END_NAMESPACE

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.