{"id":38053,"date":"2004-08-25T07:00:00","date_gmt":"2004-08-25T07:00:00","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/oldnewthing\/2004\/08\/25\/why-cant-you-treat-a-filetime-as-an-__int64\/"},"modified":"2004-08-25T07:00:00","modified_gmt":"2004-08-25T07:00:00","slug":"why-cant-you-treat-a-filetime-as-an-__int64","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/oldnewthing\/20040825-00\/?p=38053","title":{"rendered":"Why can&#8217;t you treat a FILETIME as an __int64?"},"content":{"rendered":"<p><P>\n<A HREF=\"http:\/\/msdn.microsoft.com\/library\/en-us\/sysinfo\/base\/filetime_str.asp\">\nThe FILETIME structure<\/A> represents a 64-bit value in two parts:\n<\/P>\n<PRE>\ntypedef struct _FILETIME {\n  DWORD dwLowDateTime;\n  DWORD dwHighDateTime;\n} FILETIME, *PFILETIME;\n<\/PRE>\n<P>\nYou may be tempted to take the entire <CODE>FILETIME<\/CODE> structure\nand access it directly\nas if it were an <CODE>__int64<\/CODE>.\nAfter all, its memory layout exactly matches\nthat of a 64-bit (little-endian) integer.\n<A HREF=\"http:\/\/www.codeproject.com\/datetime\/winapi_datetime_ops.asp\">\nSome people have written sample code that does exactly this<\/a>:\n<PRE>\n<I>pi = (__int64*)&amp;ft; \/\/ WRONG\n(*pi) += (__int64)num*datepart; \/\/ WRONG<\/I>\n<\/PRE>\n<P>\nWhy is this wrong?\n<\/P>\n<P>\nAlignment.\n<\/P>\n<P>\nSince a <CODE>FILETIME<\/CODE> is a structure containing two\n<CODE>DWORD<\/CODE>s, it requires\nonly 4-byte alignment, since that is sufficient to put\neach <CODE>DWORD<\/CODE>\non a valid <CODE>DWORD<\/CODE> boundary.\nThere is no need for the first <CODE>DWORD<\/CODE>\nto reside on an 8-byte boundary.  And in fact, you&#8217;ve probably already\nused a structure where it doesn&#8217;t:\n<A HREF=\"http:\/\/msdn.microsoft.com\/library\/en-us\/fileio\/base\/win32_find_data_str.asp\">\nThe WIN32_FIND_DATA structure<\/A>.\n<\/P>\n<PRE>\ntypedef struct _WIN32_FIND_DATA {\n    DWORD dwFileAttributes;\n    FILETIME ftCreationTime;\n    FILETIME ftLastAccessTime;\n    FILETIME ftLastWriteTime;\n    DWORD nFileSizeHigh;\n    DWORD nFileSizeLow;\n    DWORD dwReserved0;\n    DWORD dwReserved1;\n    TCHAR  cFileName[ MAX_PATH ];\n    TCHAR  cAlternateFileName[ 14 ];\n} WIN32_FIND_DATA, *PWIN32_FIND_DATA, *LPWIN32_FIND_DATA;\n<\/PRE>\n<P>\nObserve that the three <CODE>FILETIME<\/CODE> structures appear at offsets 4,\n12, and 20 from the beginning of the structure.  They have been\nthrown off 8-byte alignment by the <CODE>dwFileAttributes<\/CODE> member.\n<\/P>\n<P>\nCasting a <CODE>FILETIME<\/CODE> to\nan <CODE>__int64<\/CODE> therefore can (and in the <CODE>WIN32_FIND_DATA<\/CODE>\ncase, <STRONG>will<\/STRONG>) create a misaligned pointer.\nAccessing a misaligned pointer will raise a\n<CODE>STATUS_DATATYPE_MISALIGNMENT<\/CODE> exception on architectures which\nrequire alignment.\n<\/P>\n<P>\nEven if you are on a forgiving platform that\nperforms automatic alignment fixups, you can still run into trouble.\nMore on this and other consequences of alignment in the next few entries.\n<\/P>\n<P>\n<STRONG>Exercise<\/STRONG>: Why are the\n<CODE>LARGE_INTEGER<\/CODE> and\n<CODE>ULARGE_INTEGER<\/CODE> structures not affected?\n<\/P><\/p>\n","protected":false},"excerpt":{"rendered":"<p>The FILETIME structure represents a 64-bit value in two parts: typedef struct _FILETIME { DWORD dwLowDateTime; DWORD dwHighDateTime; } FILETIME, *PFILETIME; You may be tempted to take the entire FILETIME structure and access it directly as if it were an __int64. After all, its memory layout exactly matches that of a 64-bit (little-endian) integer. Some [&hellip;]<\/p>\n","protected":false},"author":1069,"featured_media":111744,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[25,108],"class_list":["post-38053","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-oldnewthing","tag-code","tag-time"],"acf":[],"blog_post_summary":"<p>The FILETIME structure represents a 64-bit value in two parts: typedef struct _FILETIME { DWORD dwLowDateTime; DWORD dwHighDateTime; } FILETIME, *PFILETIME; You may be tempted to take the entire FILETIME structure and access it directly as if it were an __int64. After all, its memory layout exactly matches that of a 64-bit (little-endian) integer. Some [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/38053","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/users\/1069"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/comments?post=38053"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/38053\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media\/111744"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media?parent=38053"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/categories?post=38053"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/tags?post=38053"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}