2 * Background Copy Job Interface for BITS
4 * Copyright 2007 Google (Roy Shea)
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.
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.
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
27 #include "wine/debug.h"
29 WINE_DEFAULT_DEBUG_CHANNEL(qmgr
);
31 static void BackgroundCopyJobDestructor(BackgroundCopyJobImpl
*This
)
33 DeleteCriticalSection(&This
->cs
);
34 HeapFree(GetProcessHeap(), 0, This
->displayName
);
35 HeapFree(GetProcessHeap(), 0, This
);
38 static ULONG WINAPI
BITS_IBackgroundCopyJob_AddRef(IBackgroundCopyJob2
*iface
)
40 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
41 return InterlockedIncrement(&This
->ref
);
44 static HRESULT WINAPI
BITS_IBackgroundCopyJob_QueryInterface(
45 IBackgroundCopyJob2
*iface
, REFIID riid
, LPVOID
*ppvObject
)
47 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
48 TRACE("IID: %s\n", debugstr_guid(riid
));
50 if (IsEqualGUID(riid
, &IID_IUnknown
)
51 || IsEqualGUID(riid
, &IID_IBackgroundCopyJob
)
52 || IsEqualGUID(riid
, &IID_IBackgroundCopyJob2
))
54 *ppvObject
= &This
->lpVtbl
;
55 BITS_IBackgroundCopyJob_AddRef(iface
);
63 static ULONG WINAPI
BITS_IBackgroundCopyJob_Release(IBackgroundCopyJob2
*iface
)
65 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
66 ULONG ref
= InterlockedDecrement(&This
->ref
);
69 BackgroundCopyJobDestructor(This
);
74 /*** IBackgroundCopyJob methods ***/
76 static HRESULT WINAPI
BITS_IBackgroundCopyJob_AddFileSet(
77 IBackgroundCopyJob2
*iface
,
79 BG_FILE_INFO
*pFileSet
)
82 for (i
= 0; i
< cFileCount
; ++i
)
84 HRESULT hr
= IBackgroundCopyJob_AddFile(iface
, pFileSet
[i
].RemoteName
,
85 pFileSet
[i
].LocalName
);
92 static HRESULT WINAPI
BITS_IBackgroundCopyJob_AddFile(
93 IBackgroundCopyJob2
*iface
,
97 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
98 IBackgroundCopyFile
*pFile
;
99 BackgroundCopyFileImpl
*file
;
102 /* We should return E_INVALIDARG in these cases. */
103 FIXME("Check for valid filenames and supported protocols\n");
105 res
= BackgroundCopyFileConstructor(This
, RemoteUrl
, LocalName
, (LPVOID
*) &pFile
);
109 /* Add a reference to the file to file list */
110 IBackgroundCopyFile_AddRef(pFile
);
111 file
= (BackgroundCopyFileImpl
*) pFile
;
112 EnterCriticalSection(&This
->cs
);
113 list_add_head(&This
->files
, &file
->entryFromJob
);
114 This
->jobProgress
.BytesTotal
= BG_SIZE_UNKNOWN
;
115 ++This
->jobProgress
.FilesTotal
;
116 LeaveCriticalSection(&This
->cs
);
121 static HRESULT WINAPI
BITS_IBackgroundCopyJob_EnumFiles(
122 IBackgroundCopyJob2
*iface
,
123 IEnumBackgroundCopyFiles
**ppEnum
)
126 return EnumBackgroundCopyFilesConstructor((LPVOID
*) ppEnum
, iface
);
129 static HRESULT WINAPI
BITS_IBackgroundCopyJob_Suspend(
130 IBackgroundCopyJob2
*iface
)
132 FIXME("Not implemented\n");
136 static HRESULT WINAPI
BITS_IBackgroundCopyJob_Resume(
137 IBackgroundCopyJob2
*iface
)
139 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
142 EnterCriticalSection(&globalMgr
.cs
);
143 if (This
->state
== BG_JOB_STATE_CANCELLED
144 || This
->state
== BG_JOB_STATE_ACKNOWLEDGED
)
146 rv
= BG_E_INVALID_STATE
;
148 else if (This
->jobProgress
.FilesTransferred
== This
->jobProgress
.FilesTotal
)
152 else if (This
->state
!= BG_JOB_STATE_CONNECTING
153 && This
->state
!= BG_JOB_STATE_TRANSFERRING
)
155 This
->state
= BG_JOB_STATE_QUEUED
;
156 SetEvent(globalMgr
.jobEvent
);
158 LeaveCriticalSection(&globalMgr
.cs
);
163 static HRESULT WINAPI
BITS_IBackgroundCopyJob_Cancel(
164 IBackgroundCopyJob2
*iface
)
166 FIXME("Not implemented\n");
170 static HRESULT WINAPI
BITS_IBackgroundCopyJob_Complete(
171 IBackgroundCopyJob2
*iface
)
173 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
176 EnterCriticalSection(&This
->cs
);
178 if (This
->state
== BG_JOB_STATE_CANCELLED
179 || This
->state
== BG_JOB_STATE_ACKNOWLEDGED
)
181 rv
= BG_E_INVALID_STATE
;
185 BackgroundCopyFileImpl
*file
;
186 LIST_FOR_EACH_ENTRY(file
, &This
->files
, BackgroundCopyFileImpl
, entryFromJob
)
188 if (file
->fileProgress
.Completed
)
190 if (!MoveFileExW(file
->tempFileName
, file
->info
.LocalName
,
191 (MOVEFILE_COPY_ALLOWED
192 | MOVEFILE_REPLACE_EXISTING
193 | MOVEFILE_WRITE_THROUGH
)))
195 ERR("Couldn't rename file %s -> %s\n",
196 debugstr_w(file
->tempFileName
),
197 debugstr_w(file
->info
.LocalName
));
198 rv
= BG_S_PARTIAL_COMPLETE
;
202 rv
= BG_S_PARTIAL_COMPLETE
;
206 This
->state
= BG_JOB_STATE_ACKNOWLEDGED
;
207 LeaveCriticalSection(&This
->cs
);
212 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetId(
213 IBackgroundCopyJob2
*iface
,
216 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
221 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetType(
222 IBackgroundCopyJob2
*iface
,
225 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
234 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetProgress(
235 IBackgroundCopyJob2
*iface
,
236 BG_JOB_PROGRESS
*pVal
)
238 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
243 EnterCriticalSection(&This
->cs
);
244 pVal
->BytesTotal
= This
->jobProgress
.BytesTotal
;
245 pVal
->BytesTransferred
= This
->jobProgress
.BytesTransferred
;
246 pVal
->FilesTotal
= This
->jobProgress
.FilesTotal
;
247 pVal
->FilesTransferred
= This
->jobProgress
.FilesTransferred
;
248 LeaveCriticalSection(&This
->cs
);
253 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetTimes(
254 IBackgroundCopyJob2
*iface
,
257 FIXME("Not implemented\n");
261 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetState(
262 IBackgroundCopyJob2
*iface
,
265 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
270 /* Don't think we need a critical section for this */
275 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetError(
276 IBackgroundCopyJob2
*iface
,
277 IBackgroundCopyError
**ppError
)
279 FIXME("Not implemented\n");
283 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetOwner(
284 IBackgroundCopyJob2
*iface
,
287 FIXME("Not implemented\n");
291 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetDisplayName(
292 IBackgroundCopyJob2
*iface
,
295 FIXME("Not implemented\n");
299 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetDisplayName(
300 IBackgroundCopyJob2
*iface
,
303 BackgroundCopyJobImpl
*This
= (BackgroundCopyJobImpl
*) iface
;
309 n
= (lstrlenW(This
->displayName
) + 1) * sizeof **pVal
;
310 *pVal
= CoTaskMemAlloc(n
);
312 return E_OUTOFMEMORY
;
313 memcpy(*pVal
, This
->displayName
, n
);
317 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetDescription(
318 IBackgroundCopyJob2
*iface
,
321 FIXME("Not implemented\n");
325 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetDescription(
326 IBackgroundCopyJob2
*iface
,
329 FIXME("Not implemented\n");
333 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetPriority(
334 IBackgroundCopyJob2
*iface
,
337 FIXME("Not implemented\n");
341 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetPriority(
342 IBackgroundCopyJob2
*iface
,
343 BG_JOB_PRIORITY
*pVal
)
345 FIXME("Not implemented\n");
349 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetNotifyFlags(
350 IBackgroundCopyJob2
*iface
,
353 FIXME("Not implemented\n");
357 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetNotifyFlags(
358 IBackgroundCopyJob2
*iface
,
361 FIXME("Not implemented\n");
365 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetNotifyInterface(
366 IBackgroundCopyJob2
*iface
,
369 FIXME("Not implemented\n");
373 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetNotifyInterface(
374 IBackgroundCopyJob2
*iface
,
377 FIXME("Not implemented\n");
381 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetMinimumRetryDelay(
382 IBackgroundCopyJob2
*iface
,
385 FIXME("%u\n", Seconds
);
389 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetMinimumRetryDelay(
390 IBackgroundCopyJob2
*iface
,
393 FIXME("%p\n", Seconds
);
398 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetNoProgressTimeout(
399 IBackgroundCopyJob2
*iface
,
402 FIXME("%u\n", Seconds
);
406 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetNoProgressTimeout(
407 IBackgroundCopyJob2
*iface
,
410 FIXME("%p\n", Seconds
);
415 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetErrorCount(
416 IBackgroundCopyJob2
*iface
,
419 FIXME("Not implemented\n");
423 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetProxySettings(
424 IBackgroundCopyJob2
*iface
,
425 BG_JOB_PROXY_USAGE ProxyUsage
,
426 const WCHAR
*ProxyList
,
427 const WCHAR
*ProxyBypassList
)
429 FIXME("Not implemented\n");
433 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetProxySettings(
434 IBackgroundCopyJob2
*iface
,
435 BG_JOB_PROXY_USAGE
*pProxyUsage
,
437 LPWSTR
*pProxyBypassList
)
439 FIXME("Not implemented\n");
443 static HRESULT WINAPI
BITS_IBackgroundCopyJob_TakeOwnership(
444 IBackgroundCopyJob2
*iface
)
446 FIXME("Not implemented\n");
450 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetNotifyCmdLine(
451 IBackgroundCopyJob2
*iface
,
455 FIXME("Not implemented\n");
459 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetNotifyCmdLine(
460 IBackgroundCopyJob2
*iface
,
464 FIXME("Not implemented\n");
468 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetReplyProgress(
469 IBackgroundCopyJob2
*iface
,
470 BG_JOB_REPLY_PROGRESS
*progress
)
472 FIXME("Not implemented\n");
476 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetReplyData(
477 IBackgroundCopyJob2
*iface
,
481 FIXME("Not implemented\n");
485 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetReplyFileName(
486 IBackgroundCopyJob2
*iface
,
489 FIXME("Not implemented\n");
493 static HRESULT WINAPI
BITS_IBackgroundCopyJob_GetReplyFileName(
494 IBackgroundCopyJob2
*iface
,
497 FIXME("Not implemented\n");
501 static HRESULT WINAPI
BITS_IBackgroundCopyJob_SetCredentials(
502 IBackgroundCopyJob2
*iface
,
503 BG_AUTH_CREDENTIALS
*cred
)
505 FIXME("Not implemented\n");
509 static HRESULT WINAPI
BITS_IBackgroundCopyJob_RemoveCredentials(
510 IBackgroundCopyJob2
*iface
,
511 BG_AUTH_TARGET target
,
512 BG_AUTH_SCHEME scheme
)
514 FIXME("Not implemented\n");
518 static const IBackgroundCopyJob2Vtbl BITS_IBackgroundCopyJob_Vtbl
=
520 BITS_IBackgroundCopyJob_QueryInterface
,
521 BITS_IBackgroundCopyJob_AddRef
,
522 BITS_IBackgroundCopyJob_Release
,
523 BITS_IBackgroundCopyJob_AddFileSet
,
524 BITS_IBackgroundCopyJob_AddFile
,
525 BITS_IBackgroundCopyJob_EnumFiles
,
526 BITS_IBackgroundCopyJob_Suspend
,
527 BITS_IBackgroundCopyJob_Resume
,
528 BITS_IBackgroundCopyJob_Cancel
,
529 BITS_IBackgroundCopyJob_Complete
,
530 BITS_IBackgroundCopyJob_GetId
,
531 BITS_IBackgroundCopyJob_GetType
,
532 BITS_IBackgroundCopyJob_GetProgress
,
533 BITS_IBackgroundCopyJob_GetTimes
,
534 BITS_IBackgroundCopyJob_GetState
,
535 BITS_IBackgroundCopyJob_GetError
,
536 BITS_IBackgroundCopyJob_GetOwner
,
537 BITS_IBackgroundCopyJob_SetDisplayName
,
538 BITS_IBackgroundCopyJob_GetDisplayName
,
539 BITS_IBackgroundCopyJob_SetDescription
,
540 BITS_IBackgroundCopyJob_GetDescription
,
541 BITS_IBackgroundCopyJob_SetPriority
,
542 BITS_IBackgroundCopyJob_GetPriority
,
543 BITS_IBackgroundCopyJob_SetNotifyFlags
,
544 BITS_IBackgroundCopyJob_GetNotifyFlags
,
545 BITS_IBackgroundCopyJob_SetNotifyInterface
,
546 BITS_IBackgroundCopyJob_GetNotifyInterface
,
547 BITS_IBackgroundCopyJob_SetMinimumRetryDelay
,
548 BITS_IBackgroundCopyJob_GetMinimumRetryDelay
,
549 BITS_IBackgroundCopyJob_SetNoProgressTimeout
,
550 BITS_IBackgroundCopyJob_GetNoProgressTimeout
,
551 BITS_IBackgroundCopyJob_GetErrorCount
,
552 BITS_IBackgroundCopyJob_SetProxySettings
,
553 BITS_IBackgroundCopyJob_GetProxySettings
,
554 BITS_IBackgroundCopyJob_TakeOwnership
,
555 BITS_IBackgroundCopyJob_SetNotifyCmdLine
,
556 BITS_IBackgroundCopyJob_GetNotifyCmdLine
,
557 BITS_IBackgroundCopyJob_GetReplyProgress
,
558 BITS_IBackgroundCopyJob_GetReplyData
,
559 BITS_IBackgroundCopyJob_SetReplyFileName
,
560 BITS_IBackgroundCopyJob_GetReplyFileName
,
561 BITS_IBackgroundCopyJob_SetCredentials
,
562 BITS_IBackgroundCopyJob_RemoveCredentials
565 HRESULT
BackgroundCopyJobConstructor(LPCWSTR displayName
, BG_JOB_TYPE type
,
566 GUID
*pJobId
, LPVOID
*ppObj
)
569 BackgroundCopyJobImpl
*This
;
572 TRACE("(%s,%d,%p)\n", debugstr_w(displayName
), type
, ppObj
);
574 This
= HeapAlloc(GetProcessHeap(), 0, sizeof *This
);
576 return E_OUTOFMEMORY
;
578 This
->lpVtbl
= &BITS_IBackgroundCopyJob_Vtbl
;
579 InitializeCriticalSection(&This
->cs
);
583 n
= (lstrlenW(displayName
) + 1) * sizeof *displayName
;
584 This
->displayName
= HeapAlloc(GetProcessHeap(), 0, n
);
585 if (!This
->displayName
)
587 DeleteCriticalSection(&This
->cs
);
588 HeapFree(GetProcessHeap(), 0, This
);
589 return E_OUTOFMEMORY
;
591 memcpy(This
->displayName
, displayName
, n
);
593 hr
= CoCreateGuid(&This
->jobId
);
596 DeleteCriticalSection(&This
->cs
);
597 HeapFree(GetProcessHeap(), 0, This
->displayName
);
598 HeapFree(GetProcessHeap(), 0, This
);
601 *pJobId
= This
->jobId
;
603 list_init(&This
->files
);
604 This
->jobProgress
.BytesTotal
= 0;
605 This
->jobProgress
.BytesTransferred
= 0;
606 This
->jobProgress
.FilesTotal
= 0;
607 This
->jobProgress
.FilesTransferred
= 0;
609 This
->state
= BG_JOB_STATE_SUSPENDED
;
611 *ppObj
= &This
->lpVtbl
;
615 void processJob(BackgroundCopyJobImpl
*job
)
619 BackgroundCopyFileImpl
*file
;
622 EnterCriticalSection(&job
->cs
);
623 LIST_FOR_EACH_ENTRY(file
, &job
->files
, BackgroundCopyFileImpl
, entryFromJob
)
624 if (!file
->fileProgress
.Completed
)
629 LeaveCriticalSection(&job
->cs
);
632 transitionJobState(job
, BG_JOB_STATE_QUEUED
, BG_JOB_STATE_TRANSFERRED
);
636 if (!processFile(file
, job
))