1 /* 2 * Copyright 2009 Tony Wasserka 3 * 4 * This library is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU Lesser General Public 6 * License as published by the Free Software Foundation; either 7 * version 2.1 of the License, or (at your option) any later version. 8 * 9 * This library is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * Lesser General Public License for more details. 13 * 14 * You should have received a copy of the GNU Lesser General Public 15 * License along with this library; if not, write to the Free Software 16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 17 */ 18 19 #include "wine/test.h" 20 21 #define COBJMACROS 22 #include "wincodec.h" 23 24 #define CHECK_CUR_POS(a, b) _check_cur_pos((IStream *)a, b, FALSE, __LINE__) 25 #define CHECK_CUR_POS_TODO(a, b) _check_cur_pos((IStream *)a, b, TRUE, __LINE__) 26 static void _check_cur_pos(IStream *stream, ULONGLONG expected_pos, BOOL todo, unsigned int line) 27 { 28 LARGE_INTEGER offset; 29 ULARGE_INTEGER pos; 30 HRESULT hr; 31 32 offset.QuadPart = 0; 33 hr = IStream_Seek(stream, offset, STREAM_SEEK_CUR, &pos); 34 ok_(__FILE__, line)(hr == S_OK, "Failed to get current position, hr %#x.\n", hr); 35 todo_wine_if(todo) 36 ok_(__FILE__, line)(pos.QuadPart == expected_pos, "Unexpected stream position %s.\n", 37 wine_dbgstr_longlong(pos.QuadPart)); 38 } 39 40 static void test_StreamOnMemory(void) 41 { 42 IWICImagingFactory *pFactory; 43 IWICStream *pStream, *pBufStream; 44 const BYTE CmpMem[] = { 45 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 46 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 47 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 48 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 49 }; 50 const BYTE CmpMemOverlap[] = { 51 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 52 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 53 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 54 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 55 }; 56 const BYTE ZeroMem[10] = {0}; 57 BYTE Memory[64], MemBuf[64]; 58 LARGE_INTEGER LargeNull, LargeInt, SeekPos; 59 ULARGE_INTEGER uLargeNull, uNewPos; 60 ULONG uBytesRead, uBytesWritten; 61 HRESULT hr; 62 STATSTG Stats; 63 64 LargeNull.QuadPart = 0; 65 uLargeNull.QuadPart = 0; 66 SeekPos.QuadPart = 5; 67 68 memcpy(Memory, CmpMem, sizeof(CmpMem)); 69 70 hr = CoCreateInstance(&CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, &IID_IWICImagingFactory, (void**)&pFactory); 71 if(FAILED(hr)) { 72 skip("CoCreateInstance returned with %#x, expected %#x\n", hr, S_OK); 73 return; 74 } 75 76 hr = IWICImagingFactory_CreateStream(pFactory, &pStream); 77 ok(hr == S_OK, "CreateStream returned with %#x, expected %#x\n", hr, S_OK); 78 if(FAILED(hr)) { 79 skip("Failed to create stream\n"); 80 return; 81 } 82 83 /* InitializeFromMemory */ 84 hr = IWICStream_InitializeFromMemory(pStream, NULL, sizeof(Memory)); /* memory = NULL */ 85 ok(hr == E_INVALIDARG, "InitializeFromMemory returned with %#x, expected %#x\n", hr, E_INVALIDARG); 86 87 hr = IWICStream_InitializeFromMemory(pStream, Memory, 0); /* size = 0 */ 88 ok(hr == S_OK, "InitializeFromMemory returned with %#x, expected %#x\n", hr, S_OK); 89 90 hr = IWICStream_InitializeFromMemory(pStream, Memory, sizeof(Memory)); /* stream already initialized */ 91 ok(hr == WINCODEC_ERR_WRONGSTATE, "InitializeFromMemory returned with %#x, expected %#x\n", hr, WINCODEC_ERR_WRONGSTATE); 92 93 /* recreate stream */ 94 IWICStream_Release(pStream); 95 hr = IWICImagingFactory_CreateStream(pFactory, &pStream); 96 ok(hr == S_OK, "CreateStream failed with %#x\n", hr); 97 98 hr = IWICStream_InitializeFromMemory(pStream, Memory, sizeof(Memory)); 99 ok(hr == S_OK, "InitializeFromMemory returned with %#x, expected %#x\n", hr, S_OK); 100 101 /* IWICStream does not maintain an independent copy of the backing memory buffer. */ 102 memcpy(Memory, ZeroMem, sizeof(ZeroMem)); 103 hr = IWICStream_Read(pStream, MemBuf, sizeof(ZeroMem), &uBytesRead); 104 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 105 if(SUCCEEDED(hr)) { 106 ok(uBytesRead == sizeof(ZeroMem), "Read %u bytes\n", uBytesRead); 107 ok(memcmp(MemBuf, ZeroMem, sizeof(ZeroMem)) == 0, "Read returned invalid data!\n"); 108 } 109 110 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 111 112 hr = IWICStream_Write(pStream, CmpMem, sizeof(CmpMem), &uBytesWritten); 113 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 114 115 /* Seek */ 116 hr = IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, &uNewPos); 117 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 118 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == 0, "Seek cursor moved to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0, 0); 119 120 hr = IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 121 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 122 123 LargeInt.u.HighPart = 1; 124 LargeInt.u.LowPart = 0; 125 uNewPos.u.HighPart = 0xdeadbeef; 126 uNewPos.u.LowPart = 0xdeadbeef; 127 hr = IWICStream_Seek(pStream, LargeInt, STREAM_SEEK_SET, &uNewPos); 128 ok(hr == HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW), "Seek returned with %#x, expected %#x\n", hr, HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW)); 129 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 130 CHECK_CUR_POS(pStream, 0); 131 132 LargeInt.QuadPart = sizeof(Memory) + 10; 133 uNewPos.u.HighPart = 0xdeadbeef; 134 uNewPos.u.LowPart = 0xdeadbeef; 135 hr = IWICStream_Seek(pStream, LargeInt, STREAM_SEEK_SET, &uNewPos); 136 ok(hr == E_INVALIDARG, "Seek returned with %#x, expected %#x\n", hr, E_INVALIDARG); 137 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 138 CHECK_CUR_POS(pStream, 0); 139 140 LargeInt.QuadPart = 1; 141 uNewPos.u.HighPart = 0xdeadbeef; 142 uNewPos.u.LowPart = 0xdeadbeef; 143 hr = IWICStream_Seek(pStream, LargeInt, STREAM_SEEK_END, &uNewPos); 144 ok(hr == E_INVALIDARG, "Seek returned with %#x, expected %#x\n", hr, E_INVALIDARG); 145 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 146 CHECK_CUR_POS(pStream, 0); 147 148 LargeInt.QuadPart = -1; 149 hr = IWICStream_Seek(pStream, LargeInt, STREAM_SEEK_END, &uNewPos); 150 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 151 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == sizeof(Memory) - 1, "bSeek cursor moved to position (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart); 152 153 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, &uNewPos); /* reset seek pointer */ 154 LargeInt.QuadPart = -(LONGLONG)sizeof(Memory) - 5; 155 uNewPos.u.HighPart = 0xdeadbeef; 156 uNewPos.u.LowPart = 0xdeadbeef; 157 hr = IWICStream_Seek(pStream, LargeInt, STREAM_SEEK_END, &uNewPos); 158 ok(hr == HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW), 159 "Seek returned with %#x, expected %#x\n", hr, HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW)); 160 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 161 CHECK_CUR_POS(pStream, 0); 162 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 163 164 /* Read */ 165 hr = IWICStream_Read(pStream, MemBuf, 12, &uBytesRead); 166 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 167 if(SUCCEEDED(hr)) { 168 ok(uBytesRead == 12, "Read %u bytes, expected %u\n", uBytesRead, 12); 169 ok(memcmp(MemBuf, CmpMem, 12) == 0, "Read returned invalid data!\n"); 170 171 /* check whether the seek pointer has moved correctly */ 172 CHECK_CUR_POS(pStream, uBytesRead); 173 } 174 175 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 176 177 hr = IWICStream_Read(pStream, Memory, 10, &uBytesRead); /* source = dest */ 178 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 179 if(SUCCEEDED(hr)) { 180 ok(uBytesRead == 10, "Read %u bytes, expected %u\n", uBytesRead, 10); 181 ok(memcmp(Memory, CmpMem, uBytesRead) == 0, "Read returned invalid data!\n"); 182 } 183 184 IWICStream_Seek(pStream, SeekPos, STREAM_SEEK_SET, NULL); 185 186 hr = IWICStream_Read(pStream, Memory, 10, &uBytesRead); /* source and dest overlap */ 187 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 188 if(SUCCEEDED(hr)) { 189 ok(uBytesRead == 10, "Read %u bytes, expected %u\n", uBytesRead, 10); 190 ok(memcmp(Memory, CmpMemOverlap, uBytesRead) == 0, "Read returned invalid data!\n"); 191 } 192 193 memcpy(Memory, CmpMem, sizeof(CmpMem)); 194 195 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 196 197 hr = IWICStream_Read(pStream, Memory, sizeof(Memory) + 10, &uBytesRead); /* request too many bytes */ 198 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 199 if(SUCCEEDED(hr)) { 200 ok(uBytesRead == sizeof(Memory), "Read %u bytes\n", uBytesRead); 201 ok(memcmp(Memory, CmpMem, uBytesRead) == 0, "Read returned invalid data!\n"); 202 } 203 204 hr = IWICStream_Read(pStream, NULL, 1, &uBytesRead); /* destination buffer = NULL */ 205 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 206 207 hr = IWICStream_Read(pStream, MemBuf, 0, &uBytesRead); /* read 0 bytes */ 208 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 209 210 hr = IWICStream_Read(pStream, NULL, 0, &uBytesRead); 211 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 212 213 hr = IWICStream_Read(pStream, NULL, 0, NULL); 214 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 215 216 hr = IWICStream_Read(pStream, MemBuf, 1, NULL); 217 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 218 219 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 220 ZeroMemory(MemBuf, sizeof(MemBuf)); 221 hr = IWICStream_Read(pStream, MemBuf, sizeof(Memory) + 10, &uBytesRead); 222 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 223 if(SUCCEEDED(hr)) { 224 ok(uBytesRead == sizeof(Memory), "Read %u bytes\n", uBytesRead); 225 ok(memcmp(Memory, CmpMem, 64) == 0, "Read returned invalid data!\n"); 226 } 227 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 228 229 230 /* Write */ 231 MemBuf[0] = CmpMem[0] + 1; 232 MemBuf[1] = CmpMem[1] + 1; 233 MemBuf[2] = CmpMem[2] + 1; 234 hr = IWICStream_Write(pStream, MemBuf, 3, &uBytesWritten); 235 ok(hr == S_OK, "Write returned with %#x, expected %#x\n", hr, S_OK); 236 if(SUCCEEDED(hr)) { 237 ok(uBytesWritten == 3, "Wrote %u bytes, expected %u\n", uBytesWritten, 3); 238 ok(memcmp(MemBuf, Memory, 3) == 0, "Wrote returned invalid data!\n"); /* make sure we're writing directly */ 239 240 /* check whether the seek pointer has moved correctly */ 241 CHECK_CUR_POS(pStream, uBytesWritten); 242 } 243 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 244 245 hr = IWICStream_Write(pStream, MemBuf, 0, &uBytesWritten); 246 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 247 248 /* Restore the original contents of the memory stream. */ 249 hr = IWICStream_Write(pStream, CmpMem, sizeof(CmpMem), &uBytesWritten); 250 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 251 252 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 253 254 /* Source and destination overlap. */ 255 hr = IWICStream_Write(pStream, Memory + 5, 10, &uBytesWritten); 256 ok(hr == S_OK, "Write returned with %#x, expected %#x\n", hr, S_OK); 257 if(SUCCEEDED(hr)) { 258 ok(uBytesWritten == 10, "Wrote %u bytes, expected %u\n", uBytesWritten, 10); 259 ok(memcmp(CmpMemOverlap, Memory, sizeof(CmpMemOverlap)) == 0, "Wrote returned invalid data!\n"); 260 } 261 262 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 263 264 uBytesWritten = 0xdeadbeef; 265 hr = IWICStream_Write(pStream, NULL, 3, &uBytesWritten); 266 ok(hr == E_INVALIDARG, "Write returned with %#x, expected %#x\n", hr, E_INVALIDARG); 267 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 268 CHECK_CUR_POS(pStream, 0); 269 270 uBytesWritten = 0xdeadbeef; 271 hr = IWICStream_Write(pStream, NULL, 0, &uBytesWritten); 272 ok(hr == E_INVALIDARG, "Write returned with %#x, expected %#x\n", hr, E_INVALIDARG); 273 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 274 CHECK_CUR_POS(pStream, 0); 275 276 uBytesWritten = 0xdeadbeef; 277 hr = IWICStream_Write(pStream, CmpMem, sizeof(Memory) + 10, &uBytesWritten); 278 ok(hr == STG_E_MEDIUMFULL, "Write returned with %#x, expected %#x\n", hr, STG_E_MEDIUMFULL); 279 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 280 CHECK_CUR_POS(pStream, 0); 281 IWICStream_Seek(pStream, LargeNull, STREAM_SEEK_SET, NULL); 282 283 284 /* SetSize */ 285 uNewPos.u.HighPart = 0; 286 uNewPos.u.LowPart = sizeof(Memory) + 10; 287 hr = IWICStream_SetSize(pStream, uNewPos); 288 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 289 290 uNewPos.u.HighPart = 0; 291 uNewPos.u.LowPart = sizeof(Memory); 292 hr = IWICStream_SetSize(pStream, uNewPos); 293 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 294 295 uNewPos.u.HighPart = 0; 296 uNewPos.u.LowPart = sizeof(Memory) - 10; 297 hr = IWICStream_SetSize(pStream, uNewPos); 298 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 299 300 uNewPos.u.HighPart = 0; 301 uNewPos.u.LowPart = 0; 302 hr = IWICStream_SetSize(pStream, uNewPos); 303 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 304 305 uNewPos.QuadPart = -10; 306 hr = IWICStream_SetSize(pStream, uNewPos); 307 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 308 309 310 /* CopyTo */ 311 uNewPos.u.HighPart = 0; 312 uNewPos.u.LowPart = 5; 313 hr = IWICStream_CopyTo(pStream, NULL, uNewPos, NULL, NULL); 314 ok(hr == E_NOTIMPL, "CopyTo returned %#x, expected %#x\n", hr, E_NOTIMPL); 315 316 hr = IWICImagingFactory_CreateStream(pFactory, &pBufStream); 317 ok(hr == S_OK, "CreateStream failed with %#x\n", hr); 318 319 hr = IWICStream_InitializeFromMemory(pBufStream, Memory, sizeof(Memory)); 320 ok(hr == S_OK, "InitializeFromMemory returned with %#x, expected %#x\n", hr, S_OK); 321 322 hr = IWICStream_CopyTo(pStream, (IStream*)pBufStream, uNewPos, NULL, NULL); 323 ok(hr == E_NOTIMPL, "CopyTo returned %#x, expected %#x\n", hr, E_NOTIMPL); 324 IWICStream_Release(pBufStream); 325 326 327 /* Commit */ 328 hr = IWICStream_Commit(pStream, STGC_DEFAULT); 329 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 330 331 hr = IWICStream_Commit(pStream, STGC_OVERWRITE); 332 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 333 334 hr = IWICStream_Commit(pStream, STGC_ONLYIFCURRENT); 335 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 336 337 hr = IWICStream_Commit(pStream, STGC_DANGEROUSLYCOMMITMERELYTODISKCACHE); 338 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 339 340 hr = IWICStream_Commit(pStream, STGC_CONSOLIDATE); 341 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 342 343 344 /* Revert */ 345 IWICStream_Write(pStream, &MemBuf[5], 6, NULL); 346 hr = IWICStream_Revert(pStream); 347 ok(hr == E_NOTIMPL, "Revert returned %#x, expected %#x\n", hr, E_NOTIMPL); 348 memcpy(Memory, CmpMem, sizeof(Memory)); 349 350 351 /* LockRegion/UnlockRegion */ 352 hr = IWICStream_LockRegion(pStream, uLargeNull, uLargeNull, 0); 353 ok(hr == E_NOTIMPL, "LockRegion returned %#x, expected %#x\n", hr, E_NOTIMPL); 354 355 hr = IWICStream_UnlockRegion(pStream, uLargeNull, uLargeNull, 0); 356 ok(hr == E_NOTIMPL, "UnlockRegion returned %#x, expected %#x\n", hr, E_NOTIMPL); 357 358 359 /* Stat */ 360 hr = IWICStream_Stat(pStream, NULL, 0); 361 ok(hr == E_INVALIDARG, "Stat returned %#x, expected %#x\n", hr, E_INVALIDARG); 362 363 hr = IWICStream_Stat(pStream, &Stats, 0); 364 ok(hr == S_OK, "Stat returned %#x, expected %#x\n", hr, S_OK); 365 ok(Stats.pwcsName == NULL, "Stat returned name %p, expected %p\n", Stats.pwcsName, NULL); 366 ok(Stats.type == STGTY_STREAM, "Stat returned type %d, expected %d\n", Stats.type, STGTY_STREAM); 367 ok(Stats.cbSize.u.HighPart == 0 && Stats.cbSize.u.LowPart == sizeof(Memory), "Stat returned size (%u;%u)\n", Stats.cbSize.u.HighPart, Stats.cbSize.u.LowPart); 368 ok(Stats.mtime.dwHighDateTime == 0 && Stats.mtime.dwLowDateTime == 0, "Stat returned mtime (%u;%u), expected (%u;%u)\n", Stats.mtime.dwHighDateTime, Stats.mtime.dwLowDateTime, 0, 0); 369 ok(Stats.ctime.dwHighDateTime == 0 && Stats.ctime.dwLowDateTime == 0, "Stat returned ctime (%u;%u), expected (%u;%u)\n", Stats.ctime.dwHighDateTime, Stats.ctime.dwLowDateTime, 0, 0); 370 ok(Stats.atime.dwHighDateTime == 0 && Stats.atime.dwLowDateTime == 0, "Stat returned atime (%u;%u), expected (%u;%u)\n", Stats.atime.dwHighDateTime, Stats.atime.dwLowDateTime, 0, 0); 371 ok(Stats.grfMode == 0, "Stat returned access mode %d, expected %d\n", Stats.grfMode, 0); 372 ok(Stats.grfLocksSupported == 0, "Stat returned supported locks %#x, expected %#x\n", Stats.grfLocksSupported, 0); 373 ok(Stats.grfStateBits == 0, "Stat returned state bits %#x, expected %#x\n", Stats.grfStateBits, 0); 374 375 376 /* Clone */ 377 hr = IWICStream_Clone(pStream, (IStream**)&pBufStream); 378 ok(hr == E_NOTIMPL, "UnlockRegion returned %#x, expected %#x\n", hr, E_NOTIMPL); 379 380 381 IWICStream_Release(pStream); 382 IWICImagingFactory_Release(pFactory); 383 } 384 385 static void test_StreamOnStreamRange(void) 386 { 387 IWICImagingFactory *pFactory; 388 IWICStream *pStream, *pSubStream; 389 IStream *CopyStream; 390 const BYTE CmpMem[] = { 391 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 392 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 393 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 394 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 395 }; 396 BYTE Memory[64], MemBuf[64]; 397 LARGE_INTEGER LargeNull, LargeInt; 398 ULARGE_INTEGER uLargeNull, uNewPos, uSize; 399 ULONG uBytesRead, uBytesWritten; 400 HRESULT hr; 401 STATSTG Stats; 402 403 LargeNull.QuadPart = 0; 404 uLargeNull.QuadPart = 0; 405 406 memcpy(Memory, CmpMem, sizeof(CmpMem)); 407 408 CoInitialize(NULL); 409 410 hr = CoCreateInstance(&CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, &IID_IWICImagingFactory, (void**)&pFactory); 411 if(FAILED(hr)) { 412 skip("CoCreateInstance returned with %#x, expected %#x\n", hr, S_OK); 413 return; 414 } 415 416 hr = IWICImagingFactory_CreateStream(pFactory, &pStream); 417 ok(hr == S_OK, "CreateStream returned with %#x, expected %#x\n", hr, S_OK); 418 if(FAILED(hr)) { 419 skip("Failed to create stream\n"); 420 return; 421 } 422 423 hr = IWICStream_InitializeFromMemory(pStream, Memory, sizeof(Memory)); 424 ok(hr == S_OK, "InitializeFromMemory returned with %#x, expected %#x\n", hr, S_OK); 425 426 hr = IWICImagingFactory_CreateStream(pFactory, &pSubStream); 427 ok(hr == S_OK, "CreateStream returned with %#x, expected %#x\n", hr, S_OK); 428 429 uNewPos.QuadPart = 20; 430 uSize.QuadPart = 20; 431 hr = IWICStream_InitializeFromIStreamRegion(pSubStream, (IStream*)pStream, uNewPos, uSize); 432 ok(hr == S_OK, "InitializeFromIStreamRegion returned with %#x, expected %#x\n", hr, S_OK); 433 if(FAILED(hr)) { 434 skip("InitializeFromIStreamRegion unimplemented\n"); 435 IWICStream_Release(pSubStream); 436 IWICStream_Release(pStream); 437 IWICImagingFactory_Release(pFactory); 438 CoUninitialize(); 439 return; 440 } 441 442 /* Seek */ 443 CHECK_CUR_POS(pStream, 0); 444 hr = IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_END, &uNewPos); 445 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == 20, "Seek cursor moved to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0, 20); 446 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 447 CHECK_CUR_POS(pStream, 0); 448 449 hr = IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, &uNewPos); 450 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 451 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == 0, "Seek cursor moved to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0, 0); 452 CHECK_CUR_POS(pStream, 0); 453 454 hr = IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 455 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 456 457 LargeInt.u.HighPart = 1; 458 LargeInt.u.LowPart = 0; 459 uNewPos.u.HighPart = 0xdeadbeef; 460 uNewPos.u.LowPart = 0xdeadbeef; 461 hr = IWICStream_Seek(pSubStream, LargeInt, STREAM_SEEK_SET, &uNewPos); 462 ok(hr == WINCODEC_ERR_VALUEOUTOFRANGE, "Seek returned with %#x, expected %#x\n", hr, WINCODEC_ERR_VALUEOUTOFRANGE); 463 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 464 CHECK_CUR_POS(pStream, 0); 465 466 LargeInt.QuadPart = 30; 467 uNewPos.u.HighPart = 0xdeadbeef; 468 uNewPos.u.LowPart = 0xdeadbeef; 469 hr = IWICStream_Seek(pSubStream, LargeInt, STREAM_SEEK_SET, &uNewPos); 470 ok(hr == WINCODEC_ERR_VALUEOUTOFRANGE, "Seek returned with %#x, expected %#x\n", hr, WINCODEC_ERR_VALUEOUTOFRANGE); 471 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 472 CHECK_CUR_POS(pStream, 0); 473 474 LargeInt.QuadPart = 1; 475 uNewPos.u.HighPart = 0xdeadbeef; 476 uNewPos.u.LowPart = 0xdeadbeef; 477 hr = IWICStream_Seek(pSubStream, LargeInt, STREAM_SEEK_END, &uNewPos); 478 ok(hr == WINCODEC_ERR_VALUEOUTOFRANGE, "Seek returned with %#x, expected %#x\n", hr, WINCODEC_ERR_VALUEOUTOFRANGE); 479 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 480 CHECK_CUR_POS(pStream, 0); 481 482 LargeInt.QuadPart = -1; 483 hr = IWICStream_Seek(pSubStream, LargeInt, STREAM_SEEK_END, &uNewPos); 484 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 485 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == 19, "bSeek cursor moved to position (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart); 486 CHECK_CUR_POS(pStream, 0); 487 488 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, &uNewPos); /* reset seek pointer */ 489 LargeInt.QuadPart = -25; 490 uNewPos.u.HighPart = 0xdeadbeef; 491 uNewPos.u.LowPart = 0xdeadbeef; 492 hr = IWICStream_Seek(pSubStream, LargeInt, STREAM_SEEK_END, &uNewPos); 493 ok(hr == WINCODEC_ERR_VALUEOUTOFRANGE, 494 "Seek returned with %#x, expected %#x\n", hr, HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW)); 495 ok(uNewPos.u.HighPart == 0xdeadbeef && uNewPos.u.LowPart == 0xdeadbeef, "Seek cursor initialized to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0xdeadbeef, 0xdeadbeef); 496 CHECK_CUR_POS(pStream, 0); 497 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 498 499 500 /* Read */ 501 hr = IWICStream_Read(pSubStream, MemBuf, 12, &uBytesRead); 502 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 503 if(SUCCEEDED(hr)) { 504 ok(uBytesRead == 12, "Read %u bytes, expected %u\n", uBytesRead, 12); 505 ok(memcmp(MemBuf, CmpMem+20, 12) == 0, "Read returned invalid data!\n"); 506 507 /* check whether the seek pointer has moved correctly */ 508 CHECK_CUR_POS(pSubStream, uBytesRead); 509 CHECK_CUR_POS(pStream, 0); 510 } 511 512 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 513 514 hr = IWICStream_Read(pSubStream, Memory, 10, &uBytesRead); /* source = dest */ 515 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 516 if(SUCCEEDED(hr)) { 517 ok(uBytesRead == 10, "Read %u bytes, expected %u\n", uBytesRead, 10); 518 ok(memcmp(Memory, CmpMem+20, uBytesRead) == 0, "Read returned invalid data!\n"); 519 } 520 CHECK_CUR_POS(pStream, 0); 521 522 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 523 524 hr = IWICStream_Read(pSubStream, Memory, 30, &uBytesRead); /* request too many bytes */ 525 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 526 if(SUCCEEDED(hr)) { 527 ok(uBytesRead == 20, "Read %u bytes\n", uBytesRead); 528 ok(memcmp(Memory, CmpMem+20, uBytesRead) == 0, "Read returned invalid data!\n"); 529 } 530 CHECK_CUR_POS(pStream, 0); 531 532 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 533 uBytesRead = 0xdeadbeef; 534 hr = IWICStream_Read(pSubStream, NULL, 1, &uBytesRead); /* destination buffer = NULL */ 535 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 536 ok(uBytesRead == 0xdeadbeef, "Expected uBytesRead to be unchanged, got %u\n", uBytesRead); 537 538 hr = IWICStream_Read(pSubStream, MemBuf, 0, &uBytesRead); /* read 0 bytes */ 539 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 540 541 uBytesRead = 0xdeadbeef; 542 hr = IWICStream_Read(pSubStream, NULL, 0, &uBytesRead); 543 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 544 ok(uBytesRead == 0xdeadbeef, "Expected uBytesRead to be unchanged, got %u\n", uBytesRead); 545 546 hr = IWICStream_Read(pSubStream, NULL, 0, NULL); 547 ok(hr == E_INVALIDARG, "Read returned with %#x, expected %#x\n", hr, E_INVALIDARG); 548 549 hr = IWICStream_Read(pSubStream, MemBuf, 1, NULL); 550 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 551 552 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 553 ZeroMemory(MemBuf, sizeof(MemBuf)); 554 hr = IWICStream_Read(pSubStream, MemBuf, 30, &uBytesRead); 555 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 556 if(SUCCEEDED(hr)) { 557 ok(uBytesRead == 20, "Read %u bytes\n", uBytesRead); 558 ok(memcmp(Memory, CmpMem+20, 20) == 0, "Read returned invalid data!\n"); 559 } 560 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 561 562 563 /* Write */ 564 MemBuf[0] = CmpMem[0] + 1; 565 MemBuf[1] = CmpMem[1] + 1; 566 MemBuf[2] = CmpMem[2] + 1; 567 hr = IWICStream_Write(pSubStream, MemBuf, 3, &uBytesWritten); 568 ok(hr == S_OK, "Write returned with %#x, expected %#x\n", hr, S_OK); 569 if(SUCCEEDED(hr)) { 570 ok(uBytesWritten == 3, "Wrote %u bytes, expected %u\n", uBytesWritten, 3); 571 ok(memcmp(MemBuf, Memory+20, 3) == 0, "Wrote returned invalid data!\n"); /* make sure we're writing directly */ 572 573 /* check whether the seek pointer has moved correctly */ 574 CHECK_CUR_POS(pSubStream, uBytesWritten); 575 CHECK_CUR_POS(pStream, 0); 576 } 577 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 578 579 hr = IWICStream_Write(pSubStream, MemBuf, 0, &uBytesWritten); 580 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 581 582 uBytesWritten = 0xdeadbeef; 583 hr = IWICStream_Write(pSubStream, NULL, 3, &uBytesWritten); 584 ok(hr == E_INVALIDARG, "Write returned with %#x, expected %#x\n", hr, E_INVALIDARG); 585 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 586 CHECK_CUR_POS(pSubStream, 0); 587 CHECK_CUR_POS(pStream, 0); 588 589 uBytesWritten = 0xdeadbeef; 590 hr = IWICStream_Write(pSubStream, NULL, 0, &uBytesWritten); 591 ok(hr == E_INVALIDARG, "Write returned with %#x, expected %#x\n", hr, E_INVALIDARG); 592 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 593 CHECK_CUR_POS(pSubStream, 0); 594 CHECK_CUR_POS(pStream, 0); 595 596 hr = IWICStream_Write(pSubStream, CmpMem, 30, &uBytesWritten); 597 ok(hr == S_OK, "Write returned with %#x, expected %#x\n", hr, STG_E_MEDIUMFULL); 598 ok(uBytesWritten == 20, "Wrote %u bytes, expected %u\n", uBytesWritten, 0); 599 CHECK_CUR_POS(pSubStream, uBytesWritten); 600 CHECK_CUR_POS(pStream, 0); 601 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 602 603 604 /* SetSize */ 605 uNewPos.u.HighPart = 0; 606 uNewPos.u.LowPart = sizeof(Memory) + 10; 607 hr = IWICStream_SetSize(pSubStream, uNewPos); 608 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 609 610 uNewPos.u.HighPart = 0; 611 uNewPos.u.LowPart = sizeof(Memory); 612 hr = IWICStream_SetSize(pSubStream, uNewPos); 613 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 614 615 uNewPos.u.HighPart = 0; 616 uNewPos.u.LowPart = sizeof(Memory) - 10; 617 hr = IWICStream_SetSize(pSubStream, uNewPos); 618 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 619 620 uNewPos.u.HighPart = 0; 621 uNewPos.u.LowPart = 0; 622 hr = IWICStream_SetSize(pSubStream, uNewPos); 623 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 624 625 uNewPos.QuadPart = -10; 626 hr = IWICStream_SetSize(pSubStream, uNewPos); 627 ok(hr == E_NOTIMPL, "SetSize returned %#x, expected %#x\n", hr, E_NOTIMPL); 628 629 630 /* CopyTo */ 631 uNewPos.u.HighPart = 0; 632 uNewPos.u.LowPart = 30; 633 hr = IWICStream_CopyTo(pSubStream, NULL, uNewPos, NULL, NULL); 634 ok(hr == E_NOTIMPL, "CopyTo returned %#x, expected %#x\n", hr, E_NOTIMPL); 635 636 hr = CreateStreamOnHGlobal(NULL, TRUE, &CopyStream); 637 ok(hr == S_OK, "CreateStream failed with %#x\n", hr); 638 639 hr = IWICStream_CopyTo(pSubStream, CopyStream, uNewPos, NULL, NULL); 640 ok(hr == E_NOTIMPL, "CopyTo returned %#x, expected %#x\n", hr, E_NOTIMPL); 641 IStream_Release(CopyStream); 642 643 644 /* Commit */ 645 hr = IWICStream_Commit(pSubStream, STGC_DEFAULT); 646 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 647 648 hr = IWICStream_Commit(pSubStream, STGC_OVERWRITE); 649 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 650 651 hr = IWICStream_Commit(pSubStream, STGC_ONLYIFCURRENT); 652 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 653 654 hr = IWICStream_Commit(pSubStream, STGC_DANGEROUSLYCOMMITMERELYTODISKCACHE); 655 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 656 657 hr = IWICStream_Commit(pSubStream, STGC_CONSOLIDATE); 658 ok(hr == E_NOTIMPL, "Commit returned %#x, expected %#x\n", hr, E_NOTIMPL); 659 660 661 /* Revert */ 662 IWICStream_Write(pSubStream, &MemBuf[5], 6, NULL); 663 hr = IWICStream_Revert(pSubStream); 664 ok(hr == E_NOTIMPL, "Revert returned %#x, expected %#x\n", hr, E_NOTIMPL); 665 memcpy(Memory, CmpMem, sizeof(Memory)); 666 667 668 /* LockRegion/UnlockRegion */ 669 hr = IWICStream_LockRegion(pSubStream, uLargeNull, uLargeNull, 0); 670 ok(hr == E_NOTIMPL, "LockRegion returned %#x, expected %#x\n", hr, E_NOTIMPL); 671 672 hr = IWICStream_UnlockRegion(pSubStream, uLargeNull, uLargeNull, 0); 673 ok(hr == E_NOTIMPL, "UnlockRegion returned %#x, expected %#x\n", hr, E_NOTIMPL); 674 675 676 /* Stat */ 677 hr = IWICStream_Stat(pSubStream, NULL, 0); 678 ok(hr == E_INVALIDARG, "Stat returned %#x, expected %#x\n", hr, E_INVALIDARG); 679 680 hr = IWICStream_Stat(pSubStream, &Stats, 0); 681 ok(hr == S_OK, "Stat returned %#x, expected %#x\n", hr, S_OK); 682 ok(Stats.pwcsName == NULL, "Stat returned name %p, expected %p\n", Stats.pwcsName, NULL); 683 ok(Stats.type == STGTY_STREAM, "Stat returned type %d, expected %d\n", Stats.type, STGTY_STREAM); 684 ok(Stats.cbSize.u.HighPart == 0 && Stats.cbSize.u.LowPart == 20, "Stat returned size (%u;%u)\n", Stats.cbSize.u.HighPart, Stats.cbSize.u.LowPart); 685 ok(Stats.mtime.dwHighDateTime == 0 && Stats.mtime.dwLowDateTime == 0, "Stat returned mtime (%u;%u), expected (%u;%u)\n", Stats.mtime.dwHighDateTime, Stats.mtime.dwLowDateTime, 0, 0); 686 ok(Stats.ctime.dwHighDateTime == 0 && Stats.ctime.dwLowDateTime == 0, "Stat returned ctime (%u;%u), expected (%u;%u)\n", Stats.ctime.dwHighDateTime, Stats.ctime.dwLowDateTime, 0, 0); 687 ok(Stats.atime.dwHighDateTime == 0 && Stats.atime.dwLowDateTime == 0, "Stat returned atime (%u;%u), expected (%u;%u)\n", Stats.atime.dwHighDateTime, Stats.atime.dwLowDateTime, 0, 0); 688 ok(Stats.grfMode == 0, "Stat returned access mode %d, expected %d\n", Stats.grfMode, 0); 689 ok(Stats.grfLocksSupported == 0, "Stat returned supported locks %#x, expected %#x\n", Stats.grfLocksSupported, 0); 690 ok(Stats.grfStateBits == 0, "Stat returned state bits %#x, expected %#x\n", Stats.grfStateBits, 0); 691 692 693 /* Clone */ 694 hr = IWICStream_Clone(pSubStream, &CopyStream); 695 ok(hr == E_NOTIMPL, "Clone returned %#x, expected %#x\n", hr, E_NOTIMPL); 696 697 698 IWICStream_Release(pSubStream); 699 700 701 /* Recreate, this time larger than the original. */ 702 hr = IWICImagingFactory_CreateStream(pFactory, &pSubStream); 703 ok(hr == S_OK, "CreateStream returned with %#x, expected %#x\n", hr, S_OK); 704 705 uNewPos.QuadPart = 48; 706 uSize.QuadPart = 32; 707 hr = IWICStream_InitializeFromIStreamRegion(pSubStream, (IStream*)pStream, uNewPos, uSize); 708 ok(hr == S_OK, "InitializeFromMemory returned with %#x, expected %#x\n", hr, S_OK); 709 710 hr = IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_END, &uNewPos); 711 ok(hr == S_OK, "Seek returned with %#x, expected %#x\n", hr, S_OK); 712 ok(uNewPos.u.HighPart == 0 && uNewPos.u.LowPart == 16, "Seek cursor moved to position (%u;%u), expected (%u;%u)\n", uNewPos.u.HighPart, uNewPos.u.LowPart, 0, 16); 713 714 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 715 hr = IWICStream_Read(pSubStream, Memory, 48, &uBytesRead); 716 ok(hr == S_OK, "Read returned with %#x, expected %#x\n", hr, S_OK); 717 if(SUCCEEDED(hr)) { 718 ok(uBytesRead == 16, "Read %u bytes\n", uBytesRead); 719 ok(memcmp(Memory, CmpMem+48, uBytesRead) == 0, "Read returned invalid data!\n"); 720 } 721 722 IWICStream_Seek(pSubStream, LargeNull, STREAM_SEEK_SET, NULL); 723 uBytesWritten = 0xdeadbeef; 724 hr = IWICStream_Write(pSubStream, CmpMem, 32, &uBytesWritten); 725 ok(hr == STG_E_MEDIUMFULL, "Write returned with %#x, expected %#x\n", hr, STG_E_MEDIUMFULL); 726 ok(uBytesWritten == 0xdeadbeef, "Expected uBytesWritten to be unchanged, got %u\n", uBytesWritten); 727 CHECK_CUR_POS(pSubStream, 0); 728 CHECK_CUR_POS(pStream, 0); 729 730 IWICStream_Release(pSubStream); 731 IWICStream_Release(pStream); 732 IWICImagingFactory_Release(pFactory); 733 CoUninitialize(); 734 } 735 736 static void test_StreamOnIStream(void) 737 { 738 static const BYTE data[] = 739 { 740 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 741 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 742 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 743 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 744 }; 745 static const LARGE_INTEGER zero_pos; 746 static const ULARGE_INTEGER uzero; 747 IWICStream *stream, *substream; 748 IWICImagingFactory *factory; 749 BYTE memory[64], buff[64]; 750 ULONG read_len, written; 751 ULARGE_INTEGER newpos; 752 IStream *copy_stream; 753 LARGE_INTEGER pos; 754 unsigned int i; 755 STATSTG stats; 756 HRESULT hr; 757 758 memcpy(memory, data, sizeof(data)); 759 760 hr = CoCreateInstance(&CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, 761 &IID_IWICImagingFactory, (void **)&factory); 762 ok(hr == S_OK, "Failed to create a factory, hr %#x.\n", hr); 763 764 hr = IWICImagingFactory_CreateStream(factory, &stream); 765 ok(hr == S_OK, "Failed to create a stream, hr %#x.\n", hr); 766 767 hr = IWICStream_InitializeFromMemory(stream, memory, sizeof(memory)); 768 ok(hr == S_OK, "Failed to initialize stream, hr %#x.\n", hr); 769 770 hr = IWICImagingFactory_CreateStream(factory, &substream); 771 ok(hr == S_OK, "Failed to create a stream, hr %#x.\n", hr); 772 773 pos.QuadPart = 1; 774 hr = IWICStream_Seek(stream, pos, STREAM_SEEK_SET, &newpos); 775 ok(hr == S_OK, "Failed to set position, hr %#x.\n", hr); 776 CHECK_CUR_POS(stream, 1); 777 778 hr = IWICStream_InitializeFromIStream(substream, (IStream *)stream); 779 ok(hr == S_OK, "Failed to initialize stream, hr %#x.\n", hr); 780 CHECK_CUR_POS(substream, 1); 781 782 /* Seek */ 783 CHECK_CUR_POS(stream, 1); 784 hr = IWICStream_Seek(substream, zero_pos, STREAM_SEEK_END, &newpos); 785 ok(hr == S_OK, "Failed to seek a stream, hr %#x.\n", hr); 786 ok(newpos.QuadPart == sizeof(memory), "Unexpected position %s.\n", wine_dbgstr_longlong(newpos.QuadPart)); 787 CHECK_CUR_POS(substream, sizeof(memory)); 788 CHECK_CUR_POS(stream, sizeof(memory)); 789 790 hr = IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, &newpos); 791 ok(hr == S_OK, "Failed to seek a stream, hr %#x.\n", hr); 792 ok(newpos.QuadPart == 0, "Unexpected position %s.\n", wine_dbgstr_longlong(newpos.QuadPart)); 793 CHECK_CUR_POS(stream, 0); 794 CHECK_CUR_POS(substream, 0); 795 796 hr = IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 797 ok(hr == S_OK, "Failed to seek a stream, hr %#x.\n", hr); 798 799 pos.u.HighPart = 1; 800 pos.u.LowPart = 0; 801 newpos.u.HighPart = 0xdeadbeef; 802 newpos.u.LowPart = 0xdeadbeef; 803 hr = IWICStream_Seek(substream, pos, STREAM_SEEK_SET, &newpos); 804 ok(hr == HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW), "Unexpected hr %#x.\n", hr); 805 ok(newpos.u.HighPart == 0xdeadbeef && newpos.u.LowPart == 0xdeadbeef, "Unexpected position %s.\n", 806 wine_dbgstr_longlong(newpos.QuadPart)); 807 CHECK_CUR_POS(stream, 0); 808 CHECK_CUR_POS(substream, 0); 809 810 pos.QuadPart = sizeof(memory) + 1; 811 newpos.u.HighPart = 0xdeadbeef; 812 newpos.u.LowPart = 0xdeadbeef; 813 hr = IWICStream_Seek(substream, pos, STREAM_SEEK_SET, &newpos); 814 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 815 ok(newpos.u.HighPart == 0xdeadbeef && newpos.u.LowPart == 0xdeadbeef, "Unexpected position %s.\n", 816 wine_dbgstr_longlong(newpos.QuadPart)); 817 CHECK_CUR_POS(stream, 0); 818 CHECK_CUR_POS(substream, 0); 819 820 pos.QuadPart = 1; 821 newpos.u.HighPart = 0xdeadbeef; 822 newpos.u.LowPart = 0xdeadbeef; 823 hr = IWICStream_Seek(substream, pos, STREAM_SEEK_END, &newpos); 824 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 825 ok(newpos.u.HighPart == 0xdeadbeef && newpos.u.LowPart == 0xdeadbeef, "Unexpected position %s.\n", 826 wine_dbgstr_longlong(newpos.QuadPart)); 827 CHECK_CUR_POS(stream, 0); 828 CHECK_CUR_POS(substream, 0); 829 830 pos.QuadPart = -1; 831 hr = IWICStream_Seek(substream, pos, STREAM_SEEK_END, &newpos); 832 ok(hr == S_OK, "Failed to seek a stream, hr %#x.\n", hr); 833 ok(newpos.QuadPart == sizeof(memory) - 1, "Unexpected position %s.\n", wine_dbgstr_longlong(newpos.QuadPart)); 834 CHECK_CUR_POS(stream, sizeof(memory) - 1); 835 CHECK_CUR_POS(substream, sizeof(memory) - 1); 836 837 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 838 839 /* Read */ 840 hr = IWICStream_Read(substream, buff, 12, &read_len); 841 ok(hr == S_OK, "Failed to read from stream, hr %#x.\n", hr); 842 ok(read_len == 12, "Unexpected read length %u.\n", read_len); 843 ok(!memcmp(buff, data, 12), "Unexpected data.\n"); 844 CHECK_CUR_POS(substream, read_len); 845 CHECK_CUR_POS(stream, read_len); 846 847 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 848 CHECK_CUR_POS(stream, 0); 849 850 hr = IWICStream_Read(substream, memory, 10, &read_len); /* source = dest */ 851 ok(hr == S_OK, "Failed to read from stream, hr %#x.\n", hr); 852 ok(read_len == 10, "Unexpected read length %u.\n", read_len); 853 ok(!memcmp(memory, data, read_len), "Unexpected data.\n"); 854 CHECK_CUR_POS(stream, 10); 855 856 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 857 hr = IWICStream_Read(substream, memory, 2 * sizeof(data), &read_len); /* request too many bytes */ 858 ok(hr == S_OK, "Failed to read from stream, hr %#x.\n", hr); 859 ok(read_len == 64, "Unexpected read length %u.\n", read_len); 860 ok(!memcmp(memory, data, read_len), "Unexpected data.\n"); 861 CHECK_CUR_POS(stream, sizeof(data)); 862 863 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 864 read_len = 0xdeadbeef; 865 hr = IWICStream_Read(substream, NULL, 1, &read_len); /* destination buffer = NULL */ 866 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 867 ok(read_len == 0xdeadbeef, "Unexpected read length %u.\n", read_len); 868 869 read_len = 1; 870 hr = IWICStream_Read(substream, buff, 0, &read_len); /* read 0 bytes */ 871 ok(hr == S_OK, "Failed to read from stream, hr %#x.\n", hr); 872 ok(read_len == 0, "Unexpected read length %u.\n", read_len); 873 874 read_len = 0xdeadbeef; 875 hr = IWICStream_Read(substream, NULL, 0, &read_len); 876 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 877 ok(read_len == 0xdeadbeef, "Unexpected read length %u.\n", read_len); 878 879 hr = IWICStream_Read(substream, NULL, 0, NULL); 880 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 881 882 hr = IWICStream_Read(substream, buff, 1, NULL); 883 ok(hr == S_OK, "Failed to read from stream, hr %#x.\n", hr); 884 CHECK_CUR_POS(substream, 1); 885 CHECK_CUR_POS(stream, 1); 886 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 887 888 /* Write */ 889 for (i = 0; i < 3; ++i) 890 buff[i] = data[i] + 1; 891 892 hr = IWICStream_Write(substream, buff, 3, &written); 893 ok(hr == S_OK, "Failed to write to stream, hr %#x.\n", hr); 894 ok(written == 3, "Unexpected written length %u.\n", written); 895 ok(!memcmp(buff, memory, 3), "Unexpected stream data.\n"); 896 CHECK_CUR_POS(substream, written); 897 CHECK_CUR_POS(stream, written); 898 IWICStream_Seek(substream, zero_pos, STREAM_SEEK_SET, NULL); 899 900 hr = IWICStream_Write(substream, buff, 0, &written); 901 ok(hr == S_OK, "Failed to write to stream, hr %#x.\n", hr); 902 903 written = 0xdeadbeef; 904 hr = IWICStream_Write(substream, NULL, 3, &written); 905 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 906 ok(written == 0xdeadbeef, "Unexpected written length %u.\n", written); 907 CHECK_CUR_POS(substream, 0); 908 CHECK_CUR_POS(stream, 0); 909 910 written = 0xdeadbeef; 911 hr = IWICStream_Write(substream, NULL, 0, &written); 912 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 913 ok(written == 0xdeadbeef, "Unexpected written length %u.\n", written); 914 CHECK_CUR_POS(substream, 0); 915 CHECK_CUR_POS(stream, 0); 916 917 /* SetSize */ 918 newpos.u.HighPart = 0; 919 newpos.u.LowPart = sizeof(memory) + 10; 920 hr = IWICStream_SetSize(substream, newpos); 921 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 922 923 newpos.u.HighPart = 0; 924 newpos.u.LowPart = sizeof(memory); 925 hr = IWICStream_SetSize(substream, newpos); 926 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 927 928 newpos.u.HighPart = 0; 929 newpos.u.LowPart = sizeof(memory) - 10; 930 hr = IWICStream_SetSize(substream, newpos); 931 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 932 933 newpos.QuadPart = 0; 934 hr = IWICStream_SetSize(substream, newpos); 935 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 936 937 newpos.QuadPart = -10; 938 hr = IWICStream_SetSize(substream, newpos); 939 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 940 941 /* CopyTo */ 942 newpos.u.HighPart = 0; 943 newpos.u.LowPart = 30; 944 hr = IWICStream_CopyTo(substream, NULL, newpos, NULL, NULL); 945 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 946 947 hr = CreateStreamOnHGlobal(NULL, TRUE, ©_stream); 948 ok(hr == S_OK, "Failed to create a stream, hr %#x.\n", hr); 949 950 hr = IWICStream_CopyTo(substream, copy_stream, newpos, NULL, NULL); 951 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 952 IStream_Release(copy_stream); 953 954 /* Commit */ 955 hr = IWICStream_Commit(substream, STGC_DEFAULT); 956 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 957 958 hr = IWICStream_Commit(substream, STGC_OVERWRITE); 959 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 960 961 hr = IWICStream_Commit(substream, STGC_ONLYIFCURRENT); 962 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 963 964 hr = IWICStream_Commit(substream, STGC_DANGEROUSLYCOMMITMERELYTODISKCACHE); 965 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 966 967 hr = IWICStream_Commit(substream, STGC_CONSOLIDATE); 968 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 969 970 /* Revert */ 971 IWICStream_Write(substream, buff + 5, 6, NULL); 972 hr = IWICStream_Revert(substream); 973 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 974 memcpy(memory, data, sizeof(memory)); 975 976 /* LockRegion/UnlockRegion */ 977 hr = IWICStream_LockRegion(substream, uzero, uzero, 0); 978 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 979 980 hr = IWICStream_UnlockRegion(substream, uzero, uzero, 0); 981 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 982 983 /* Stat */ 984 hr = IWICStream_Stat(substream, NULL, 0); 985 ok(hr == E_INVALIDARG, "Unexpected hr %#x.\n", hr); 986 987 hr = IWICStream_Stat(substream, &stats, 0); 988 ok(hr == S_OK, "Failed to get stream stats, hr %#x.\n", hr); 989 ok(stats.pwcsName == NULL, "Unexpected name %p.\n", stats.pwcsName); 990 ok(stats.type == STGTY_STREAM, "Unexpected type %d.\n", stats.type); 991 ok(stats.cbSize.QuadPart == sizeof(data), "Unexpected size %s.\n", wine_dbgstr_longlong(stats.cbSize.QuadPart)); 992 ok(stats.mtime.dwHighDateTime == 0 && stats.mtime.dwLowDateTime == 0, "Unexpected mtime (%u;%u).\n", 993 stats.mtime.dwHighDateTime, stats.mtime.dwLowDateTime); 994 ok(stats.ctime.dwHighDateTime == 0 && stats.ctime.dwLowDateTime == 0, "Unexpected ctime (%u;%u).\n", 995 stats.ctime.dwHighDateTime, stats.ctime.dwLowDateTime); 996 ok(stats.atime.dwHighDateTime == 0 && stats.atime.dwLowDateTime == 0, "Unexpected atime (%u;%u).\n", 997 stats.atime.dwHighDateTime, stats.atime.dwLowDateTime); 998 ok(stats.grfMode == 0, "Unexpected mode %d.\n", stats.grfMode); 999 ok(stats.grfLocksSupported == 0, "Unexpected locks support %#x.\n", stats.grfLocksSupported); 1000 ok(stats.grfStateBits == 0, "Unexpected state bits %#x.\n", stats.grfStateBits); 1001 1002 /* Clone */ 1003 hr = IWICStream_Clone(substream, ©_stream); 1004 ok(hr == E_NOTIMPL, "Unexpected hr %#x.\n", hr); 1005 1006 IWICStream_Release(substream); 1007 IWICStream_Release(stream); 1008 IWICImagingFactory_Release(factory); 1009 } 1010 1011 START_TEST(stream) 1012 { 1013 CoInitialize(NULL); 1014 1015 test_StreamOnMemory(); 1016 test_StreamOnStreamRange(); 1017 test_StreamOnIStream(); 1018 1019 CoUninitialize(); 1020 } 1021