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
7b7011e5
Commit
7b7011e5
authored
Jan 23, 2010
by
Nikolay Sivov
Committed by
Alexandre Julliard
Jan 25, 2010
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
xmllite: Implement a query through IXmlReaderInput for underlying stream interface,.
parent
37b7de2b
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
164 additions
and
24 deletions
+164
-24
reader.c
dlls/xmllite/reader.c
+41
-14
reader.c
dlls/xmllite/tests/reader.c
+123
-10
No files found.
dlls/xmllite/reader.c
View file @
7b7011e5
...
...
@@ -34,17 +34,22 @@ WINE_DEFAULT_DEBUG_CHANNEL(xmllite);
/* not defined in public headers */
DEFINE_GUID
(
IID_IXmlReaderInput
,
0x0b3ccc9b
,
0x9214
,
0x428b
,
0xa2
,
0xae
,
0xef
,
0x3a
,
0xa8
,
0x71
,
0xaf
,
0xda
);
static
HRESULT
xmlreaderinput_query_for_stream
(
IXmlReaderInput
*
iface
,
void
**
pObj
);
typedef
struct
_xmlreader
{
const
IXmlReaderVtbl
*
lpVtbl
;
LONG
ref
;
IXmlReaderInput
*
input
;
ISequentialStream
*
stream
;
/* stored as sequential stream, cause currently
optimizations possible with IStream aren't implemented */
}
xmlreader
;
typedef
struct
_xmlreaderinput
{
const
IUnknownVtbl
*
lpVtbl
;
LONG
ref
;
IUnknown
*
input
;
/* reference passed on IXmlReaderInput creation */
}
xmlreaderinput
;
static
inline
xmlreader
*
impl_from_IXmlReader
(
IXmlReader
*
iface
)
...
...
@@ -96,7 +101,11 @@ static ULONG WINAPI xmlreader_Release(IXmlReader *iface)
ref
=
InterlockedDecrement
(
&
This
->
ref
);
if
(
ref
==
0
)
{
if
(
This
->
input
)
IUnknown_Release
(
This
->
input
);
if
(
This
->
input
)
{
IUnknown_Release
(
This
->
stream
);
IUnknown_Release
(
This
->
input
);
}
HeapFree
(
GetProcessHeap
(),
0
,
This
);
}
...
...
@@ -123,22 +132,22 @@ static HRESULT WINAPI xmlreader_SetInput(IXmlReader* iface, IUnknown *input)
hr
=
IUnknown_QueryInterface
(
input
,
&
IID_IXmlReaderInput
,
(
void
**
)
&
This
->
input
);
if
(
hr
!=
S_OK
)
{
IUnknown
*
stream_input
=
NULL
;
hr
=
IUnknown_QueryInterface
(
input
,
&
IID_ISequentialStream
,
(
void
**
)
&
stream_input
);
if
(
hr
!=
S_OK
)
{
hr
=
IUnknown_QueryInterface
(
input
,
&
IID_IStream
,
(
void
**
)
&
stream_input
);
if
(
hr
!=
S_OK
)
return
hr
;
}
/* create IXmlReaderInput basing on supplied interface */
IUnknown_Release
(
stream_input
);
return
CreateXmlReaderInputWithEncodingName
(
stream_input
,
hr
=
CreateXmlReaderInputWithEncodingName
(
input
,
NULL
,
NULL
,
FALSE
,
NULL
,
&
This
->
input
);
if
(
hr
!=
S_OK
)
return
hr
;
}
return
S_OK
;
/* set stream for supplied IXmlReaderInput */
hr
=
xmlreaderinput_query_for_stream
(
This
->
input
,
(
void
**
)
&
This
->
stream
);
if
(
hr
!=
S_OK
)
{
/* IXmlReaderInput doesn't provide streaming interface */
IUnknown_Release
(
This
->
input
);
This
->
input
=
NULL
;
}
return
hr
;
}
static
HRESULT
WINAPI
xmlreader_GetProperty
(
IXmlReader
*
iface
,
UINT
property
,
LONG_PTR
*
value
)
...
...
@@ -319,7 +328,22 @@ static const struct IXmlReaderVtbl xmlreader_vtbl =
xmlreader_IsEOF
};
/* IXmlReaderInput */
/** IXmlReaderInput **/
/* Queries already stored interface for IStream/ISequentialStream.
Interface supplied on creation will be overwritten */
static
HRESULT
xmlreaderinput_query_for_stream
(
IXmlReaderInput
*
iface
,
void
**
pObj
)
{
xmlreaderinput
*
This
=
impl_from_IXmlReaderInput
(
iface
);
HRESULT
hr
;
hr
=
IUnknown_QueryInterface
(
This
->
input
,
&
IID_IStream
,
pObj
);
if
(
hr
!=
S_OK
)
hr
=
IUnknown_QueryInterface
(
This
->
input
,
&
IID_ISequentialStream
,
pObj
);
return
hr
;
}
static
HRESULT
WINAPI
xmlreaderinput_QueryInterface
(
IXmlReaderInput
*
iface
,
REFIID
riid
,
void
**
ppvObject
)
{
xmlreaderinput
*
This
=
impl_from_IXmlReaderInput
(
iface
);
...
...
@@ -359,6 +383,7 @@ static ULONG WINAPI xmlreaderinput_Release(IXmlReaderInput *iface)
ref
=
InterlockedDecrement
(
&
This
->
ref
);
if
(
ref
==
0
)
{
if
(
This
->
input
)
IUnknown_Release
(
This
->
input
);
HeapFree
(
GetProcessHeap
(),
0
,
This
);
}
...
...
@@ -391,6 +416,7 @@ HRESULT WINAPI CreateXmlReader(REFIID riid, void **pObject, IMalloc *pMalloc)
reader
->
lpVtbl
=
&
xmlreader_vtbl
;
reader
->
ref
=
1
;
reader
->
stream
=
NULL
;
reader
->
input
=
NULL
;
*
pObject
=
&
reader
->
lpVtbl
;
...
...
@@ -419,6 +445,7 @@ HRESULT WINAPI CreateXmlReaderInputWithEncodingName(IUnknown *stream,
readerinput
->
lpVtbl
=
&
xmlreaderinput_vtbl
;
readerinput
->
ref
=
1
;
IUnknown_QueryInterface
(
stream
,
&
IID_IUnknown
,
(
void
**
)
&
readerinput
->
input
);
*
ppInput
=
(
IXmlReaderInput
*
)
&
readerinput
->
lpVtbl
;
...
...
dlls/xmllite/tests/reader.c
View file @
7b7011e5
...
...
@@ -58,15 +58,37 @@ typedef struct input_iids_t {
static
const
IID
*
setinput_full
[]
=
{
&
IID_IXmlReaderInput
,
&
IID_IStream
,
&
IID_ISequentialStream
,
&
IID_IStream
NULL
};
/* this applies to early xmllite versions */
static
const
IID
*
setinput_full_old
[]
=
{
&
IID_IXmlReaderInput
,
&
IID_ISequentialStream
,
&
IID_IStream
,
NULL
};
/* after ::SetInput(IXmlReaderInput*) */
static
const
IID
*
setinput_readerinput
[]
=
{
&
IID_IStream
,
&
IID_ISequentialStream
,
NULL
};
static
const
IID
*
empty_seq
[]
=
{
NULL
};
static
input_iids_t
input_iids
;
static
void
ok_iids_
(
const
input_iids_t
*
iids
,
const
IID
**
expected
,
int
size
,
int
todo
,
int
line
)
static
void
ok_iids_
(
const
input_iids_t
*
iids
,
const
IID
**
expected
,
const
IID
**
exp_broken
,
int
todo
,
int
line
)
{
int
i
;
int
i
=
0
,
size
=
0
;
while
(
expected
[
i
++
])
size
++
;
if
(
todo
)
{
todo_wine
...
...
@@ -78,11 +100,12 @@ static void ok_iids_(const input_iids_t *iids, const IID **expected, int size, i
if
(
iids
->
count
!=
size
)
return
;
for
(
i
=
0
;
i
<
size
;
i
++
)
{
ok_
(
__FILE__
,
line
)(
IsEqualGUID
(
&
iids
->
iids
[
i
],
expected
[
i
]),
"Wrong IID(%d), got (%s)
\n
"
,
i
,
debugstr_guid
(
&
iids
->
iids
[
i
]));
ok_
(
__FILE__
,
line
)(
IsEqualGUID
(
&
iids
->
iids
[
i
],
expected
[
i
])
||
(
exp_broken
?
broken
(
IsEqualGUID
(
&
iids
->
iids
[
i
],
exp_broken
[
i
]))
:
FALSE
),
"Wrong IID(%d), got (%s)
\n
"
,
i
,
debugstr_guid
(
&
iids
->
iids
[
i
]));
}
}
#define ok_iids(got, exp,
size, todo) ok_iids_(got, exp, size
, todo, __LINE__)
#define ok_iids(got, exp,
brk, todo) ok_iids_(got, exp, brk
, todo, __LINE__)
typedef
struct
_testinput
{
...
...
@@ -199,7 +222,7 @@ static void test_reader_create(void)
input_iids
.
count
=
0
;
hr
=
IXmlReader_SetInput
(
reader
,
input
);
ok
(
hr
==
E_NOINTERFACE
,
"Expected E_NOINTERFACE, got %08x
\n
"
,
hr
);
ok_iids
(
&
input_iids
,
setinput_full
,
s
izeof
(
setinput_full
)
/
sizeof
(
REFIID
)
,
FALSE
);
ok_iids
(
&
input_iids
,
setinput_full
,
s
etinput_full_old
,
FALSE
);
IUnknown_Release
(
input
);
...
...
@@ -209,7 +232,8 @@ static void test_reader_create(void)
static
void
test_readerinput
(
void
)
{
IXmlReaderInput
*
reader_input
;
IUnknown
*
obj
;
IXmlReader
*
reader
,
*
reader2
;
IUnknown
*
obj
,
*
input
;
IStream
*
stream
;
HRESULT
hr
;
LONG
ref
;
...
...
@@ -228,11 +252,40 @@ static void test_readerinput(void)
hr
=
pCreateXmlReaderInputWithEncodingName
((
IUnknown
*
)
stream
,
NULL
,
NULL
,
FALSE
,
NULL
,
&
reader_input
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
/* IXmlReader grabs a stream reference */
/* IXmlReader
Input
grabs a stream reference */
ref
=
IStream_AddRef
(
stream
);
todo_wine
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IStream_Release
(
stream
);
/* try ::SetInput() with valid IXmlReaderInput */
hr
=
pCreateXmlReader
(
&
IID_IXmlReader
,
(
LPVOID
*
)
&
reader
,
NULL
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
ref
=
IUnknown_AddRef
(
reader_input
);
ok
(
ref
==
2
,
"Expected 2, got %d
\n
"
,
ref
);
IUnknown_Release
(
reader_input
);
hr
=
IXmlReader_SetInput
(
reader
,
reader_input
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
/* IXmlReader grabs a IXmlReaderInput reference */
ref
=
IUnknown_AddRef
(
reader_input
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IUnknown_Release
(
reader_input
);
ref
=
IStream_AddRef
(
stream
);
ok
(
ref
==
4
,
"Expected 4, got %d
\n
"
,
ref
);
IStream_Release
(
stream
);
IXmlReader_Release
(
reader
);
ref
=
IStream_AddRef
(
stream
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IStream_Release
(
stream
);
ref
=
IUnknown_AddRef
(
reader_input
);
ok
(
ref
==
2
,
"Expected 2, got %d
\n
"
,
ref
);
IUnknown_Release
(
reader_input
);
/* IID_IXmlReaderInput */
/* it returns a kind of private undocumented vtable incompatible with IUnknown,
so it's not a COM interface actually.
...
...
@@ -246,6 +299,66 @@ static void test_readerinput(void)
IUnknown_Release
(
reader_input
);
IStream_Release
(
stream
);
/* test input interface selection sequence */
hr
=
testinput_createinstance
((
void
**
)
&
input
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
input_iids
.
count
=
0
;
ref
=
IUnknown_AddRef
(
input
);
ok
(
ref
==
2
,
"Expected 2, got %d
\n
"
,
ref
);
IUnknown_Release
(
input
);
hr
=
pCreateXmlReaderInputWithEncodingName
(
input
,
NULL
,
NULL
,
FALSE
,
NULL
,
&
reader_input
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
ok_iids
(
&
input_iids
,
empty_seq
,
NULL
,
FALSE
);
/* IXmlReaderInput stores stream interface as IUnknown */
ref
=
IUnknown_AddRef
(
input
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IUnknown_Release
(
input
);
hr
=
pCreateXmlReader
(
&
IID_IXmlReader
,
(
LPVOID
*
)
&
reader
,
NULL
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
input_iids
.
count
=
0
;
ref
=
IUnknown_AddRef
(
reader_input
);
ok
(
ref
==
2
,
"Expected 2, got %d
\n
"
,
ref
);
IUnknown_Release
(
reader_input
);
ref
=
IUnknown_AddRef
(
input
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IUnknown_Release
(
input
);
hr
=
IXmlReader_SetInput
(
reader
,
reader_input
);
ok
(
hr
==
E_NOINTERFACE
,
"Expected E_NOINTERFACE, got %08x
\n
"
,
hr
);
ok_iids
(
&
input_iids
,
setinput_readerinput
,
NULL
,
FALSE
);
ref
=
IUnknown_AddRef
(
input
);
ok
(
ref
==
3
,
"Expected 3, got %d
\n
"
,
ref
);
IUnknown_Release
(
input
);
ref
=
IUnknown_AddRef
(
reader_input
);
ok
(
ref
==
2
,
"Expected 2, got %d
\n
"
,
ref
);
IUnknown_Release
(
reader_input
);
/* repeat another time, no check or caching here */
input_iids
.
count
=
0
;
hr
=
IXmlReader_SetInput
(
reader
,
reader_input
);
ok
(
hr
==
E_NOINTERFACE
,
"Expected E_NOINTERFACE, got %08x
\n
"
,
hr
);
ok_iids
(
&
input_iids
,
setinput_readerinput
,
NULL
,
FALSE
);
/* another reader */
hr
=
pCreateXmlReader
(
&
IID_IXmlReader
,
(
LPVOID
*
)
&
reader2
,
NULL
);
ok
(
hr
==
S_OK
,
"Expected S_OK, got %08x
\n
"
,
hr
);
/* resolving from IXmlReaderInput to IStream/ISequentialStream is done at
::SetInput() level, each time it's called */
input_iids
.
count
=
0
;
hr
=
IXmlReader_SetInput
(
reader2
,
reader_input
);
ok
(
hr
==
E_NOINTERFACE
,
"Expected E_NOINTERFACE, got %08x
\n
"
,
hr
);
ok_iids
(
&
input_iids
,
setinput_readerinput
,
NULL
,
FALSE
);
IXmlReader_Release
(
reader2
);
IXmlReader_Release
(
reader
);
IUnknown_Release
(
reader_input
);
IUnknown_Release
(
input
);
}
START_TEST
(
reader
)
...
...
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