// =====================================================================
//  $Id: TSystemClock.cc,v 1.4 2004/03/07 10:30:34 goiwai Exp $
//  $Name: CLDAQ-1-14-06 $
//  $Log: TSystemClock.cc,v $
//  Revision 1.4  2004/03/07 10:30:34  goiwai
//  ROOTに組みこむためのおまじないマクロを埋めこみました。
//  全てにおいて完全に動作するわけではありません。
//
//  Revision 1.3  2003/10/06 16:38:26  goiwai
//  *** empty log message ***
//
//  Revision 1.2  2003/07/30 16:21:21  goiwai
//  ファイルにコミットログをつけることにしました.
//
// =====================================================================
#include "TSystemClock.hh"

TSystemClock::TSystemClock()
  : theAllocatedTime( -1 ), theLastUpdateTime( -1 ), theTime( -1 )
{
  theAllocatedTime = (Tint)time( 0 );
  theTime = theAllocatedTime;
}

TSystemClock::TSystemClock( const TSystemClock& right )
  : theAllocatedTime( -1 ), 
    theLastUpdateTime( -1 ), 
    theTime( -1 )
{
  theAllocatedTime = (Tint)time( 0 );
  theLastUpdateTime = right.theLastUpdateTime;
  theTime = theAllocatedTime;
}

TSystemClock::~TSystemClock()
{;}

const TSystemClock& TSystemClock::operator=( const TSystemClock& right )
{
  theAllocatedTime = (Tint)time( 0 );
  theLastUpdateTime = right.theLastUpdateTime;
  theTime = theAllocatedTime;
  return *this;
}

Tstring TSystemClock::WhatTimeIsItNow()
{
  Ttime_t now = (Ttime_t)Update();

  struct tm* tp = localtime( &now );
  Tint year = tp -> tm_year + 1900;
  Tint month = tp -> tm_mon + 1;
  Tint day = tp -> tm_mday;
  Tint hour = tp -> tm_hour;
  Tint min = tp -> tm_min;
  Tint sec = tp -> tm_sec;

  static const Tsize_t buflen = 128;
  static Tchar cbuf[ buflen ];
  Tostrstream bufstream( cbuf, buflen );

  bufstream << year;
  bufstream << "/";
  bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << month;
  bufstream << "/";
  bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << day;
  bufstream << " ";
  bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << hour;
  bufstream << ":";
  bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << min;
  bufstream << ":";
  bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << sec;
  bufstream << Tflush;

  Tstring s = bufstream.str();
  return s;
}

Tstring TSystemClock::WhatTimeIsIt( Tint second )
{
  if ( second < 0 ) {
    return WhatTimeIsItNow();
  } else {
    struct tm* tp = localtime( (Ttime_t*)(&second) );
    Tint year = tp -> tm_year + 1900;
    Tint month = tp -> tm_mon + 1;
    Tint day = tp -> tm_mday;
    Tint hour = tp -> tm_hour;
    Tint min = tp -> tm_min;
    Tint sec = tp -> tm_sec;

    static const Tsize_t buflen = 128;
    static Tchar cbuf[ buflen ];
    Tostrstream bufstream( cbuf, buflen );

    bufstream << year;
    bufstream << "/";
    bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << month;
    bufstream << "/";
    bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << day;
    bufstream << " ";
    bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << hour;
    bufstream << ":";
    bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << min;
    bufstream << ":";
    bufstream << setfill( '0' ) << setiosflags( Tios::right ) << setw( 2 ) << sec;
    bufstream << Tflush;

    Tstring s = bufstream.str();
    return s;
  }
}

Tstring TSystemClock::WhenAllocated()
{
  return WhatTimeIsIt( theAllocatedTime );
}

Tstring TSystemClock::WhenUpdate()
{
  return WhatTimeIsIt( theLastUpdateTime );
}

Tint TSystemClock::GetElapsedTime( const Tstring& unit )
{
  Update();
  Tint diff = theTime - theAllocatedTime;
  if ( unit == Thour ) {
    return diff/60/24;
  } else if ( unit == Tmin ) {
    return diff/60;
  } else {
    return diff;
  }
}

Tint TSystemClock::GetElapsedTimeOfLastUpdate( const Tstring& unit )
{
  Update();
  Tint diff = theTime - theLastUpdateTime;
  if ( unit == Thour ) {
    return diff/60/24;
  } else if ( unit == Tmin ) {
    return diff/60;
  } else {
    return diff;
  }
}

Tint TSystemClock::GetYear( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_year + 1900;
}

Tint TSystemClock::GetMonth( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_mon + 1;
}

Tint TSystemClock::GetDay( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_mday;
}

Tint TSystemClock::GetHour( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_hour;
}

Tint TSystemClock::GetMinute( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_min;
}

Tint TSystemClock::GetSecond( Tint second )
{
  struct tm* tp = 0;
  if ( second < 0 ) {
    Ttime_t now = (Ttime_t)Update();
    tp = localtime( &now );
  } else {
    tp = localtime( (Ttime_t*)(&second) );
  }
  return tp -> tm_sec;
}

Tint TSystemClock::Update()
{
  theLastUpdateTime = theTime;
  return theTime = (Tint)time( 0 );
}

Tostream& operator<<( Tostream& tos, const TSystemClock& right )
{
  TSystemClock copy( right );
  tos << copy.WhatTimeIsItNow() << Tflush;
  return tos;
}

#ifdef __CLDAQ_ROOT_DLL
    ClassImp(TSystemClock)
#endif
