djd0 djd0 - 1 month ago 11
C++ Question

How can a Windows DATE be converted into a Unix time in c++

Windows uses the

type to represent dates. This is a
double
value representing the number of days since 30 December 1899, midnight.

How can a
DATE
be converted into a Unix timestamp (the number of seconds since 01 January 1970) value?

Specifically, how can this be achieved using only the c++ standard library, and windows libraries for which MinGW distributes header files?

For example, I can get a date property from an
IShellFolder2
:

void MyFunc(IShellFolder2 *folder, PCUITEMID_CHILD pidl, const SHCOLUMNID *columnid) {
VARIANT* v = (VARIANT*) malloc(sizeof(VARIANT));
DATE d;
HRESULT hr = folder->GetDetailsEx(pidl, colid, v);
if (SUCCEEDED(hr)) {
hr = VariantChangeType(v, v, 0, VT_DATE);
if (SUCCEEDED(hr)) {
d = v->date;
}
VariantClear(v);
}
free(v);
// process date here
}


How do I then transform this value for use with software that uses the Unix timestamp format?

Currently used header files (not all relevant to this specific issue):

#include <iostream>
#include <windows.h>
#include <stdio.h>
#include <tchar.h>
#include <shlobj.h>
#include <shlwapi.h>
#include <propkey.h>
#include <wchar.h>
#include <shlguid.h>
#include <string>
#include <vector>

Answer

Use VariantTimeToSystemTime to convert DATE to SYSTEMTIME.

Conversion of SYSTEMTIME to unix time is then a simple task.

In Visual Studio you could use COleDateTime but that's not available in MinGW

#include <Windows.h>
#include <stdio.h>
#include <time.h>
#include <OleAuto.h>

int main()
{
    DATE dt = 25569.000000; //1970,1,1
    SYSTEMTIME st;
    VariantTimeToSystemTime(dt, &st);

    time_t rawtime;
    struct tm * timeinfo;
    time(&rawtime);
    timeinfo = localtime(&rawtime);
    timeinfo->tm_year = st.wYear - 1900;
    timeinfo->tm_mon = st.wMonth - 1;
    timeinfo->tm_mday = st.wDay;
    timeinfo->tm_hour = st.wHour;
    timeinfo->tm_min = st.wMinute;
    timeinfo->tm_sec = st.wSecond;
    mktime(timeinfo);

    printf("%d\n", st.wYear);

    return 0;
}
Comments