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 inline BOOL
is_job_done(const BackgroundCopyJobImpl
*job
)
33 return job
->state
== BG_JOB_STATE_CANCELLED
|| job
->state
== BG_JOB_STATE_ACKNOWLEDGED
;
36 static inline BackgroundCopyJobImpl
*impl_from_IBackgroundCopyJob2(IBackgroundCopyJob2
*iface
)
38 return CONTAINING_RECORD(iface
, BackgroundCopyJobImpl
, IBackgroundCopyJob2_iface
);
41 static HRESULT WINAPI
BackgroundCopyJob_QueryInterface(
42 IBackgroundCopyJob2
*iface
, REFIID riid
, void **obj
)
44 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
46 TRACE("(%p)->(%s %p)\n", This
, debugstr_guid(riid
), obj
);
48 if (IsEqualGUID(riid
, &IID_IUnknown
)
49 || IsEqualGUID(riid
, &IID_IBackgroundCopyJob
)
50 || IsEqualGUID(riid
, &IID_IBackgroundCopyJob2
))
53 IBackgroundCopyJob2_AddRef(iface
);
61 static ULONG WINAPI
BackgroundCopyJob_AddRef(IBackgroundCopyJob2
*iface
)
63 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
64 ULONG ref
= InterlockedIncrement(&This
->ref
);
65 TRACE("(%p)->(%d)\n", This
, ref
);
69 static ULONG WINAPI
BackgroundCopyJob_Release(IBackgroundCopyJob2
*iface
)
71 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
72 ULONG ref
= InterlockedDecrement(&This
->ref
);
74 TRACE("(%p)->(%d)\n", This
, ref
);
78 This
->cs
.DebugInfo
->Spare
[0] = 0;
79 DeleteCriticalSection(&This
->cs
);
81 IBackgroundCopyCallback2_Release(This
->callback
);
82 HeapFree(GetProcessHeap(), 0, This
->displayName
);
83 HeapFree(GetProcessHeap(), 0, This
->description
);
84 HeapFree(GetProcessHeap(), 0, This
);
90 /*** IBackgroundCopyJob methods ***/
92 static HRESULT WINAPI
BackgroundCopyJob_AddFileSet(
93 IBackgroundCopyJob2
*iface
,
95 BG_FILE_INFO
*pFileSet
)
97 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
101 TRACE("(%p)->(%d %p)\n", This
, cFileCount
, pFileSet
);
103 EnterCriticalSection(&This
->cs
);
105 for (i
= 0; i
< cFileCount
; ++i
)
107 BackgroundCopyFileImpl
*file
;
109 /* We should return E_INVALIDARG in these cases. */
110 FIXME("Check for valid filenames and supported protocols\n");
112 hr
= BackgroundCopyFileConstructor(This
, pFileSet
[i
].RemoteName
, pFileSet
[i
].LocalName
, &file
);
113 if (hr
!= S_OK
) break;
115 /* Add a reference to the file to file list */
116 list_add_head(&This
->files
, &file
->entryFromJob
);
117 This
->jobProgress
.BytesTotal
= BG_SIZE_UNKNOWN
;
118 ++This
->jobProgress
.FilesTotal
;
121 LeaveCriticalSection(&This
->cs
);
126 static HRESULT WINAPI
BackgroundCopyJob_AddFile(
127 IBackgroundCopyJob2
*iface
,
131 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
134 TRACE("(%p)->(%s %s)\n", This
, debugstr_w(RemoteUrl
), debugstr_w(LocalName
));
136 file
.RemoteName
= (LPWSTR
)RemoteUrl
;
137 file
.LocalName
= (LPWSTR
)LocalName
;
138 return IBackgroundCopyJob2_AddFileSet(iface
, 1, &file
);
141 static HRESULT WINAPI
BackgroundCopyJob_EnumFiles(
142 IBackgroundCopyJob2
*iface
,
143 IEnumBackgroundCopyFiles
**enum_files
)
145 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
146 TRACE("(%p)->(%p)\n", This
, enum_files
);
147 return EnumBackgroundCopyFilesConstructor(This
, enum_files
);
150 static HRESULT WINAPI
BackgroundCopyJob_Suspend(
151 IBackgroundCopyJob2
*iface
)
153 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
154 FIXME("(%p): stub\n", This
);
158 static HRESULT WINAPI
BackgroundCopyJob_Resume(
159 IBackgroundCopyJob2
*iface
)
161 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
164 TRACE("(%p)\n", This
);
166 EnterCriticalSection(&globalMgr
.cs
);
167 if (is_job_done(This
))
169 rv
= BG_E_INVALID_STATE
;
171 else if (This
->jobProgress
.FilesTransferred
== This
->jobProgress
.FilesTotal
)
175 else if (This
->state
!= BG_JOB_STATE_CONNECTING
176 && This
->state
!= BG_JOB_STATE_TRANSFERRING
)
178 This
->state
= BG_JOB_STATE_QUEUED
;
179 SetEvent(globalMgr
.jobEvent
);
181 LeaveCriticalSection(&globalMgr
.cs
);
186 static HRESULT WINAPI
BackgroundCopyJob_Cancel(
187 IBackgroundCopyJob2
*iface
)
189 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
190 FIXME("(%p): stub\n", This
);
194 static HRESULT WINAPI
BackgroundCopyJob_Complete(
195 IBackgroundCopyJob2
*iface
)
197 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
200 TRACE("(%p)\n", This
);
202 EnterCriticalSection(&This
->cs
);
204 if (is_job_done(This
))
206 rv
= BG_E_INVALID_STATE
;
210 BackgroundCopyFileImpl
*file
;
211 LIST_FOR_EACH_ENTRY(file
, &This
->files
, BackgroundCopyFileImpl
, entryFromJob
)
213 if (file
->fileProgress
.Completed
)
215 if (!MoveFileExW(file
->tempFileName
, file
->info
.LocalName
,
216 (MOVEFILE_COPY_ALLOWED
217 | MOVEFILE_REPLACE_EXISTING
218 | MOVEFILE_WRITE_THROUGH
)))
220 ERR("Couldn't rename file %s -> %s\n",
221 debugstr_w(file
->tempFileName
),
222 debugstr_w(file
->info
.LocalName
));
223 rv
= BG_S_PARTIAL_COMPLETE
;
227 rv
= BG_S_PARTIAL_COMPLETE
;
231 This
->state
= BG_JOB_STATE_ACKNOWLEDGED
;
232 LeaveCriticalSection(&This
->cs
);
237 static HRESULT WINAPI
BackgroundCopyJob_GetId(
238 IBackgroundCopyJob2
*iface
,
241 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
242 TRACE("(%p)->(%p)\n", This
, pVal
);
247 static HRESULT WINAPI
BackgroundCopyJob_GetType(
248 IBackgroundCopyJob2
*iface
,
251 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
253 TRACE("(%p)->(%p)\n", This
, pVal
);
262 static HRESULT WINAPI
BackgroundCopyJob_GetProgress(
263 IBackgroundCopyJob2
*iface
,
264 BG_JOB_PROGRESS
*pVal
)
266 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
268 TRACE("(%p)->(%p)\n", This
, pVal
);
273 EnterCriticalSection(&This
->cs
);
274 pVal
->BytesTotal
= This
->jobProgress
.BytesTotal
;
275 pVal
->BytesTransferred
= This
->jobProgress
.BytesTransferred
;
276 pVal
->FilesTotal
= This
->jobProgress
.FilesTotal
;
277 pVal
->FilesTransferred
= This
->jobProgress
.FilesTransferred
;
278 LeaveCriticalSection(&This
->cs
);
283 static HRESULT WINAPI
BackgroundCopyJob_GetTimes(
284 IBackgroundCopyJob2
*iface
,
287 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
288 FIXME("(%p)->(%p): stub\n", This
, pVal
);
292 static HRESULT WINAPI
BackgroundCopyJob_GetState(
293 IBackgroundCopyJob2
*iface
,
296 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
298 TRACE("(%p)->(%p)\n", This
, pVal
);
303 /* Don't think we need a critical section for this */
308 static HRESULT WINAPI
BackgroundCopyJob_GetError(
309 IBackgroundCopyJob2
*iface
,
310 IBackgroundCopyError
**ppError
)
312 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
313 FIXME("(%p)->(%p): stub\n", This
, ppError
);
317 static HRESULT WINAPI
BackgroundCopyJob_GetOwner(
318 IBackgroundCopyJob2
*iface
,
321 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
322 FIXME("(%p)->(%p): stub\n", This
, pVal
);
326 static HRESULT WINAPI
BackgroundCopyJob_SetDisplayName(
327 IBackgroundCopyJob2
*iface
,
330 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
331 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(Val
));
335 static HRESULT WINAPI
BackgroundCopyJob_GetDisplayName(
336 IBackgroundCopyJob2
*iface
,
339 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
341 TRACE("(%p)->(%p)\n", This
, pVal
);
343 return return_strval(This
->displayName
, pVal
);
346 static HRESULT WINAPI
BackgroundCopyJob_SetDescription(
347 IBackgroundCopyJob2
*iface
,
350 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
351 static const int max_description_len
= 1024;
355 TRACE("(%p)->(%s)\n", This
, debugstr_w(Val
));
357 if (!Val
) return E_INVALIDARG
;
360 if (len
> max_description_len
) return BG_E_STRING_TOO_LONG
;
362 EnterCriticalSection(&This
->cs
);
364 if (is_job_done(This
))
366 hr
= BG_E_INVALID_STATE
;
370 HeapFree(GetProcessHeap(), 0, This
->description
);
371 if ((This
->description
= HeapAlloc(GetProcessHeap(), 0, (len
+1)*sizeof(WCHAR
))))
372 strcpyW(This
->description
, Val
);
377 LeaveCriticalSection(&This
->cs
);
382 static HRESULT WINAPI
BackgroundCopyJob_GetDescription(
383 IBackgroundCopyJob2
*iface
,
386 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
388 TRACE("(%p)->(%p)\n", This
, pVal
);
390 return return_strval(This
->description
, pVal
);
393 static HRESULT WINAPI
BackgroundCopyJob_SetPriority(
394 IBackgroundCopyJob2
*iface
,
397 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
398 FIXME("(%p)->(%d): stub\n", This
, Val
);
402 static HRESULT WINAPI
BackgroundCopyJob_GetPriority(
403 IBackgroundCopyJob2
*iface
,
404 BG_JOB_PRIORITY
*pVal
)
406 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
407 FIXME("(%p)->(%p): stub\n", This
, pVal
);
411 static HRESULT WINAPI
BackgroundCopyJob_SetNotifyFlags(
412 IBackgroundCopyJob2
*iface
,
415 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
416 static const ULONG valid_flags
= BG_NOTIFY_JOB_TRANSFERRED
|
417 BG_NOTIFY_JOB_ERROR
|
419 BG_NOTIFY_JOB_MODIFICATION
|
420 BG_NOTIFY_FILE_TRANSFERRED
;
422 TRACE("(%p)->(0x%x)\n", This
, Val
);
424 if (is_job_done(This
)) return BG_E_INVALID_STATE
;
425 if (Val
& ~valid_flags
) return E_NOTIMPL
;
426 This
->notify_flags
= Val
;
430 static HRESULT WINAPI
BackgroundCopyJob_GetNotifyFlags(
431 IBackgroundCopyJob2
*iface
,
434 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
436 TRACE("(%p)->(%p)\n", This
, pVal
);
438 if (!pVal
) return E_INVALIDARG
;
440 *pVal
= This
->notify_flags
;
445 static HRESULT WINAPI
BackgroundCopyJob_SetNotifyInterface(
446 IBackgroundCopyJob2
*iface
,
449 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
452 TRACE("(%p)->(%p)\n", This
, Val
);
454 if (is_job_done(This
)) return BG_E_INVALID_STATE
;
458 IBackgroundCopyCallback2_Release(This
->callback
);
459 This
->callback
= NULL
;
460 This
->callback2
= FALSE
;
465 hr
= IUnknown_QueryInterface(Val
, &IID_IBackgroundCopyCallback2
, (void**)&This
->callback
);
467 hr
= IUnknown_QueryInterface(Val
, &IID_IBackgroundCopyCallback
, (void**)&This
->callback
);
469 This
->callback2
= TRUE
;
475 static HRESULT WINAPI
BackgroundCopyJob_GetNotifyInterface(
476 IBackgroundCopyJob2
*iface
,
479 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
481 TRACE("(%p)->(%p)\n", This
, pVal
);
483 if (!pVal
) return E_INVALIDARG
;
485 *pVal
= (IUnknown
*)This
->callback
;
487 IUnknown_AddRef(*pVal
);
492 static HRESULT WINAPI
BackgroundCopyJob_SetMinimumRetryDelay(
493 IBackgroundCopyJob2
*iface
,
496 FIXME("%u\n", Seconds
);
500 static HRESULT WINAPI
BackgroundCopyJob_GetMinimumRetryDelay(
501 IBackgroundCopyJob2
*iface
,
504 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
505 FIXME("(%p)->(%p): stub\n", This
, Seconds
);
510 static HRESULT WINAPI
BackgroundCopyJob_SetNoProgressTimeout(
511 IBackgroundCopyJob2
*iface
,
514 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
515 FIXME("(%p)->(%d): stub\n", This
, Seconds
);
519 static HRESULT WINAPI
BackgroundCopyJob_GetNoProgressTimeout(
520 IBackgroundCopyJob2
*iface
,
523 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
524 FIXME("(%p)->(%p): stub\n", This
, Seconds
);
529 static HRESULT WINAPI
BackgroundCopyJob_GetErrorCount(
530 IBackgroundCopyJob2
*iface
,
533 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
534 FIXME("(%p)->(%p): stub\n", This
, Errors
);
538 static HRESULT WINAPI
BackgroundCopyJob_SetProxySettings(
539 IBackgroundCopyJob2
*iface
,
540 BG_JOB_PROXY_USAGE ProxyUsage
,
541 const WCHAR
*ProxyList
,
542 const WCHAR
*ProxyBypassList
)
544 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
545 FIXME("(%p)->(%d %s %s): stub\n", This
, ProxyUsage
, debugstr_w(ProxyList
), debugstr_w(ProxyBypassList
));
549 static HRESULT WINAPI
BackgroundCopyJob_GetProxySettings(
550 IBackgroundCopyJob2
*iface
,
551 BG_JOB_PROXY_USAGE
*pProxyUsage
,
553 LPWSTR
*pProxyBypassList
)
555 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
556 FIXME("(%p)->(%p %p %p): stub\n", This
, pProxyUsage
, pProxyList
, pProxyBypassList
);
560 static HRESULT WINAPI
BackgroundCopyJob_TakeOwnership(
561 IBackgroundCopyJob2
*iface
)
563 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
564 FIXME("(%p): stub\n", This
);
568 static HRESULT WINAPI
BackgroundCopyJob_SetNotifyCmdLine(
569 IBackgroundCopyJob2
*iface
,
573 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
574 FIXME("(%p)->(%s %s): stub\n", This
, debugstr_w(prog
), debugstr_w(params
));
578 static HRESULT WINAPI
BackgroundCopyJob_GetNotifyCmdLine(
579 IBackgroundCopyJob2
*iface
,
583 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
584 FIXME("(%p)->(%p %p): stub\n", This
, prog
, params
);
588 static HRESULT WINAPI
BackgroundCopyJob_GetReplyProgress(
589 IBackgroundCopyJob2
*iface
,
590 BG_JOB_REPLY_PROGRESS
*progress
)
592 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
593 FIXME("(%p)->(%p): stub\n", This
, progress
);
597 static HRESULT WINAPI
BackgroundCopyJob_GetReplyData(
598 IBackgroundCopyJob2
*iface
,
602 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
603 FIXME("(%p)->(%p %p): stub\n", This
, pBuffer
, pLength
);
607 static HRESULT WINAPI
BackgroundCopyJob_SetReplyFileName(
608 IBackgroundCopyJob2
*iface
,
611 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
612 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(filename
));
616 static HRESULT WINAPI
BackgroundCopyJob_GetReplyFileName(
617 IBackgroundCopyJob2
*iface
,
620 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
621 FIXME("(%p)->(%p): stub\n", This
, pFilename
);
625 static HRESULT WINAPI
BackgroundCopyJob_SetCredentials(
626 IBackgroundCopyJob2
*iface
,
627 BG_AUTH_CREDENTIALS
*cred
)
629 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
630 FIXME("(%p)->(%p): stub\n", This
, cred
);
634 static HRESULT WINAPI
BackgroundCopyJob_RemoveCredentials(
635 IBackgroundCopyJob2
*iface
,
636 BG_AUTH_TARGET target
,
637 BG_AUTH_SCHEME scheme
)
639 BackgroundCopyJobImpl
*This
= impl_from_IBackgroundCopyJob2(iface
);
640 FIXME("(%p)->(%d %d): stub\n", This
, target
, scheme
);
644 static const IBackgroundCopyJob2Vtbl BackgroundCopyJobVtbl
=
646 BackgroundCopyJob_QueryInterface
,
647 BackgroundCopyJob_AddRef
,
648 BackgroundCopyJob_Release
,
649 BackgroundCopyJob_AddFileSet
,
650 BackgroundCopyJob_AddFile
,
651 BackgroundCopyJob_EnumFiles
,
652 BackgroundCopyJob_Suspend
,
653 BackgroundCopyJob_Resume
,
654 BackgroundCopyJob_Cancel
,
655 BackgroundCopyJob_Complete
,
656 BackgroundCopyJob_GetId
,
657 BackgroundCopyJob_GetType
,
658 BackgroundCopyJob_GetProgress
,
659 BackgroundCopyJob_GetTimes
,
660 BackgroundCopyJob_GetState
,
661 BackgroundCopyJob_GetError
,
662 BackgroundCopyJob_GetOwner
,
663 BackgroundCopyJob_SetDisplayName
,
664 BackgroundCopyJob_GetDisplayName
,
665 BackgroundCopyJob_SetDescription
,
666 BackgroundCopyJob_GetDescription
,
667 BackgroundCopyJob_SetPriority
,
668 BackgroundCopyJob_GetPriority
,
669 BackgroundCopyJob_SetNotifyFlags
,
670 BackgroundCopyJob_GetNotifyFlags
,
671 BackgroundCopyJob_SetNotifyInterface
,
672 BackgroundCopyJob_GetNotifyInterface
,
673 BackgroundCopyJob_SetMinimumRetryDelay
,
674 BackgroundCopyJob_GetMinimumRetryDelay
,
675 BackgroundCopyJob_SetNoProgressTimeout
,
676 BackgroundCopyJob_GetNoProgressTimeout
,
677 BackgroundCopyJob_GetErrorCount
,
678 BackgroundCopyJob_SetProxySettings
,
679 BackgroundCopyJob_GetProxySettings
,
680 BackgroundCopyJob_TakeOwnership
,
681 BackgroundCopyJob_SetNotifyCmdLine
,
682 BackgroundCopyJob_GetNotifyCmdLine
,
683 BackgroundCopyJob_GetReplyProgress
,
684 BackgroundCopyJob_GetReplyData
,
685 BackgroundCopyJob_SetReplyFileName
,
686 BackgroundCopyJob_GetReplyFileName
,
687 BackgroundCopyJob_SetCredentials
,
688 BackgroundCopyJob_RemoveCredentials
691 HRESULT
BackgroundCopyJobConstructor(LPCWSTR displayName
, BG_JOB_TYPE type
, GUID
*job_id
, BackgroundCopyJobImpl
**job
)
694 BackgroundCopyJobImpl
*This
;
697 TRACE("(%s,%d,%p)\n", debugstr_w(displayName
), type
, job
);
699 This
= HeapAlloc(GetProcessHeap(), 0, sizeof *This
);
701 return E_OUTOFMEMORY
;
703 This
->IBackgroundCopyJob2_iface
.lpVtbl
= &BackgroundCopyJobVtbl
;
704 InitializeCriticalSection(&This
->cs
);
705 This
->cs
.DebugInfo
->Spare
[0] = (DWORD_PTR
)(__FILE__
": BackgroundCopyJobImpl.cs");
710 n
= (strlenW(displayName
) + 1) * sizeof *displayName
;
711 This
->displayName
= HeapAlloc(GetProcessHeap(), 0, n
);
712 if (!This
->displayName
)
714 This
->cs
.DebugInfo
->Spare
[0] = 0;
715 DeleteCriticalSection(&This
->cs
);
716 HeapFree(GetProcessHeap(), 0, This
);
717 return E_OUTOFMEMORY
;
719 memcpy(This
->displayName
, displayName
, n
);
721 hr
= CoCreateGuid(&This
->jobId
);
724 This
->cs
.DebugInfo
->Spare
[0] = 0;
725 DeleteCriticalSection(&This
->cs
);
726 HeapFree(GetProcessHeap(), 0, This
->displayName
);
727 HeapFree(GetProcessHeap(), 0, This
);
730 *job_id
= This
->jobId
;
732 list_init(&This
->files
);
733 This
->jobProgress
.BytesTotal
= 0;
734 This
->jobProgress
.BytesTransferred
= 0;
735 This
->jobProgress
.FilesTotal
= 0;
736 This
->jobProgress
.FilesTransferred
= 0;
738 This
->state
= BG_JOB_STATE_SUSPENDED
;
739 This
->description
= NULL
;
740 This
->notify_flags
= BG_NOTIFY_JOB_ERROR
| BG_NOTIFY_JOB_TRANSFERRED
;
741 This
->callback
= NULL
;
742 This
->callback2
= FALSE
;
746 TRACE("created job %s:%p\n", debugstr_guid(&This
->jobId
), This
);
751 void processJob(BackgroundCopyJobImpl
*job
)
755 BackgroundCopyFileImpl
*file
;
758 EnterCriticalSection(&job
->cs
);
759 LIST_FOR_EACH_ENTRY(file
, &job
->files
, BackgroundCopyFileImpl
, entryFromJob
)
760 if (!file
->fileProgress
.Completed
)
765 LeaveCriticalSection(&job
->cs
);
768 transitionJobState(job
, BG_JOB_STATE_QUEUED
, BG_JOB_STATE_TRANSFERRED
);
772 if (!processFile(file
, job
))