mirror of https://github.com/tongzx/nt5src
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
285 lines
8.5 KiB
285 lines
8.5 KiB
// xloctime internal header (from <locale>)
|
|
#ifndef _XLOCTIME_
|
|
#define _XLOCTIME_
|
|
#include <ctime>
|
|
#include <xiosbase>
|
|
|
|
#ifdef _MSC_VER
|
|
#pragma pack(push,8)
|
|
#endif /* _MSC_VER */
|
|
_STD_BEGIN
|
|
// STRUCT time_base
|
|
struct _CRTIMP2 time_base : public locale::facet {
|
|
enum _Dateorder {no_order, dmy, mdy, ymd, ydm};
|
|
_BITMASK(_Dateorder, dateorder);
|
|
time_base(size_t _R = 0)
|
|
: locale::facet(_R) {}
|
|
};
|
|
_BITMASK_OPS(time_base::_Dateorder);
|
|
// TEMPLATE CLASS time_get
|
|
template<class _E,
|
|
class _II = istreambuf_iterator<_E, char_traits<_E> > >
|
|
class time_get : public time_base {
|
|
public:
|
|
typedef _E char_type;
|
|
typedef _II iter_type;
|
|
static locale::id id;
|
|
dateorder date_order() const
|
|
{return (do_date_order()); }
|
|
_II get_time(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{return (do_get_time(_F, _L, _X, _St, _Tp)); }
|
|
_II get_date(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{return (do_get_date(_F, _L, _X, _St, _Tp)); }
|
|
_II get_weekday(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{return (do_get_weekday(_F, _L, _X, _St, _Tp)); }
|
|
_II get_monthname(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{return (do_get_monthname(_F, _L, _X, _St, _Tp)); }
|
|
_II get_year(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{return (do_get_year(_F, _L, _X, _St, _Tp)); }
|
|
explicit time_get(size_t _R = 0)
|
|
: time_base(_R) {_Init(_Locinfo()); }
|
|
time_get(const _Locinfo& _Lobj, size_t _R = 0)
|
|
: time_base(_R) {_Init(_Lobj); }
|
|
static size_t __cdecl _Getcat()
|
|
{return (_LC_TIME); }
|
|
_PROTECTED:
|
|
virtual ~time_get()
|
|
{delete[] _Days;
|
|
delete[] _Months; }
|
|
protected:
|
|
void _Init(const _Locinfo& _Lobj)
|
|
{_Days = _MAKLOCSTR(_E, _Lobj._Getdays());
|
|
_Months = _MAKLOCSTR(_E, _Lobj._Getmonths()); }
|
|
virtual dateorder do_date_order() const
|
|
{return (mdy); }
|
|
virtual _II do_get_time(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{const _E _Colon = _WIDEN(_E, ':');
|
|
_St |= _Getint(_F, _L, 0, 23, _Tp->tm_hour);
|
|
if (_St != ios_base::goodbit || *_F != _Colon)
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_St |= _Getint(++_F, _L, 0, 59, _Tp->tm_min);
|
|
if (_St != ios_base::goodbit || *_F != _Colon)
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_St |= _Getint(++_F, _L, 0, 59, _Tp->tm_sec);
|
|
return (_F); }
|
|
virtual _II do_get_date(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const // Dec 2, 1979
|
|
{_F = get_monthname(_F, _L, _X, _St, _Tp);
|
|
if (_St != ios_base::goodbit || *_F != _WIDEN(_E, ' '))
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_St |= _Getint(++_F, _L, 1, 31, _Tp->tm_mday);
|
|
if (_St != ios_base::goodbit || *_F != _WIDEN(_E, ','))
|
|
_St |= ios_base::failbit;
|
|
else if (++_F == _L || *_F != _WIDEN(_E, ' '))
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_F = get_year(++_F, _L, _X, _St, _Tp);
|
|
if (_F == _L)
|
|
_St |= ios_base::eofbit;
|
|
return (_F); }
|
|
virtual _II do_get_weekday(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{int _N = _Getloctxt(_F, _L, (size_t)0, _Days);
|
|
if (_N < 0)
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_Tp->tm_wday = _N >> 1;
|
|
return (_F); }
|
|
virtual _II do_get_monthname(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{int _N = _Getloctxt(_F, _L, (size_t)0, _Months);
|
|
if (_N < 0)
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_Tp->tm_mon = _N >> 1;
|
|
return (_F); }
|
|
virtual _II do_get_year(_II _F, _II _L, ios_base& _X,
|
|
ios_base::iostate& _St, tm *_Tp) const
|
|
{int _Ans;
|
|
_St |= _Getint(_F, _L, 0, 2035, _Ans);
|
|
if (_St & ios_base::failbit)
|
|
;
|
|
else if (1900 <= _Ans)
|
|
_Ans -= 1900;
|
|
else if (2035 - 1900 < _Ans)
|
|
_St |= ios_base::failbit;
|
|
if (!(_St & ios_base::failbit))
|
|
_Tp->tm_year = _Ans;
|
|
return (_F); }
|
|
private:
|
|
static ios_base::iostate __cdecl _Getint(_II& _F, _II& _L,
|
|
int _Lo, int _Hi, int& _V)
|
|
{char _Ac[_MAX_INT_DIG], *_Ep;
|
|
char *_P = _Ac;
|
|
if (_F == _L)
|
|
;
|
|
else if (*_F == _WIDEN(_E, '+'))
|
|
*_P++ = '+', ++_F;
|
|
else if (*_F == _WIDEN(_E, '-'))
|
|
*_P++ = '-', ++_F;
|
|
bool _Sd = false;
|
|
while (_F != _L && *_F == _WIDEN(_E, '0'))
|
|
_Sd = true, ++_F;
|
|
if (_Sd)
|
|
*_P++ = '0';
|
|
for (char *const _Pe = &_Ac[_MAX_INT_DIG - 1]; _F != _L
|
|
&& '0' <= (*_P = (char)_NARROW(_E, *_F)) && *_P <= '9';
|
|
_Sd = true, ++_F)
|
|
if (_P < _Pe)
|
|
++_P;
|
|
if (!_Sd)
|
|
_P = _Ac;
|
|
*_P = '\0';
|
|
errno = 0;
|
|
const long _Ans = strtol(_Ac, &_Ep, 10);
|
|
ios_base::iostate _St = ios_base::goodbit;
|
|
if (_F == _L)
|
|
_St |= ios_base::eofbit;
|
|
if (_Ep == _Ac || errno != 0 || _Ans < _Lo || _Hi < _Ans)
|
|
_St |= ios_base::failbit;
|
|
else
|
|
_V = _Ans;
|
|
return (_St); }
|
|
_E *_Days, *_Months;
|
|
};
|
|
template<class _E, class _II>
|
|
locale::id time_get<_E, _II>::id;
|
|
// TEMPLATE CLASS time_get_byname
|
|
template<class _E,
|
|
class _II = istreambuf_iterator<_E, char_traits<_E> > >
|
|
class time_get_byname : public time_get<_E, _II> {
|
|
public:
|
|
explicit time_get_byname(const char *_S, size_t _R = 0)
|
|
: time_get<_E, _II>(_Locinfo(_S), _R) {}
|
|
_PROTECTED:
|
|
virtual ~time_get_byname()
|
|
{}
|
|
};
|
|
// TEMPLATE CLASS time_put
|
|
template<class _E,
|
|
class _OI = ostreambuf_iterator<_E, char_traits<_E> > >
|
|
class time_put : public time_base {
|
|
public:
|
|
typedef _E char_type;
|
|
typedef _OI iter_type;
|
|
_OI put(_OI _F, ios_base& _X, const tm *_Tp,
|
|
const _E *_Ff, const _E *_Lf) const
|
|
{const _E _Pct = _WIDEN(_E, '%');
|
|
for (; _Ff != _Lf; ++_Ff)
|
|
if (*_Ff != _Pct)
|
|
*_F++ = *_Ff;
|
|
else if (++_Ff == _Lf)
|
|
{*_F++ = _Pct;
|
|
break; }
|
|
else
|
|
{char _C = (char)_NARROW(_E, *_Ff);
|
|
char _Q = '\0';
|
|
if (_C != 'E' && _C != 'O' && _C != 'Q'
|
|
&& _C != '#')
|
|
;
|
|
else if (++_Ff == _Lf)
|
|
{*_F++ = _Pct, *_F++ = _C;
|
|
break; }
|
|
else
|
|
_Q = _C, _C = (char)_NARROW(_E, *_Ff);
|
|
_F = do_put(_F, _X, _Tp, _C, _Q); }
|
|
return (_F); }
|
|
_OI put(_OI _F, ios_base& _X, const tm *_Tp,
|
|
char _C, char _M = 0) const
|
|
{return (do_put(_F, _X, _Tp, _C, _M)); }
|
|
static locale::id id;
|
|
explicit time_put(size_t _R = 0)
|
|
: time_base(_R) {_Init(_Locinfo()); }
|
|
time_put(const _Locinfo& _Lobj, size_t _R = 0)
|
|
: time_base(_R) {_Init(_Lobj); }
|
|
static size_t __cdecl _Getcat()
|
|
{return (_LC_TIME); }
|
|
_PROTECTED:
|
|
virtual ~time_put()
|
|
{}
|
|
protected:
|
|
void _Init(const _Locinfo& _Lobj)
|
|
{_Tnames = _Lobj._Gettnames(); }
|
|
virtual _OI do_put(_OI _F, ios_base& _X, const tm *_Tp,
|
|
char _C, char _M = 0) const
|
|
{char _Fmt[5] = {"!%x\0"};
|
|
size_t _I, _N;
|
|
string _Str;
|
|
if (_M == (_E)0)
|
|
_Fmt[2] = _C;
|
|
else
|
|
_Fmt[2] = _M, _Fmt[3] = _C;
|
|
for (_N = 16; ; _N *= 2)
|
|
{_Str.append(_N, '\0');
|
|
if (0 < (_I = _Strftime(_Str.begin(), _Str.size(),
|
|
_Fmt, _Tp, _Tnames._Getptr())))
|
|
break; }
|
|
for (char *_S = _Str.begin(); 0 < --_I; ++_F)
|
|
*_F = _WIDEN(_E, *++_S);
|
|
return (_F); }
|
|
private:
|
|
_Locinfo::_Timevec _Tnames;
|
|
};
|
|
template<class _E, class _OI>
|
|
locale::id time_put<_E, _OI>::id;
|
|
// TEMPLATE CLASS time_put_byname
|
|
template<class _E,
|
|
class _OI = ostreambuf_iterator<_E, char_traits<_E> > >
|
|
class time_put_byname : public time_put<_E, _OI> {
|
|
public:
|
|
explicit time_put_byname(const char *_S, size_t _R = 0)
|
|
: time_put<_E, _OI>(_Locinfo(_S), _R) {}
|
|
_PROTECTED:
|
|
virtual ~time_put_byname()
|
|
{}
|
|
};
|
|
#ifdef _DLL
|
|
#ifdef __FORCE_INSTANCE
|
|
|
|
template class _CRTIMP2 time_get<char,
|
|
istreambuf_iterator<char, char_traits<char> > >;
|
|
template class _CRTIMP2 time_get<wchar_t,
|
|
istreambuf_iterator<wchar_t, char_traits<wchar_t> > >;
|
|
template class _CRTIMP2 time_put<char,
|
|
ostreambuf_iterator<char, char_traits<char> > >;
|
|
template class _CRTIMP2 time_put<wchar_t,
|
|
ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >;
|
|
|
|
#else // __FORCE_INSTANCE
|
|
|
|
#pragma warning(disable:4231) /* the extern before template is a non-standard extension */
|
|
|
|
extern template class _CRTIMP2 time_get<char,
|
|
istreambuf_iterator<char, char_traits<char> > >;
|
|
extern template class _CRTIMP2 time_get<wchar_t,
|
|
istreambuf_iterator<wchar_t, char_traits<wchar_t> > >;
|
|
extern template class _CRTIMP2 time_put<char,
|
|
ostreambuf_iterator<char, char_traits<char> > >;
|
|
extern template class _CRTIMP2 time_put<wchar_t,
|
|
ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >;
|
|
|
|
#pragma warning(default:4231) /* restore previous warning */
|
|
|
|
#endif // __FORCE_INSTANCE
|
|
#endif // _DLL
|
|
|
|
_STD_END
|
|
#ifdef _MSC_VER
|
|
#pragma pack(pop)
|
|
#endif /* _MSC_VER */
|
|
|
|
#endif /* _XLOCTIME_ */
|
|
|
|
/*
|
|
* Copyright (c) 1995 by P.J. Plauger. ALL RIGHTS RESERVED.
|
|
* Consult your license regarding permissions and restrictions.
|
|
*/
|