1

I have got a value of timestamp represented by number of ticks. Obtaining from it date/time under c# is easy by creating a new System.DateTime object and passing the timestamp value into the constructor, or so I am told (it was created in c#). The thing is I can only use C/C++. Even converting ticks into seconds is somewhat confusing. According to cplusplus.com simple multiplication by the macro CLOCKS_PER_SEC - Clock ticks per second, should suffice. This results in multiplication by 1000. According to Microsoft website, however, the conversion factor to seconds should be 1e7. Sample value to be converted is 634400640022968750, suggesting the second version is closer to reality.

I will not spend time describing my failed attempts, because they got me nowhere. Any help will be deeply appreciated.

Matt Gos
  • 33
  • 3

2 Answers2

2

Assuming you are on windows, the problem is that c# DateTime starts at 1 january of 0001 and c++ FILETIME starts at 1 january of 1601 so to get a SYSTEMTIME with the C# value, you need something like this...

    ULARGE_INTEGER uliTime;
    uliTime.QuadPart = 634400640022968750; // Your sample value

    SYSTEMTIME stSytemTime;
    memset(&stSytemTime,0,sizeof(SYSTEMTIME));

    FILETIME stFileTime;
    memset(&stFileTime,0,sizeof(FILETIME));

    // Fill FILETIME with your value
    stFileTime.dwLowDateTime = uliTime.LowPart;
    stFileTime.dwHighDateTime = uliTime.HighPart;

    // Convert FILETIME so SYSTEMTIME
    FileTimeToSystemTime(&stFileTime, &stSytemTime);
    stSytemTime.wYear -= 1600; // Remove the "start" diference

Convert SYSTEMTIME to time_t

void ConvertSystemTimeToTimeT(const SYSTEMTIME &stSystemTime, time_t &stTimeT)
{
    // time_t min value is 1 January 1970
    LARGE_INTEGER liJanuary1970 = {0};
    liJanuary1970.QuadPart = 116444736000000000;

    FILETIME stFileTime = {0};    
    SystemTimeToFileTime(&stSystemTime, &stFileTime);

    ULARGE_INTEGER ullConverter;
    ullConverter.LowPart = stFileTime.dwLowDateTime;
    ullConverter.HighPart = stFileTime.dwHighDateTime;

    // time_t resolution is 1 second, FILETIME is 100 nanoseconds, so convert to seconds and remove the 1970 value  
    stTimeT = (time_t)(ullConverter.QuadPart - liJanuary1970.QuadPart) / 10000000;
}
João Augusto
  • 2,285
  • 24
  • 28
  • thanks, works beautifully. and is there an easy way to convert stSystemTime into a string like ctime() does with seconds? – Matt Gos Oct 18 '12 at 12:29
  • 1
    There is no "pretty print" function for SYSTEMTIME, use sprintf or std::stringstream to convert to a string, but if you want to use the ctime() you can always convert from SYSTEMTIME to time_t... Check my Edit – João Augusto Oct 18 '12 at 13:18
0

if you want to time your code, I would advise to use the QueryPerformance library (QueryPerformanceFrequency and QueryPerformanceCounterfunctions especially) , if it is supported by your hardware.

If you just want an timestamp in seconds from an epoch, use the "time.h" library : How to get current time and date in C++?

Community
  • 1
  • 1
lucasg
  • 10,734
  • 4
  • 35
  • 57
  • yeah, i know how to use time.h, but this didn't seem to be enough for my particular need (see my comment above). thanks for mentioning the libraries though, i will read more about it. – Matt Gos Oct 18 '12 at 12:07