[3/4] windowscodecs: Add support for WICPersistOptionsLittleEndian/WICPersistOptionsBigEndian in the IFD metadata reader.

Dmitry Timoshkov dmitry at baikal.ru
Fri Jun 8 23:26:13 CDT 2012


---
 dlls/windowscodecs/metadatahandler.c |   23 +++++++++++++++++++++--
 1 file changed, 21 insertions(+), 2 deletions(-)

diff --git a/dlls/windowscodecs/metadatahandler.c b/dlls/windowscodecs/metadatahandler.c
index 20785b4..ff900a4 100644
--- a/dlls/windowscodecs/metadatahandler.c
+++ b/dlls/windowscodecs/metadatahandler.c
@@ -26,6 +26,7 @@
 
 #include "windef.h"
 #include "winbase.h"
+#include "winternl.h"
 #include "objbase.h"
 #include "wincodec.h"
 #include "wincodecsdk.h"
@@ -599,6 +600,10 @@ HRESULT UnknownMetadataReader_CreateInstance(IUnknown *pUnkOuter, REFIID iid, vo
     return MetadataReader_Create(&UnknownMetadataReader_Vtbl, pUnkOuter, iid, ppv);
 }
 
+#define SWAP_USHORT(x) do { if (!native_byte_order) (x) = RtlUshortByteSwap(x); } while(0)
+#define SWAP_ULONG(x) do { if (!native_byte_order) (x) = RtlUlongByteSwap(x); } while(0)
+#define SWAP_ULONGLONG(x) do { if (!native_byte_order) (x) = RtlUlonglongByteSwap(x); } while(0)
+
 #include "pshpack2.h"
 struct IFD_entry
 {
@@ -629,7 +634,8 @@ struct IFD_rational
 #define IFD_DOUBLE 12
 #define IFD_IFD 13
 
-static HRESULT load_IFD_entry(IStream *input, struct IFD_entry *entry, MetadataItem *item)
+static HRESULT load_IFD_entry(IStream *input, struct IFD_entry *entry,
+                              MetadataItem *item, BOOL native_byte_order)
 {
     item->schema.vt = VT_EMPTY;
     item->id.vt = VT_UI2;
@@ -642,6 +648,7 @@ static HRESULT load_IFD_entry(IStream *input, struct IFD_entry *entry, MetadataI
         {
             item->value.vt = VT_UI2;
             item->value.u.uiVal = entry->value;
+            SWAP_USHORT(item->value.u.uiVal);
             break;
         }
         FIXME("loading multiple short fields is not implemented\n");
@@ -651,6 +658,7 @@ static HRESULT load_IFD_entry(IStream *input, struct IFD_entry *entry, MetadataI
         {
             item->value.vt = VT_UI4;
             item->value.u.ulVal = entry->value;
+            SWAP_ULONG(item->value.u.ulVal);
             break;
         }
         FIXME("loading multiple long fields is not implemented\n");
@@ -670,6 +678,7 @@ static HRESULT load_IFD_entry(IStream *input, struct IFD_entry *entry, MetadataI
             hr = IStream_Read(input, &rational , sizeof(rational), NULL);
             if (FAILED(hr)) return hr;
             item->value.u.uhVal.QuadPart = ((LONGLONG)rational.denominator << 32) | rational.numerator;
+            SWAP_ULONGLONG(item->value.u.uhVal.QuadPart);
             break;
         }
         FIXME("loading multiple rational fields is not implemented\n");
@@ -688,12 +697,22 @@ static HRESULT LoadIfdMetadata(IStream *input, const GUID *preferred_vendor,
     MetadataItem *result;
     USHORT count, i;
     struct IFD_entry *entry;
+    BOOL native_byte_order = TRUE;
 
     TRACE("\n");
 
+#ifdef WORDS_BIGENDIAN
+    if (persist_options & WICPersistOptionsLittleEndian)
+#else
+    if (persist_options & WICPersistOptionsBigEndian)
+#endif
+        native_byte_order = FALSE;
+
     hr = IStream_Read(input, &count, sizeof(count), NULL);
     if (FAILED(hr)) return hr;
 
+    SWAP_USHORT(count);
+
     entry = HeapAlloc(GetProcessHeap(), 0, count * sizeof(*entry));
     if (!entry) return E_OUTOFMEMORY;
 
@@ -713,7 +732,7 @@ static HRESULT LoadIfdMetadata(IStream *input, const GUID *preferred_vendor,
 
     for (i = 0; i < count; i++)
     {
-        hr = load_IFD_entry(input, &entry[i], &result[i]);
+        hr = load_IFD_entry(input, &entry[i], &result[i], native_byte_order);
         if (FAILED(hr))
         {
             HeapFree(GetProcessHeap(), 0, entry);
-- 
1.7.10.1




More information about the wine-patches mailing list