Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-cw
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-cw
Commits
432d8229
Commit
432d8229
authored
Jul 23, 2023
by
Jeff Smith
Committed by
Alexandre Julliard
Jul 31, 2023
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
windowscodecs: Handle PNG last-modification time (tIME) chunk type.
parent
60f6539f
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
173 additions
and
8 deletions
+173
-8
clsfactory.c
dlls/windowscodecs/clsfactory.c
+1
-0
pngformat.c
dlls/windowscodecs/pngformat.c
+86
-0
regsvr.c
dlls/windowscodecs/regsvr.c
+25
-0
metadata.c
dlls/windowscodecs/tests/metadata.c
+53
-8
wincodecs_private.h
dlls/windowscodecs/wincodecs_private.h
+1
-0
windowscodecs_wincodec.idl
dlls/windowscodecs/windowscodecs_wincodec.idl
+7
-0
No files found.
dlls/windowscodecs/clsfactory.c
View file @
432d8229
...
@@ -67,6 +67,7 @@ static const classinfo wic_classes[] = {
...
@@ -67,6 +67,7 @@ static const classinfo wic_classes[] = {
{
&
CLSID_WICPngGamaMetadataReader
,
PngGamaReader_CreateInstance
},
{
&
CLSID_WICPngGamaMetadataReader
,
PngGamaReader_CreateInstance
},
{
&
CLSID_WICPngHistMetadataReader
,
PngHistReader_CreateInstance
},
{
&
CLSID_WICPngHistMetadataReader
,
PngHistReader_CreateInstance
},
{
&
CLSID_WICPngTextMetadataReader
,
PngTextReader_CreateInstance
},
{
&
CLSID_WICPngTextMetadataReader
,
PngTextReader_CreateInstance
},
{
&
CLSID_WICPngTimeMetadataReader
,
PngTimeReader_CreateInstance
},
{
&
CLSID_WICLSDMetadataReader
,
LSDReader_CreateInstance
},
{
&
CLSID_WICLSDMetadataReader
,
LSDReader_CreateInstance
},
{
&
CLSID_WICIMDMetadataReader
,
IMDReader_CreateInstance
},
{
&
CLSID_WICIMDMetadataReader
,
IMDReader_CreateInstance
},
{
&
CLSID_WICGCEMetadataReader
,
GCEReader_CreateInstance
},
{
&
CLSID_WICGCEMetadataReader
,
GCEReader_CreateInstance
},
...
...
dlls/windowscodecs/pngformat.c
View file @
432d8229
...
@@ -311,6 +311,92 @@ HRESULT PngHistReader_CreateInstance(REFIID iid, void** ppv)
...
@@ -311,6 +311,92 @@ HRESULT PngHistReader_CreateInstance(REFIID iid, void** ppv)
return
MetadataReader_Create
(
&
HistReader_Vtbl
,
iid
,
ppv
);
return
MetadataReader_Create
(
&
HistReader_Vtbl
,
iid
,
ppv
);
}
}
static
HRESULT
LoadTimeMetadata
(
IStream
*
stream
,
const
GUID
*
preferred_vendor
,
DWORD
persist_options
,
MetadataItem
**
items
,
DWORD
*
item_count
)
{
HRESULT
hr
;
BYTE
type
[
4
];
BYTE
*
data
;
ULONG
data_size
,
i
;
MetadataItem
*
result
;
static
const
WCHAR
*
names
[
6
]
=
{
L"Year"
,
L"Month"
,
L"Day"
,
L"Hour"
,
L"Minute"
,
L"Second"
,
};
LPWSTR
id_values
[
6
]
=
{
0
};
hr
=
read_png_chunk
(
stream
,
type
,
&
data
,
&
data_size
);
if
(
FAILED
(
hr
))
return
hr
;
if
(
data_size
!=
7
)
{
HeapFree
(
GetProcessHeap
(),
0
,
data
);
return
E_FAIL
;
}
result
=
HeapAlloc
(
GetProcessHeap
(),
HEAP_ZERO_MEMORY
,
sizeof
(
MetadataItem
)
*
6
);
for
(
i
=
0
;
i
<
6
;
i
++
)
{
SHStrDupW
(
names
[
i
],
&
id_values
[
i
]);
if
(
!
id_values
[
i
])
break
;
}
if
(
!
result
||
i
<
6
)
{
HeapFree
(
GetProcessHeap
(),
0
,
result
);
for
(
i
=
0
;
i
<
6
;
i
++
)
CoTaskMemFree
(
id_values
[
i
]);
HeapFree
(
GetProcessHeap
(),
0
,
data
);
return
E_OUTOFMEMORY
;
}
for
(
i
=
0
;
i
<
6
;
i
++
)
{
PropVariantInit
(
&
result
[
i
].
schema
);
PropVariantInit
(
&
result
[
i
].
id
);
PropVariantInit
(
&
result
[
i
].
value
);
result
[
i
].
id
.
vt
=
VT_LPWSTR
;
result
[
i
].
id
.
pwszVal
=
id_values
[
i
];
}
result
[
0
].
value
.
vt
=
VT_UI2
;
result
[
0
].
value
.
uiVal
=
read_ushort_be
(
data
);
result
[
1
].
value
.
vt
=
VT_UI1
;
result
[
1
].
value
.
bVal
=
data
[
2
];
result
[
2
].
value
.
vt
=
VT_UI1
;
result
[
2
].
value
.
bVal
=
data
[
3
];
result
[
3
].
value
.
vt
=
VT_UI1
;
result
[
3
].
value
.
bVal
=
data
[
4
];
result
[
4
].
value
.
vt
=
VT_UI1
;
result
[
4
].
value
.
bVal
=
data
[
5
];
result
[
5
].
value
.
vt
=
VT_UI1
;
result
[
5
].
value
.
bVal
=
data
[
6
];
*
items
=
result
;
*
item_count
=
6
;
HeapFree
(
GetProcessHeap
(),
0
,
data
);
return
S_OK
;
}
static
const
MetadataHandlerVtbl
TimeReader_Vtbl
=
{
0
,
&
CLSID_WICPngTimeMetadataReader
,
LoadTimeMetadata
};
HRESULT
PngTimeReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
)
{
return
MetadataReader_Create
(
&
TimeReader_Vtbl
,
iid
,
ppv
);
}
HRESULT
PngDecoder_CreateInstance
(
REFIID
iid
,
void
**
ppv
)
HRESULT
PngDecoder_CreateInstance
(
REFIID
iid
,
void
**
ppv
)
{
{
HRESULT
hr
;
HRESULT
hr
;
...
...
dlls/windowscodecs/regsvr.c
View file @
432d8229
...
@@ -1635,6 +1635,21 @@ static const struct reader_containers pnghist_containers[] = {
...
@@ -1635,6 +1635,21 @@ static const struct reader_containers pnghist_containers[] = {
{
NULL
}
/* list terminator */
{
NULL
}
/* list terminator */
};
};
static
const
BYTE
tIME
[]
=
"tIME"
;
static
const
struct
metadata_pattern
pngtime_metadata_pattern
[]
=
{
{
4
,
4
,
tIME
,
mask_all
,
4
},
{
0
}
};
static
const
struct
reader_containers
pngtime_containers
[]
=
{
{
&
GUID_ContainerFormatPng
,
pngtime_metadata_pattern
},
{
NULL
}
/* list terminator */
};
static
const
struct
metadata_pattern
lsd_metadata_patterns
[]
=
{
static
const
struct
metadata_pattern
lsd_metadata_patterns
[]
=
{
{
0
,
6
,
gif87a_magic
,
mask_all
,
0
},
{
0
,
6
,
gif87a_magic
,
mask_all
,
0
},
{
0
,
6
,
gif89a_magic
,
mask_all
,
0
},
{
0
,
6
,
gif89a_magic
,
mask_all
,
0
},
...
@@ -1770,6 +1785,16 @@ static struct regsvr_metadatareader const metadatareader_list[] = {
...
@@ -1770,6 +1785,16 @@ static struct regsvr_metadatareader const metadatareader_list[] = {
0
,
0
,
0
,
0
,
0
,
0
,
pngtext_containers
pngtext_containers
},
},
{
&
CLSID_WICPngTimeMetadataReader
,
"The Wine Project"
,
"Chunk tIME Reader"
,
"1.0.0.0"
,
"1.0.0.0"
,
&
GUID_VendorMicrosoft
,
&
GUID_MetadataFormatChunktIME
,
0
,
0
,
0
,
pngtime_containers
},
{
&
CLSID_WICLSDMetadataReader
,
{
&
CLSID_WICLSDMetadataReader
,
"The Wine Project"
,
"The Wine Project"
,
"Logical Screen Descriptor Reader"
,
"Logical Screen Descriptor Reader"
,
...
...
dlls/windowscodecs/tests/metadata.c
View file @
432d8229
...
@@ -169,6 +169,14 @@ static const char metadata_hIST[] = {
...
@@ -169,6 +169,14 @@ static const char metadata_hIST[] = {
0xff
,
0xff
,
0xff
,
0xff
0xff
,
0xff
,
0xff
,
0xff
};
};
static
const
char
metadata_tIME
[]
=
{
0
,
0
,
0
,
7
,
/* chunk length */
't'
,
'I'
,
'M'
,
'E'
,
/* chunk type */
0x07
,
0xd0
,
0x01
,
0x02
,
/* year (2 bytes), month, day */
0x0c
,
0x22
,
0x38
,
/* hour, minute, second */
0xff
,
0xff
,
0xff
,
0xff
};
static
const
char
pngimage
[
285
]
=
{
static
const
char
pngimage
[
285
]
=
{
0x89
,
0x50
,
0x4e
,
0x47
,
0x0d
,
0x0a
,
0x1a
,
0x0a
,
0x00
,
0x00
,
0x00
,
0x0d
,
0x49
,
0x48
,
0x44
,
0x52
,
0x89
,
0x50
,
0x4e
,
0x47
,
0x0d
,
0x0a
,
0x1a
,
0x0a
,
0x00
,
0x00
,
0x00
,
0x0d
,
0x49
,
0x48
,
0x44
,
0x52
,
0x00
,
0x00
,
0x00
,
0x01
,
0x00
,
0x00
,
0x00
,
0x01
,
0x08
,
0x02
,
0x00
,
0x00
,
0x00
,
0x90
,
0x77
,
0x53
,
0x00
,
0x00
,
0x00
,
0x01
,
0x00
,
0x00
,
0x00
,
0x01
,
0x08
,
0x02
,
0x00
,
0x00
,
0x00
,
0x90
,
0x77
,
0x53
,
...
@@ -725,6 +733,42 @@ static void test_metadata_hIST(void)
...
@@ -725,6 +733,42 @@ static void test_metadata_hIST(void)
IWICMetadataReader_Release
(
reader
);
IWICMetadataReader_Release
(
reader
);
}
}
static
void
test_metadata_tIME
(
void
)
{
HRESULT
hr
;
IWICMetadataReader
*
reader
;
UINT
count
;
GUID
format
;
static
const
struct
test_data
td
[]
=
{
{
VT_UI2
,
0
,
0
,
{
2000
},
NULL
,
L"Year"
},
{
VT_UI1
,
0
,
0
,
{
1
},
NULL
,
L"Month"
},
{
VT_UI1
,
0
,
0
,
{
2
},
NULL
,
L"Day"
},
{
VT_UI1
,
0
,
0
,
{
12
},
NULL
,
L"Hour"
},
{
VT_UI1
,
0
,
0
,
{
34
},
NULL
,
L"Minute"
},
{
VT_UI1
,
0
,
0
,
{
56
},
NULL
,
L"Second"
},
};
hr
=
CoCreateInstance
(
&
CLSID_WICPngTimeMetadataReader
,
NULL
,
CLSCTX_INPROC_SERVER
,
&
IID_IWICMetadataReader
,
(
void
**
)
&
reader
);
ok
(
hr
==
S_OK
||
broken
(
hr
==
REGDB_E_CLASSNOTREG
)
/*winxp*/
,
"CoCreateInstance failed, hr=%lx
\n
"
,
hr
);
if
(
FAILED
(
hr
))
return
;
load_stream
((
IUnknown
*
)
reader
,
metadata_tIME
,
sizeof
(
metadata_tIME
),
WICPersistOptionDefault
);
hr
=
IWICMetadataReader_GetMetadataFormat
(
reader
,
&
format
);
ok
(
hr
==
S_OK
,
"GetMetadataFormat failed, hr=%lx
\n
"
,
hr
);
ok
(
IsEqualGUID
(
&
format
,
&
GUID_MetadataFormatChunktIME
),
"unexpected format %s
\n
"
,
wine_dbgstr_guid
(
&
format
));
hr
=
IWICMetadataReader_GetCount
(
reader
,
&
count
);
ok
(
hr
==
S_OK
,
"GetCount failed, hr=%lx
\n
"
,
hr
);
ok
(
count
==
ARRAY_SIZE
(
td
),
"unexpected count %i
\n
"
,
count
);
compare_metadata
(
reader
,
td
,
count
);
IWICMetadataReader_Release
(
reader
);
}
static
inline
USHORT
ushort_bswap
(
USHORT
s
)
static
inline
USHORT
ushort_bswap
(
USHORT
s
)
{
{
return
(
s
>>
8
)
|
(
s
<<
8
);
return
(
s
>>
8
)
|
(
s
<<
8
);
...
@@ -1108,12 +1152,12 @@ static void test_metadata_png(void)
...
@@ -1108,12 +1152,12 @@ static void test_metadata_png(void)
{
{
static
const
struct
test_data
td
[
6
]
=
static
const
struct
test_data
td
[
6
]
=
{
{
{
VT_UI2
,
0
,
0
,
{
2005
},
NULL
,
{
'Y'
,
'e'
,
'a'
,
'r'
,
0
}
},
{
VT_UI2
,
0
,
0
,
{
2005
},
NULL
,
L"Year"
},
{
VT_UI1
,
0
,
0
,
{
6
},
NULL
,
{
'M'
,
'o'
,
'n'
,
't'
,
'h'
,
0
}
},
{
VT_UI1
,
0
,
0
,
{
6
},
NULL
,
L"Month"
},
{
VT_UI1
,
0
,
0
,
{
3
},
NULL
,
{
'D'
,
'a'
,
'y'
,
0
}
},
{
VT_UI1
,
0
,
0
,
{
3
},
NULL
,
L"Day"
},
{
VT_UI1
,
0
,
0
,
{
15
},
NULL
,
{
'H'
,
'o'
,
'u'
,
'r'
,
0
}
},
{
VT_UI1
,
0
,
0
,
{
15
},
NULL
,
L"Hour"
},
{
VT_UI1
,
0
,
0
,
{
7
},
NULL
,
{
'M'
,
'i'
,
'n'
,
'u'
,
't'
,
'e'
,
0
}
},
{
VT_UI1
,
0
,
0
,
{
7
},
NULL
,
L"Minute"
},
{
VT_UI1
,
0
,
0
,
{
45
},
NULL
,
{
'S'
,
'e'
,
'c'
,
'o'
,
'n'
,
'd'
,
0
}
}
{
VT_UI1
,
0
,
0
,
{
45
},
NULL
,
L"Second"
}
};
};
IStream
*
stream
;
IStream
*
stream
;
IWICBitmapDecoder
*
decoder
;
IWICBitmapDecoder
*
decoder
;
...
@@ -1176,13 +1220,13 @@ static void test_metadata_png(void)
...
@@ -1176,13 +1220,13 @@ static void test_metadata_png(void)
{
{
hr
=
IWICMetadataReader_GetMetadataFormat
(
reader
,
&
containerformat
);
hr
=
IWICMetadataReader_GetMetadataFormat
(
reader
,
&
containerformat
);
ok
(
hr
==
S_OK
,
"GetMetadataFormat failed, hr=%#lx
\n
"
,
hr
);
ok
(
hr
==
S_OK
,
"GetMetadataFormat failed, hr=%#lx
\n
"
,
hr
);
todo_wine
ok
(
IsEqualGUID
(
&
containerformat
,
&
GUID_MetadataFormatChunktIME
)
||
ok
(
IsEqualGUID
(
&
containerformat
,
&
GUID_MetadataFormatChunktIME
)
||
broken
(
IsEqualGUID
(
&
containerformat
,
&
GUID_MetadataFormatUnknown
))
/* Windows XP */
,
broken
(
IsEqualGUID
(
&
containerformat
,
&
GUID_MetadataFormatUnknown
))
/* Windows XP */
,
"unexpected container format
\n
"
);
"unexpected container format
\n
"
);
hr
=
IWICMetadataReader_GetCount
(
reader
,
&
count
);
hr
=
IWICMetadataReader_GetCount
(
reader
,
&
count
);
ok
(
hr
==
S_OK
,
"GetCount error %#lx
\n
"
,
hr
);
ok
(
hr
==
S_OK
,
"GetCount error %#lx
\n
"
,
hr
);
todo_wine
ok
(
count
==
6
||
broken
(
count
==
1
)
/* XP */
,
"expected 6, got %u
\n
"
,
count
);
ok
(
count
==
6
||
broken
(
count
==
1
)
/* XP */
,
"expected 6, got %u
\n
"
,
count
);
if
(
count
==
6
)
if
(
count
==
6
)
compare_metadata
(
reader
,
td
,
count
);
compare_metadata
(
reader
,
td
,
count
);
...
@@ -3272,6 +3316,7 @@ START_TEST(metadata)
...
@@ -3272,6 +3316,7 @@ START_TEST(metadata)
test_metadata_gAMA
();
test_metadata_gAMA
();
test_metadata_cHRM
();
test_metadata_cHRM
();
test_metadata_hIST
();
test_metadata_hIST
();
test_metadata_tIME
();
test_metadata_IFD
();
test_metadata_IFD
();
test_metadata_Exif
();
test_metadata_Exif
();
test_create_reader
();
test_create_reader
();
...
...
dlls/windowscodecs/wincodecs_private.h
View file @
432d8229
...
@@ -221,6 +221,7 @@ extern HRESULT PngChrmReader_CreateInstance(REFIID iid, void** ppv);
...
@@ -221,6 +221,7 @@ extern HRESULT PngChrmReader_CreateInstance(REFIID iid, void** ppv);
extern
HRESULT
PngGamaReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngGamaReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngHistReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngHistReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngTextReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngTextReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
PngTimeReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
LSDReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
LSDReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
IMDReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
IMDReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
GCEReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
extern
HRESULT
GCEReader_CreateInstance
(
REFIID
iid
,
void
**
ppv
);
...
...
dlls/windowscodecs/windowscodecs_wincodec.idl
View file @
432d8229
...
@@ -190,6 +190,13 @@ coclass WICPngHistMetadataReader { interface IWICMetadataReader; }
...
@@ -190,6 +190,13 @@ coclass WICPngHistMetadataReader { interface IWICMetadataReader; }
coclass
WICPngTextMetadataReader
{
interface
IWICMetadataReader
; }
coclass
WICPngTextMetadataReader
{
interface
IWICMetadataReader
; }
[
[
helpstring
(
"WIC Png tIME Metadata Reader"
),
threading
(
both
),
uuid
(
d94edf02
-
efe5
-
4
f0d
-
85
c8
-
f5a68b3000b1
)
]
coclass
WICPngTimeMetadataReader
{
interface
IWICMetadataReader
; }
[
helpstring
(
"WIC LSD Metadata Reader"
),
helpstring
(
"WIC LSD Metadata Reader"
),
threading
(
both
),
threading
(
both
),
uuid
(
41070793
-
59
e4
-
479
a
-
a1f7
-
954
adc2ef5fc
)
uuid
(
41070793
-
59
e4
-
479
a
-
a1f7
-
954
adc2ef5fc
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment