1 /* 2 * Unit test suite for Background Copy Job Interface 3 * 4 * Copyright 2007 Google (Roy Shea) 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2.1 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, write to the Free Software 18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 19 */ 20 21 #include <stdio.h> 22 23 #define COBJMACROS 24 25 #include "wine/test.h" 26 #include "bits.h" 27 #include "initguid.h" 28 #include "bits2_0.h" 29 #include "bits2_5.h" 30 31 /* Globals used by many tests */ 32 static const WCHAR test_displayName[] = {'T', 'e', 's', 't', 0}; 33 static WCHAR test_remotePathA[MAX_PATH]; 34 static WCHAR test_remotePathB[MAX_PATH]; 35 static WCHAR test_localPathA[MAX_PATH]; 36 static WCHAR test_localPathB[MAX_PATH]; 37 static IBackgroundCopyManager *test_manager; 38 static IBackgroundCopyJob *test_job; 39 static GUID test_jobId; 40 static BG_JOB_TYPE test_type; 41 42 static HRESULT test_create_manager(void) 43 { 44 HRESULT hres; 45 IBackgroundCopyManager *manager = NULL; 46 47 /* Creating BITS instance */ 48 hres = CoCreateInstance(&CLSID_BackgroundCopyManager, NULL, CLSCTX_LOCAL_SERVER, 49 &IID_IBackgroundCopyManager, (void **) &manager); 50 51 if(hres == HRESULT_FROM_WIN32(ERROR_SERVICE_DISABLED)) { 52 win_skip("Needed Service is disabled\n"); 53 return hres; 54 } 55 56 if (hres == S_OK) 57 IBackgroundCopyManager_Release(manager); 58 59 return hres; 60 } 61 62 static void init_paths(void) 63 { 64 WCHAR tmpDir[MAX_PATH]; 65 WCHAR prefix[] = {'q', 'm', 'g', 'r', 0}; 66 67 GetTempPathW(MAX_PATH, tmpDir); 68 69 GetTempFileNameW(tmpDir, prefix, 0, test_localPathA); 70 GetTempFileNameW(tmpDir, prefix, 0, test_localPathB); 71 GetTempFileNameW(tmpDir, prefix, 0, test_remotePathA); 72 GetTempFileNameW(tmpDir, prefix, 0, test_remotePathB); 73 } 74 75 /* Generic test setup */ 76 static BOOL setup(void) 77 { 78 HRESULT hres; 79 80 test_manager = NULL; 81 test_job = NULL; 82 memset(&test_jobId, 0, sizeof test_jobId); 83 test_type = BG_JOB_TYPE_DOWNLOAD; 84 85 hres = CoCreateInstance(&CLSID_BackgroundCopyManager, NULL, 86 CLSCTX_LOCAL_SERVER, 87 &IID_IBackgroundCopyManager, 88 (void **) &test_manager); 89 if(hres != S_OK) 90 return FALSE; 91 92 hres = IBackgroundCopyManager_CreateJob(test_manager, test_displayName, 93 test_type, &test_jobId, &test_job); 94 if(hres != S_OK) 95 { 96 IBackgroundCopyManager_Release(test_manager); 97 return FALSE; 98 } 99 100 return TRUE; 101 } 102 103 /* Generic test cleanup */ 104 static void teardown(void) 105 { 106 IBackgroundCopyJob_Cancel(test_job); 107 IBackgroundCopyJob_Release(test_job); 108 IBackgroundCopyManager_Release(test_manager); 109 } 110 111 static BOOL check_bits20(void) 112 { 113 HRESULT hres; 114 IBackgroundCopyManager *manager; 115 IBackgroundCopyJob *job, *job3; 116 117 hres = CoCreateInstance(&CLSID_BackgroundCopyManager, NULL, 118 CLSCTX_LOCAL_SERVER, &IID_IBackgroundCopyManager, 119 (void **)&manager); 120 if (hres != S_OK) return FALSE; 121 122 hres = IBackgroundCopyManager_CreateJob(manager, test_displayName, test_type, &test_jobId, &job); 123 if (hres != S_OK) 124 { 125 IBackgroundCopyManager_Release(manager); 126 return FALSE; 127 } 128 129 hres = IBackgroundCopyJob_QueryInterface(job, &IID_IBackgroundCopyJob3, (void **)&job3); 130 IBackgroundCopyJob_Cancel(job); 131 IBackgroundCopyJob_Release(job); 132 if (hres != S_OK) 133 { 134 IBackgroundCopyManager_Release(manager); 135 return FALSE; 136 } 137 138 IBackgroundCopyJob_Release(job3); 139 IBackgroundCopyManager_Release(manager); 140 return TRUE; 141 } 142 143 static BOOL check_bits25(void) 144 { 145 HRESULT hres; 146 IBackgroundCopyManager *manager; 147 IBackgroundCopyJob *job; 148 IBackgroundCopyJobHttpOptions *options; 149 150 hres = CoCreateInstance(&CLSID_BackgroundCopyManager, NULL, 151 CLSCTX_LOCAL_SERVER, &IID_IBackgroundCopyManager, 152 (void **)&manager); 153 if (hres != S_OK) return FALSE; 154 155 hres = IBackgroundCopyManager_CreateJob(manager, test_displayName, test_type, &test_jobId, &job); 156 if (hres != S_OK) 157 { 158 IBackgroundCopyManager_Release(manager); 159 return FALSE; 160 } 161 162 hres = IBackgroundCopyJob_QueryInterface(job, &IID_IBackgroundCopyJobHttpOptions, (void **)&options); 163 IBackgroundCopyJob_Cancel(job); 164 IBackgroundCopyJob_Release(job); 165 if (hres != S_OK) 166 { 167 IBackgroundCopyManager_Release(manager); 168 return FALSE; 169 } 170 171 IBackgroundCopyJobHttpOptions_Release(options); 172 IBackgroundCopyManager_Release(manager); 173 return TRUE; 174 } 175 176 /* Test that the jobId is properly set */ 177 static void test_GetId(void) 178 { 179 HRESULT hres; 180 GUID tmpId; 181 182 hres = IBackgroundCopyJob_GetId(test_job, &tmpId); 183 ok(hres == S_OK, "GetId failed: %08x\n", hres); 184 ok(memcmp(&tmpId, &test_jobId, sizeof tmpId) == 0, "Got incorrect GUID\n"); 185 } 186 187 /* Test that the type is properly set */ 188 static void test_GetType(void) 189 { 190 HRESULT hres; 191 BG_JOB_TYPE type; 192 193 hres = IBackgroundCopyJob_GetType(test_job, &type); 194 ok(hres == S_OK, "GetType failed: %08x\n", hres); 195 ok(type == test_type, "Got incorrect type\n"); 196 } 197 198 /* Test that the display name is properly set */ 199 static void test_GetName(void) 200 { 201 HRESULT hres; 202 LPWSTR displayName; 203 204 hres = IBackgroundCopyJob_GetDisplayName(test_job, &displayName); 205 ok(hres == S_OK, "GetName failed: %08x\n", hres); 206 ok(lstrcmpW(displayName, test_displayName) == 0, "Got incorrect type\n"); 207 CoTaskMemFree(displayName); 208 } 209 210 /* Test adding a file */ 211 static void test_AddFile(void) 212 { 213 HRESULT hres; 214 215 hres = IBackgroundCopyJob_AddFile(test_job, test_remotePathA, 216 test_localPathA); 217 ok(hres == S_OK, "First call to AddFile failed: 0x%08x\n", hres); 218 219 hres = IBackgroundCopyJob_AddFile(test_job, test_remotePathB, 220 test_localPathB); 221 ok(hres == S_OK, "Second call to AddFile failed: 0x%08x\n", hres); 222 } 223 224 /* Test adding a set of files */ 225 static void test_AddFileSet(void) 226 { 227 HRESULT hres; 228 BG_FILE_INFO files[2] = 229 { 230 {test_remotePathA, test_localPathA}, 231 {test_remotePathB, test_localPathB} 232 }; 233 hres = IBackgroundCopyJob_AddFileSet(test_job, 2, files); 234 ok(hres == S_OK, "AddFileSet failed: 0x%08x\n", hres); 235 } 236 237 /* Test creation of a job enumerator */ 238 static void test_EnumFiles(void) 239 { 240 HRESULT hres; 241 IEnumBackgroundCopyFiles *enumFiles; 242 ULONG res; 243 244 hres = IBackgroundCopyJob_AddFile(test_job, test_remotePathA, 245 test_localPathA); 246 ok(hres == S_OK, "got 0x%08x\n", hres); 247 248 hres = IBackgroundCopyJob_EnumFiles(test_job, &enumFiles); 249 ok(hres == S_OK, "EnumFiles failed: 0x%08x\n", hres); 250 251 res = IEnumBackgroundCopyFiles_Release(enumFiles); 252 ok(res == 0, "Bad ref count on release: %u\n", res); 253 } 254 255 /* Test getting job progress */ 256 static void test_GetProgress_preTransfer(void) 257 { 258 HRESULT hres; 259 BG_JOB_PROGRESS progress; 260 261 hres = IBackgroundCopyJob_GetProgress(test_job, &progress); 262 ok(hres == S_OK, "GetProgress failed: 0x%08x\n", hres); 263 264 ok(progress.BytesTotal == 0, "Incorrect BytesTotal: %s\n", 265 wine_dbgstr_longlong(progress.BytesTotal)); 266 ok(progress.BytesTransferred == 0, "Incorrect BytesTransferred: %s\n", 267 wine_dbgstr_longlong(progress.BytesTransferred)); 268 ok(progress.FilesTotal == 0, "Incorrect FilesTotal: %u\n", progress.FilesTotal); 269 ok(progress.FilesTransferred == 0, "Incorrect FilesTransferred %u\n", progress.FilesTransferred); 270 } 271 272 /* Test getting job state */ 273 static void test_GetState(void) 274 { 275 HRESULT hres; 276 BG_JOB_STATE state; 277 278 state = BG_JOB_STATE_ERROR; 279 hres = IBackgroundCopyJob_GetState(test_job, &state); 280 ok(hres == S_OK, "GetState failed: 0x%08x\n", hres); 281 ok(state == BG_JOB_STATE_SUSPENDED, "Incorrect job state: %d\n", state); 282 } 283 284 /* Test resuming a job */ 285 static void test_ResumeEmpty(void) 286 { 287 HRESULT hres; 288 BG_JOB_STATE state; 289 290 hres = IBackgroundCopyJob_Resume(test_job); 291 ok(hres == BG_E_EMPTY, "Resume failed to return BG_E_EMPTY error: 0x%08x\n", hres); 292 293 state = BG_JOB_STATE_ERROR; 294 hres = IBackgroundCopyJob_GetState(test_job, &state); 295 ok(hres == S_OK, "got 0x%08x\n", hres); 296 ok(state == BG_JOB_STATE_SUSPENDED, "Incorrect job state: %d\n", state); 297 } 298 299 static void makeFile(WCHAR *name, const char *contents) 300 { 301 HANDLE file; 302 DWORD w, len = strlen(contents); 303 304 DeleteFileW(name); 305 file = CreateFileW(name, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 306 FILE_ATTRIBUTE_NORMAL, NULL); 307 ok(file != INVALID_HANDLE_VALUE, "CreateFile\n"); 308 ok(WriteFile(file, contents, len, &w, NULL), "WriteFile\n"); 309 CloseHandle(file); 310 } 311 312 static void compareFiles(WCHAR *n1, WCHAR *n2) 313 { 314 char b1[256]; 315 char b2[256]; 316 DWORD s1, s2; 317 HANDLE f1, f2; 318 319 f1 = CreateFileW(n1, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 320 FILE_ATTRIBUTE_NORMAL, NULL); 321 ok(f1 != INVALID_HANDLE_VALUE, "CreateFile\n"); 322 323 f2 = CreateFileW(n2, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 324 FILE_ATTRIBUTE_NORMAL, NULL); 325 ok(f2 != INVALID_HANDLE_VALUE, "CreateFile\n"); 326 327 /* Neither of these files is very big */ 328 ok(ReadFile(f1, b1, sizeof b1, &s1, NULL), "ReadFile\n"); 329 ok(ReadFile(f2, b2, sizeof b2, &s2, NULL), "ReadFile\n"); 330 331 CloseHandle(f1); 332 CloseHandle(f2); 333 334 ok(s1 == s2, "Files differ in length\n"); 335 ok(memcmp(b1, b2, s1) == 0, "Files differ in contents\n"); 336 } 337 338 /* Test a complete transfer for local files */ 339 static void test_CompleteLocal(void) 340 { 341 static const int timeout_sec = 30; 342 HRESULT hres; 343 BG_JOB_STATE state; 344 int i; 345 346 DeleteFileW(test_localPathA); 347 DeleteFileW(test_localPathB); 348 makeFile(test_remotePathA, "This is a WINE test file for BITS\n"); 349 makeFile(test_remotePathB, "This is another WINE test file for BITS\n"); 350 351 hres = IBackgroundCopyJob_AddFile(test_job, test_remotePathA, 352 test_localPathA); 353 ok(hres == S_OK, "got 0x%08x\n", hres); 354 355 hres = IBackgroundCopyJob_AddFile(test_job, test_remotePathB, 356 test_localPathB); 357 ok(hres == S_OK, "got 0x%08x\n", hres); 358 359 hres = IBackgroundCopyJob_Resume(test_job); 360 ok(hres == S_OK, "IBackgroundCopyJob_Resume\n"); 361 362 for (i = 0; i < timeout_sec; ++i) 363 { 364 hres = IBackgroundCopyJob_GetState(test_job, &state); 365 ok(hres == S_OK, "IBackgroundCopyJob_GetState\n"); 366 ok(state == BG_JOB_STATE_QUEUED || state == BG_JOB_STATE_CONNECTING 367 || state == BG_JOB_STATE_TRANSFERRING || state == BG_JOB_STATE_TRANSFERRED, 368 "Bad state: %d\n", state); 369 if (state == BG_JOB_STATE_TRANSFERRED) 370 break; 371 Sleep(1000); 372 } 373 374 ok(i < timeout_sec, "BITS jobs timed out\n"); 375 hres = IBackgroundCopyJob_Complete(test_job); 376 ok(hres == S_OK, "IBackgroundCopyJob_Complete\n"); 377 hres = IBackgroundCopyJob_GetState(test_job, &state); 378 ok(hres == S_OK, "IBackgroundCopyJob_GetState\n"); 379 ok(state == BG_JOB_STATE_ACKNOWLEDGED, "Bad state: %d\n", state); 380 381 compareFiles(test_remotePathA, test_localPathA); 382 compareFiles(test_remotePathB, test_localPathB); 383 384 ok(DeleteFileW(test_remotePathA), "DeleteFile\n"); 385 ok(DeleteFileW(test_remotePathB), "DeleteFile\n"); 386 DeleteFileW(test_localPathA); 387 DeleteFileW(test_localPathB); 388 } 389 390 /* Test a complete transfer for local files */ 391 static void test_CompleteLocalURL(void) 392 { 393 static const WCHAR prot[] = {'f','i','l','e',':','/','/', 0}; 394 static const int timeout_sec = 30; 395 WCHAR *urlA, *urlB; 396 HRESULT hres; 397 BG_JOB_STATE state; 398 int i; 399 400 DeleteFileW(test_localPathA); 401 DeleteFileW(test_localPathB); 402 makeFile(test_remotePathA, "This is a WINE test file for BITS\n"); 403 makeFile(test_remotePathB, "This is another WINE test file for BITS\n"); 404 405 urlA = HeapAlloc(GetProcessHeap(), 0, 406 (7 + lstrlenW(test_remotePathA) + 1) * sizeof urlA[0]); 407 urlB = HeapAlloc(GetProcessHeap(), 0, 408 (7 + lstrlenW(test_remotePathB) + 1) * sizeof urlB[0]); 409 if (!urlA || !urlB) 410 { 411 skip("Unable to allocate memory for URLs\n"); 412 HeapFree(GetProcessHeap(), 0, urlA); 413 HeapFree(GetProcessHeap(), 0, urlB); 414 return; 415 } 416 417 lstrcpyW(urlA, prot); 418 lstrcatW(urlA, test_remotePathA); 419 lstrcpyW(urlB, prot); 420 lstrcatW(urlB, test_remotePathB); 421 422 hres = IBackgroundCopyJob_AddFile(test_job, urlA, test_localPathA); 423 ok(hres == S_OK, "got 0x%08x\n", hres); 424 425 hres = IBackgroundCopyJob_AddFile(test_job, urlB, test_localPathB); 426 ok(hres == S_OK, "got 0x%08x\n", hres); 427 428 hres = IBackgroundCopyJob_Resume(test_job); 429 ok(hres == S_OK, "IBackgroundCopyJob_Resume\n"); 430 431 for (i = 0; i < timeout_sec; ++i) 432 { 433 hres = IBackgroundCopyJob_GetState(test_job, &state); 434 ok(hres == S_OK, "IBackgroundCopyJob_GetState\n"); 435 ok(state == BG_JOB_STATE_QUEUED || state == BG_JOB_STATE_CONNECTING 436 || state == BG_JOB_STATE_TRANSFERRING || state == BG_JOB_STATE_TRANSFERRED, 437 "Bad state: %d\n", state); 438 if (state == BG_JOB_STATE_TRANSFERRED) 439 break; 440 Sleep(1000); 441 } 442 443 ok(i < timeout_sec, "BITS jobs timed out\n"); 444 hres = IBackgroundCopyJob_Complete(test_job); 445 ok(hres == S_OK, "IBackgroundCopyJob_Complete\n"); 446 hres = IBackgroundCopyJob_GetState(test_job, &state); 447 ok(hres == S_OK, "IBackgroundCopyJob_GetState\n"); 448 ok(state == BG_JOB_STATE_ACKNOWLEDGED, "Bad state: %d\n", state); 449 450 compareFiles(test_remotePathA, test_localPathA); 451 compareFiles(test_remotePathB, test_localPathB); 452 453 ok(DeleteFileW(test_remotePathA), "DeleteFile\n"); 454 ok(DeleteFileW(test_remotePathB), "DeleteFile\n"); 455 DeleteFileW(test_localPathA); 456 DeleteFileW(test_localPathB); 457 458 HeapFree(GetProcessHeap(), 0, urlA); 459 HeapFree(GetProcessHeap(), 0, urlB); 460 } 461 462 static void test_NotifyFlags(void) 463 { 464 ULONG flags; 465 HRESULT hr; 466 467 /* check default flags */ 468 flags = 0; 469 hr = IBackgroundCopyJob_GetNotifyFlags(test_job, &flags); 470 ok(hr == S_OK, "got 0x%08x\n", hr); 471 ok(flags == (BG_NOTIFY_JOB_ERROR | BG_NOTIFY_JOB_TRANSFERRED), "flags 0x%08x\n", flags); 472 } 473 474 static void test_NotifyInterface(void) 475 { 476 HRESULT hr; 477 IUnknown *unk; 478 479 unk = (IUnknown*)0xdeadbeef; 480 hr = IBackgroundCopyJob_GetNotifyInterface(test_job, &unk); 481 ok(hr == S_OK, "got 0x%08x\n", hr); 482 ok(unk == NULL, "got %p\n", unk); 483 } 484 485 static void test_Cancel(void) 486 { 487 HRESULT hr; 488 BG_JOB_STATE state; 489 490 state = BG_JOB_STATE_ERROR; 491 hr = IBackgroundCopyJob_GetState(test_job, &state); 492 ok(hr == S_OK, "got 0x%08x\n", hr); 493 ok(state != BG_JOB_STATE_CANCELLED, "got %u\n", state); 494 495 hr = IBackgroundCopyJob_Cancel(test_job); 496 ok(hr == S_OK, "got 0x%08x\n", hr); 497 498 state = BG_JOB_STATE_ERROR; 499 hr = IBackgroundCopyJob_GetState(test_job, &state); 500 ok(hr == S_OK, "got 0x%08x\n", hr); 501 ok(state == BG_JOB_STATE_CANCELLED, "got %u\n", state); 502 503 hr = IBackgroundCopyJob_Cancel(test_job); 504 ok(hr == BG_E_INVALID_STATE, "got 0x%08x\n", hr); 505 } 506 507 static void test_HttpOptions(void) 508 { 509 static const WCHAR urlW[] = 510 {'h','t','t','p','s',':','/','/','t','e','s','t','.','w','i','n','e','h','q','.','o','r','g','/',0}; 511 static const WCHAR winetestW[] = 512 {'W','i','n','e',':',' ','t','e','s','t','\r','\n',0}; 513 static const unsigned int timeout = 30; 514 HRESULT hr; 515 IBackgroundCopyJobHttpOptions *options; 516 IBackgroundCopyError *error; 517 BG_JOB_STATE state; 518 unsigned int i; 519 WCHAR *headers; 520 ULONG flags, orig_flags; 521 522 DeleteFileW(test_localPathA); 523 hr = IBackgroundCopyJob_AddFile(test_job, urlW, test_localPathA); 524 ok(hr == S_OK, "got 0x%08x\n", hr); 525 526 hr = IBackgroundCopyJob_QueryInterface(test_job, &IID_IBackgroundCopyJobHttpOptions, (void **)&options); 527 ok(hr == S_OK, "got 0x%08x\n", hr); 528 529 if (options) 530 { 531 headers = (WCHAR *)0xdeadbeef; 532 hr = IBackgroundCopyJobHttpOptions_GetCustomHeaders(options, &headers); 533 ok(hr == S_FALSE, "got 0x%08x\n", hr); 534 ok(headers == NULL, "got %p\n", headers); 535 536 hr = IBackgroundCopyJobHttpOptions_SetCustomHeaders(options, winetestW); 537 ok(hr == S_OK, "got 0x%08x\n", hr); 538 539 headers = (WCHAR *)0xdeadbeef; 540 hr = IBackgroundCopyJobHttpOptions_GetCustomHeaders(options, &headers); 541 ok(hr == S_OK, "got 0x%08x\n", hr); 542 if (hr == S_OK) 543 { 544 ok(!lstrcmpW(headers, winetestW), "got %s\n", wine_dbgstr_w(headers)); 545 CoTaskMemFree(headers); 546 } 547 548 hr = IBackgroundCopyJobHttpOptions_SetCustomHeaders(options, NULL); 549 ok(hr == S_OK, "got 0x%08x\n", hr); 550 551 headers = (WCHAR *)0xdeadbeef; 552 hr = IBackgroundCopyJobHttpOptions_GetCustomHeaders(options, &headers); 553 ok(hr == S_FALSE, "got 0x%08x\n", hr); 554 ok(headers == NULL, "got %p\n", headers); 555 556 orig_flags = 0xdeadbeef; 557 hr = IBackgroundCopyJobHttpOptions_GetSecurityFlags(options, &orig_flags); 558 ok(hr == S_OK, "got 0x%08x\n", hr); 559 ok(!orig_flags, "got 0x%08x\n", orig_flags); 560 561 hr = IBackgroundCopyJobHttpOptions_SetSecurityFlags(options, 0); 562 ok(hr == S_OK, "got 0x%08x\n", hr); 563 564 flags = 0xdeadbeef; 565 hr = IBackgroundCopyJobHttpOptions_GetSecurityFlags(options, &flags); 566 ok(hr == S_OK, "got 0x%08x\n", hr); 567 ok(!flags, "got 0x%08x\n", flags); 568 } 569 570 hr = IBackgroundCopyJob_Resume(test_job); 571 ok(hr == S_OK, "got 0x%08x\n", hr); 572 573 for (i = 0; i < timeout; i++) 574 { 575 hr = IBackgroundCopyJob_GetState(test_job, &state); 576 ok(hr == S_OK, "got 0x%08x\n", hr); 577 578 ok(state == BG_JOB_STATE_QUEUED || 579 state == BG_JOB_STATE_CONNECTING || 580 state == BG_JOB_STATE_TRANSFERRING || 581 state == BG_JOB_STATE_TRANSFERRED, "unexpected state: %u\n", state); 582 583 if (state == BG_JOB_STATE_TRANSFERRED) break; 584 Sleep(1000); 585 } 586 ok(i < timeout, "BITS job timed out\n"); 587 if (i < timeout) 588 { 589 hr = IBackgroundCopyJob_GetError(test_job, &error); 590 ok(hr == BG_E_ERROR_INFORMATION_UNAVAILABLE, "got 0x%08x\n", hr); 591 } 592 593 if (options) 594 { 595 headers = (WCHAR *)0xdeadbeef; 596 hr = IBackgroundCopyJobHttpOptions_GetCustomHeaders(options, &headers); 597 ok(hr == S_FALSE, "got 0x%08x\n", hr); 598 ok(headers == NULL, "got %p\n", headers); 599 600 hr = IBackgroundCopyJobHttpOptions_SetCustomHeaders(options, NULL); 601 ok(hr == S_OK, "got 0x%08x\n", hr); 602 603 hr = IBackgroundCopyJobHttpOptions_GetCustomHeaders(options, &headers); 604 ok(hr == S_FALSE, "got 0x%08x\n", hr); 605 606 flags = 0xdeadbeef; 607 hr = IBackgroundCopyJobHttpOptions_GetSecurityFlags(options, &flags); 608 ok(hr == S_OK, "got 0x%08x\n", hr); 609 ok(!flags, "got 0x%08x\n", flags); 610 611 hr = IBackgroundCopyJobHttpOptions_SetSecurityFlags(options, orig_flags); 612 ok(hr == S_OK, "got 0x%08x\n", hr); 613 614 IBackgroundCopyJobHttpOptions_Release(options); 615 } 616 617 hr = IBackgroundCopyJob_Complete(test_job); 618 ok(hr == S_OK, "got 0x%08x\n", hr); 619 620 hr = IBackgroundCopyJob_GetState(test_job, &state); 621 ok(hr == S_OK, "got 0x%08x\n", hr); 622 ok(state == BG_JOB_STATE_ACKNOWLEDGED, "unexpected state: %u\n", state); 623 624 hr = IBackgroundCopyJob_Complete(test_job); 625 ok(hr == BG_E_INVALID_STATE, "got 0x%08x\n", hr); 626 627 DeleteFileW(test_localPathA); 628 } 629 630 typedef void (*test_t)(void); 631 632 START_TEST(job) 633 { 634 static const test_t tests[] = { 635 test_GetId, 636 test_GetType, 637 test_GetName, 638 test_GetProgress_preTransfer, 639 test_GetState, 640 test_ResumeEmpty, 641 test_NotifyFlags, 642 test_NotifyInterface, 643 0 644 }; 645 static const test_t tests_bits20[] = { 646 test_AddFile, 647 test_AddFileSet, 648 test_EnumFiles, 649 test_CompleteLocal, 650 test_CompleteLocalURL, 651 test_Cancel, /* must be last */ 652 0 653 }; 654 static const test_t tests_bits25[] = { 655 test_HttpOptions, 656 0 657 }; 658 const test_t *test; 659 int i; 660 661 init_paths(); 662 663 CoInitialize(NULL); 664 665 if (FAILED(test_create_manager())) 666 { 667 CoUninitialize(); 668 win_skip("Failed to create Manager instance, skipping tests\n"); 669 return; 670 } 671 672 for (test = tests, i = 0; *test; ++test, ++i) 673 { 674 /* Keep state separate between tests. */ 675 if (!setup()) 676 { 677 ok(0, "tests:%d: Unable to setup test\n", i); 678 break; 679 } 680 (*test)(); 681 teardown(); 682 } 683 684 if (check_bits20()) 685 { 686 for (test = tests_bits20, i = 0; *test; ++test, ++i) 687 { 688 /* Keep state separate between tests. */ 689 if (!setup()) 690 { 691 ok(0, "tests_bits20:%d: Unable to setup test\n", i); 692 break; 693 } 694 (*test)(); 695 teardown(); 696 } 697 } 698 else 699 { 700 win_skip("Tests need BITS 2.0 or higher\n"); 701 } 702 703 if (check_bits25()) 704 { 705 for (test = tests_bits25, i = 0; *test; ++test, ++i) 706 { 707 /* Keep state separate between tests. */ 708 if (!setup()) 709 { 710 ok(0, "tests_bits25:%d: Unable to setup test\n", i); 711 break; 712 } 713 (*test)(); 714 teardown(); 715 } 716 } 717 else 718 { 719 win_skip("Tests need BITS 2.5 or higher\n"); 720 } 721 722 CoUninitialize(); 723 } 724