// <chrono> -*- C++ -*-// Copyright (C) 2008, 2009 Free Software Foundation, Inc.//// This file is part of the GNU ISO C++ Library. This library is free// software; you can redistribute it and/or modify it under the// terms of the GNU General Public License as published by the// Free Software Foundation; either version 3, or (at your option)// any later version.// This library is distributed in the hope that it will be useful,// but WITHOUT ANY WARRANTY; without even the implied warranty of// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the// GNU General Public License for more details.// Under Section 7 of GPL version 3, you are granted additional// permissions described in the GCC Runtime Library Exception, version// 3.1, as published by the Free Software Foundation.// You should have received a copy of the GNU General Public License and// a copy of the GCC Runtime Library Exception along with this program;// see the files COPYING3 and COPYING.RUNTIME respectively. If not, see// <http://www.gnu.org/licenses/>./** @file include/chrono* This is a Standard C++ Library header.*/#ifndef _GLIBCXX_CHRONO#define _GLIBCXX_CHRONO 1#pragma GCC system_header#ifndef __GXX_EXPERIMENTAL_CXX0X__# include <c++0x_warning.h>#else#ifdef _GLIBCXX_INCLUDE_AS_TR1# error C++0x header cannot be included from TR1 header#endif#include <ratio>#include <type_traits>#include <limits>#include <ctime>#ifdef _GLIBCXX_USE_C99_STDINT_TR1namespace std{/*** @defgroup chrono Time* @ingroup utilities** Classes and functions for time.* @{*//** @namespace std::chrono* @brief ISO C++ 0x entities sub namespace for time and date.*/namespace chrono{template<typename _Rep, typename _Period = ratio<1>>struct duration;template<typename _Clock, typename _Duration = typename _Clock::duration>struct time_point;}// 20.8.2.3 specialization of common_type (for duration)template<typename _Rep1, typename _Period1, typename _Rep2, typename _Period2>struct common_type<chrono::duration<_Rep1, _Period1>,chrono::duration<_Rep2, _Period2>>{typedef chrono::duration<typename common_type<_Rep1, _Rep2>::type,ratio<__static_gcd<_Period1::num, _Period2::num>::value,(_Period1::den / __static_gcd<_Period1::den, _Period2::den>::value)* _Period2::den>> type;};// 20.8.2.3 specialization of common_type (for time_point)template<typename _Clock, typename _Duration1, typename _Duration2>struct common_type<chrono::time_point<_Clock, _Duration1>,chrono::time_point<_Clock, _Duration2>>{typedef chrono::time_point<_Clock,typename common_type<_Duration1, _Duration2>::type> type;};namespace chrono{// Primary template for duration_cast impl.template<typename _ToDuration, typename _CF, typename _CR,bool _NumIsOne = false, bool _DenIsOne = false>struct __duration_cast_impl{template<typename _Rep, typename _Period>static _ToDuration __cast(const duration<_Rep, _Period>& __d){return _ToDuration(static_cast<typename _ToDuration::rep>(static_cast<_CR>(__d.count())* static_cast<_CR>(_CF::num)/ static_cast<_CR>(_CF::den)));}};template<typename _ToDuration, typename _CF, typename _CR>struct __duration_cast_impl<_ToDuration, _CF, _CR, true, true>{template<typename _Rep, typename _Period>static _ToDuration __cast(const duration<_Rep, _Period>& __d){return _ToDuration(static_cast<typename _ToDuration::rep>(__d.count()));}};template<typename _ToDuration, typename _CF, typename _CR>struct __duration_cast_impl<_ToDuration, _CF, _CR, true, false>{template<typename _Rep, typename _Period>static _ToDuration __cast(const duration<_Rep, _Period>& __d){return _ToDuration(static_cast<typename _ToDuration::rep>(static_cast<_CR>(__d.count()) / static_cast<_CR>(_CF::den)));}};template<typename _ToDuration, typename _CF, typename _CR>struct __duration_cast_impl<_ToDuration, _CF, _CR, false, true>{template<typename _Rep, typename _Period>static _ToDuration __cast(const duration<_Rep, _Period>& __d){return _ToDuration(static_cast<typename _ToDuration::rep>(static_cast<_CR>(__d.count()) * static_cast<_CR>(_CF::num)));}};/// duration_casttemplate<typename _ToDuration, typename _Rep, typename _Period>inline _ToDurationduration_cast(const duration<_Rep, _Period>& __d){typedef typenameratio_divide<_Period, typename _ToDuration::period>::type __cf;typedef typenamecommon_type<typename _ToDuration::rep, _Rep, intmax_t>::type __cr;return __duration_cast_impl<_ToDuration, __cf, __cr,__cf::num == 1, __cf::den == 1>::__cast(__d);}/// treat_as_floating_pointtemplate<typename _Rep>struct treat_as_floating_point: is_floating_point<_Rep>{ };/// duration_valuestemplate<typename _Rep>struct duration_values{static const _Repzero(){ return _Rep(0); }static const _Repmax(){ return numeric_limits<_Rep>::max(); }static const _Repmin(){ return numeric_limits<_Rep>::min(); }};template<typename _Tp>struct __is_duration: std::false_type{ };template<typename _Rep, typename _Period>struct __is_duration<duration<_Rep, _Period>>: std::true_type{ };template<typename T>struct __is_ratio: std::false_type{ };template<intmax_t _Num, intmax_t _Den>struct __is_ratio<ratio<_Num, _Den>>: std::true_type{ };/// durationtemplate<typename _Rep, typename _Period>struct duration{static_assert(!__is_duration<_Rep>::value, "rep cannot be a duration");static_assert(__is_ratio<_Period>::value,"period must be a specialization of ratio");static_assert(_Period::num > 0, "period must be positive");typedef _Rep rep;typedef _Period period;// 20.8.3.1 construction / copy / destroyduration() = default;template<typename _Rep2>explicit duration(_Rep2 const& __rep): __r(static_cast<rep>(__rep)){static_assert(is_convertible<_Rep2,rep>::value&& (treat_as_floating_point<rep>::value|| !treat_as_floating_point<_Rep2>::value),"cannot construct integral duration with floating point type");}template<typename _Rep2, typename _Period2>duration(const duration<_Rep2, _Period2>& __d): __r(duration_cast<duration>(__d).count()){static_assert(treat_as_floating_point<rep>::value == true|| ratio_divide<_Period2, period>::type::den == 1,"the resulting duration is not exactly representable");}~duration() = default;duration(const duration&) = default;duration& operator=(const duration&) = default;// 20.8.3.2 observerrepcount() const{ return __r; }// 20.8.3.3 arithmeticdurationoperator+() const{ return *this; }durationoperator-() const{ return duration(-__r); }duration&operator++(){++__r;return *this;}durationoperator++(int){ return duration(__r++); }duration&operator--(){--__r;return *this;}durationoperator--(int){ return duration(__r--); }duration&operator+=(const duration& __d){__r += __d.count();return *this;}duration&operator-=(const duration& __d){__r -= __d.count();return *this;}duration&operator*=(const rep& __rhs){__r *= __rhs;return *this;}duration&operator/=(const rep& __rhs){__r /= __rhs;return *this;}// 20.8.3.4 special values// TODO: These should be constexprs.static const durationzero(){ return duration(duration_values<rep>::zero()); }static const durationmin(){ return duration(duration_values<rep>::min()); }static const durationmax(){ return duration(duration_values<rep>::max()); }private:rep __r;};template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::typeoperator+(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){typedef typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::type __ct;return __ct(__lhs) += __rhs;}template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::typeoperator-(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){typedef typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::type __ct;return __ct(__lhs) -= __rhs;}template<typename _Rep1, typename _Period, typename _Rep2>inline duration<typename common_type<_Rep1, _Rep2>::type, _Period>operator*(const duration<_Rep1, _Period>& __d, const _Rep2& __s){typedef typename common_type<_Rep1, _Rep2>::type __cr;return duration<__cr, _Period>(__d) *= __s;}template<typename _Rep1, typename _Period, typename _Rep2>inline duration<typename common_type<_Rep1, _Rep2>::type, _Period>operator*(const _Rep2& __s, const duration<_Rep1, _Period>& __d){ return __d * __s; }template<typename _Tp, typename _Up, typename _Ep = void>struct __division_impl;template<typename _Rep1, typename _Period, typename _Rep2>struct __division_impl<duration<_Rep1, _Period>, _Rep2,typename enable_if<!__is_duration<_Rep2>::value>::type>{typedef typename common_type<_Rep1, _Rep2>::type __cr;typedefduration<typename common_type<_Rep1, _Rep2>::type, _Period> __rt;static __rt__divide(const duration<_Rep1, _Period>& __d, const _Rep2& __s){ return duration<__cr, _Period>(__d) /= __s; }};template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>struct __division_impl<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>{typedef typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::type __ct;typedef typename common_type<_Rep1, _Rep2>::type __rt;static __rt__divide(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return __ct(__lhs).count() / __ct(__rhs).count(); }};template<typename _Rep, typename _Period, typename _Up>inline typename __division_impl<duration<_Rep, _Period>, _Up>::__rtoperator/(const duration<_Rep, _Period>& __d, const _Up& __u){return__division_impl<duration<_Rep, _Period>, _Up>::__divide(__d, __u);}// comparisonstemplate<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator==(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){typedef typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::type __ct;return __ct(__lhs).count() == __ct(__rhs).count();}template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator<(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){typedef typename common_type<duration<_Rep1, _Period1>,duration<_Rep2, _Period2>>::type __ct;return __ct(__lhs).count() < __ct(__rhs).count();}template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator!=(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return !(__lhs == __rhs); }template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator<=(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return !(__rhs < __lhs); }template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator>(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return __rhs < __lhs; }template<typename _Rep1, typename _Period1,typename _Rep2, typename _Period2>inline booloperator>=(const duration<_Rep1, _Period1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return !(__lhs < __rhs); }/// nanosecondstypedef duration<int64_t, nano> nanoseconds;/// microsecondstypedef duration<int64_t, micro> microseconds;/// millisecondstypedef duration<int64_t, milli> milliseconds;/// secondstypedef duration<int64_t > seconds;/// minutestypedef duration<int, ratio< 60>> minutes;/// hourstypedef duration<int, ratio<3600>> hours;/// time_pointtemplate<typename _Clock, typename _Duration>struct time_point{typedef _Clock clock;typedef _Duration duration;typedef typename duration::rep rep;typedef typename duration::period period;time_point() : __d(duration::zero()){ }explicit time_point(const duration& __dur): __d(duration::zero() + __dur){ }// conversionstemplate<typename _Duration2>time_point(const time_point<clock, _Duration2>& __t): __d(__t.time_since_epoch()){ }// observerdurationtime_since_epoch() const{ return __d; }// arithmetictime_point&operator+=(const duration& __dur){__d += __dur;return *this;}time_point&operator-=(const duration& __dur){__d -= __dur;return *this;}// special values// TODO: These should be constexprs.static const time_pointmin(){ return time_point(duration::min()); }static const time_pointmax(){ return time_point(duration::max()); }private:duration __d;};/// time_point_casttemplate<typename _ToDuration, typename _Clock, typename _Duration>inline time_point<_Clock, _ToDuration>time_point_cast(const time_point<_Clock, _Duration>& __t){return time_point<_Clock, _ToDuration>(duration_cast<_ToDuration>(__t.time_since_epoch()));}template<typename _Clock, typename _Duration1,typename _Rep2, typename _Period2>inline time_point<_Clock,typename common_type<_Duration1, duration<_Rep2, _Period2>>::type>operator+(const time_point<_Clock, _Duration1>& __lhs,const duration<_Rep2, _Period2>& __rhs){typedef time_point<_Clock,typename common_type<_Duration1,duration<_Rep2, _Period2>>::type> __ct;return __ct(__lhs) += __rhs;}template<typename _Rep1, typename _Period1,typename _Clock, typename _Duration2>inline time_point<_Clock,typename common_type<duration<_Rep1, _Period1>, _Duration2>::type>operator+(const duration<_Rep1, _Period1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return __rhs + __lhs; }template<typename _Clock, typename _Duration1,typename _Rep2, typename _Period2>inline time_point<_Clock,typename common_type<_Duration1, duration<_Rep2, _Period2>>::type>operator-(const time_point<_Clock, _Duration1>& __lhs,const duration<_Rep2, _Period2>& __rhs){ return __lhs + (-__rhs); }template<typename _Clock, typename _Duration1, typename _Duration2>inline typename common_type<_Duration1, _Duration2>::typeoperator-(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return __lhs.time_since_epoch() - __rhs.time_since_epoch(); }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator==(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return __lhs.time_since_epoch() == __rhs.time_since_epoch(); }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator!=(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return !(__lhs == __rhs); }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator<(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return __lhs.time_since_epoch() < __rhs.time_since_epoch(); }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator<=(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return !(__rhs < __lhs); }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator>(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return __rhs < __lhs; }template<typename _Clock, typename _Duration1, typename _Duration2>inline booloperator>=(const time_point<_Clock, _Duration1>& __lhs,const time_point<_Clock, _Duration2>& __rhs){ return !(__lhs < __rhs); }/// system_clockstruct system_clock{#ifdef _GLIBCXX_USE_CLOCK_REALTIMEtypedef chrono::nanoseconds duration;#elif defined(_GLIBCXX_USE_GETTIMEOFDAY)typedef chrono::microseconds duration;#elsetypedef chrono::seconds duration;#endiftypedef duration::rep rep;typedef duration::period period;typedef chrono::time_point<system_clock, duration> time_point;static const bool is_monotonic = false;static time_pointnow();// Map to C APIstatic std::time_tto_time_t(const time_point& __t){return std::time_t(duration_cast<chrono::seconds>(__t.time_since_epoch()).count());}static time_pointfrom_time_t(std::time_t __t){return time_point_cast<system_clock::duration>(chrono::time_point<system_clock, chrono::seconds>(chrono::seconds(__t)));}// TODO: requires constexpr/*static_assert(system_clock::duration::min() <system_clock::duration::zero(),"a clock's minimum duration cannot be less than its epoch");*/};#ifdef _GLIBCXX_USE_CLOCK_MONOTONIC/// monotonic_clockstruct monotonic_clock{typedef chrono::nanoseconds duration;typedef duration::rep rep;typedef duration::period period;typedef chrono::time_point<monotonic_clock, duration> time_point;static const bool is_monotonic = true;static time_pointnow();};#elsetypedef system_clock monotonic_clock;#endiftypedef system_clock high_resolution_clock;} // namespace chrono// @} group chrono} // namespace std#endif //_GLIBCXX_USE_C99_STDINT_TR1#endif //__GXX_EXPERIMENTAL_CXX0X__#endif //_GLIBCXX_CHRONO