winex11: Get rid of some needless globals.
[wine/multimedia.git] / dlls / qmgr / job.c
blob9d8d928d707124f29bc7af3edd84dba81361986d
1 /*
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
21 #include <stdarg.h>
23 #include "windef.h"
24 #include "winbase.h"
26 #include "qmgr.h"
27 #include "wine/debug.h"
29 WINE_DEFAULT_DEBUG_CHANNEL(qmgr);
31 static void BackgroundCopyJobDestructor(BackgroundCopyJobImpl *This)
33 This->cs.DebugInfo->Spare[0] = 0;
34 DeleteCriticalSection(&This->cs);
35 HeapFree(GetProcessHeap(), 0, This->displayName);
36 HeapFree(GetProcessHeap(), 0, This);
39 static ULONG WINAPI BITS_IBackgroundCopyJob_AddRef(IBackgroundCopyJob2 *iface)
41 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
42 return InterlockedIncrement(&This->ref);
45 static HRESULT WINAPI BITS_IBackgroundCopyJob_QueryInterface(
46 IBackgroundCopyJob2 *iface, REFIID riid, LPVOID *ppvObject)
48 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
49 TRACE("IID: %s\n", debugstr_guid(riid));
51 if (IsEqualGUID(riid, &IID_IUnknown)
52 || IsEqualGUID(riid, &IID_IBackgroundCopyJob)
53 || IsEqualGUID(riid, &IID_IBackgroundCopyJob2))
55 *ppvObject = &This->lpVtbl;
56 BITS_IBackgroundCopyJob_AddRef(iface);
57 return S_OK;
60 *ppvObject = NULL;
61 return E_NOINTERFACE;
64 static ULONG WINAPI BITS_IBackgroundCopyJob_Release(IBackgroundCopyJob2 *iface)
66 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
67 ULONG ref = InterlockedDecrement(&This->ref);
69 if (ref == 0)
70 BackgroundCopyJobDestructor(This);
72 return ref;
75 /*** IBackgroundCopyJob methods ***/
77 static HRESULT WINAPI BITS_IBackgroundCopyJob_AddFileSet(
78 IBackgroundCopyJob2 *iface,
79 ULONG cFileCount,
80 BG_FILE_INFO *pFileSet)
82 ULONG i;
83 for (i = 0; i < cFileCount; ++i)
85 HRESULT hr = IBackgroundCopyJob_AddFile(iface, pFileSet[i].RemoteName,
86 pFileSet[i].LocalName);
87 if (FAILED(hr))
88 return hr;
90 return S_OK;
93 static HRESULT WINAPI BITS_IBackgroundCopyJob_AddFile(
94 IBackgroundCopyJob2 *iface,
95 LPCWSTR RemoteUrl,
96 LPCWSTR LocalName)
98 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
99 IBackgroundCopyFile *pFile;
100 BackgroundCopyFileImpl *file;
101 HRESULT res;
103 /* We should return E_INVALIDARG in these cases. */
104 FIXME("Check for valid filenames and supported protocols\n");
106 res = BackgroundCopyFileConstructor(This, RemoteUrl, LocalName, (LPVOID *) &pFile);
107 if (res != S_OK)
108 return res;
110 /* Add a reference to the file to file list */
111 IBackgroundCopyFile_AddRef(pFile);
112 file = (BackgroundCopyFileImpl *) pFile;
113 EnterCriticalSection(&This->cs);
114 list_add_head(&This->files, &file->entryFromJob);
115 This->jobProgress.BytesTotal = BG_SIZE_UNKNOWN;
116 ++This->jobProgress.FilesTotal;
117 LeaveCriticalSection(&This->cs);
119 return S_OK;
122 static HRESULT WINAPI BITS_IBackgroundCopyJob_EnumFiles(
123 IBackgroundCopyJob2 *iface,
124 IEnumBackgroundCopyFiles **ppEnum)
126 TRACE("\n");
127 return EnumBackgroundCopyFilesConstructor((LPVOID *) ppEnum, iface);
130 static HRESULT WINAPI BITS_IBackgroundCopyJob_Suspend(
131 IBackgroundCopyJob2 *iface)
133 FIXME("Not implemented\n");
134 return E_NOTIMPL;
137 static HRESULT WINAPI BITS_IBackgroundCopyJob_Resume(
138 IBackgroundCopyJob2 *iface)
140 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
141 HRESULT rv = S_OK;
143 EnterCriticalSection(&globalMgr.cs);
144 if (This->state == BG_JOB_STATE_CANCELLED
145 || This->state == BG_JOB_STATE_ACKNOWLEDGED)
147 rv = BG_E_INVALID_STATE;
149 else if (This->jobProgress.FilesTransferred == This->jobProgress.FilesTotal)
151 rv = BG_E_EMPTY;
153 else if (This->state != BG_JOB_STATE_CONNECTING
154 && This->state != BG_JOB_STATE_TRANSFERRING)
156 This->state = BG_JOB_STATE_QUEUED;
157 SetEvent(globalMgr.jobEvent);
159 LeaveCriticalSection(&globalMgr.cs);
161 return rv;
164 static HRESULT WINAPI BITS_IBackgroundCopyJob_Cancel(
165 IBackgroundCopyJob2 *iface)
167 FIXME("Not implemented\n");
168 return E_NOTIMPL;
171 static HRESULT WINAPI BITS_IBackgroundCopyJob_Complete(
172 IBackgroundCopyJob2 *iface)
174 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
175 HRESULT rv = S_OK;
177 EnterCriticalSection(&This->cs);
179 if (This->state == BG_JOB_STATE_CANCELLED
180 || This->state == BG_JOB_STATE_ACKNOWLEDGED)
182 rv = BG_E_INVALID_STATE;
184 else
186 BackgroundCopyFileImpl *file;
187 LIST_FOR_EACH_ENTRY(file, &This->files, BackgroundCopyFileImpl, entryFromJob)
189 if (file->fileProgress.Completed)
191 if (!MoveFileExW(file->tempFileName, file->info.LocalName,
192 (MOVEFILE_COPY_ALLOWED
193 | MOVEFILE_REPLACE_EXISTING
194 | MOVEFILE_WRITE_THROUGH)))
196 ERR("Couldn't rename file %s -> %s\n",
197 debugstr_w(file->tempFileName),
198 debugstr_w(file->info.LocalName));
199 rv = BG_S_PARTIAL_COMPLETE;
202 else
203 rv = BG_S_PARTIAL_COMPLETE;
207 This->state = BG_JOB_STATE_ACKNOWLEDGED;
208 LeaveCriticalSection(&This->cs);
210 return rv;
213 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetId(
214 IBackgroundCopyJob2 *iface,
215 GUID *pVal)
217 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
218 *pVal = This->jobId;
219 return S_OK;
222 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetType(
223 IBackgroundCopyJob2 *iface,
224 BG_JOB_TYPE *pVal)
226 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
228 if (!pVal)
229 return E_INVALIDARG;
231 *pVal = This->type;
232 return S_OK;
235 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetProgress(
236 IBackgroundCopyJob2 *iface,
237 BG_JOB_PROGRESS *pVal)
239 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
241 if (!pVal)
242 return E_INVALIDARG;
244 EnterCriticalSection(&This->cs);
245 pVal->BytesTotal = This->jobProgress.BytesTotal;
246 pVal->BytesTransferred = This->jobProgress.BytesTransferred;
247 pVal->FilesTotal = This->jobProgress.FilesTotal;
248 pVal->FilesTransferred = This->jobProgress.FilesTransferred;
249 LeaveCriticalSection(&This->cs);
251 return S_OK;
254 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetTimes(
255 IBackgroundCopyJob2 *iface,
256 BG_JOB_TIMES *pVal)
258 FIXME("Not implemented\n");
259 return E_NOTIMPL;
262 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetState(
263 IBackgroundCopyJob2 *iface,
264 BG_JOB_STATE *pVal)
266 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
268 if (!pVal)
269 return E_INVALIDARG;
271 /* Don't think we need a critical section for this */
272 *pVal = This->state;
273 return S_OK;
276 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetError(
277 IBackgroundCopyJob2 *iface,
278 IBackgroundCopyError **ppError)
280 FIXME("Not implemented\n");
281 return E_NOTIMPL;
284 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetOwner(
285 IBackgroundCopyJob2 *iface,
286 LPWSTR *pVal)
288 FIXME("Not implemented\n");
289 return E_NOTIMPL;
292 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetDisplayName(
293 IBackgroundCopyJob2 *iface,
294 LPCWSTR Val)
296 FIXME("Not implemented\n");
297 return E_NOTIMPL;
300 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetDisplayName(
301 IBackgroundCopyJob2 *iface,
302 LPWSTR *pVal)
304 BackgroundCopyJobImpl *This = (BackgroundCopyJobImpl *) iface;
305 int n;
307 if (!pVal)
308 return E_INVALIDARG;
310 n = (lstrlenW(This->displayName) + 1) * sizeof **pVal;
311 *pVal = CoTaskMemAlloc(n);
312 if (*pVal == NULL)
313 return E_OUTOFMEMORY;
314 memcpy(*pVal, This->displayName, n);
315 return S_OK;
318 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetDescription(
319 IBackgroundCopyJob2 *iface,
320 LPCWSTR Val)
322 FIXME("Not implemented\n");
323 return E_NOTIMPL;
326 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetDescription(
327 IBackgroundCopyJob2 *iface,
328 LPWSTR *pVal)
330 FIXME("Not implemented\n");
331 return E_NOTIMPL;
334 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetPriority(
335 IBackgroundCopyJob2 *iface,
336 BG_JOB_PRIORITY Val)
338 FIXME("(%p,0x%08x) stub\n", iface, Val);
339 return S_OK;
342 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetPriority(
343 IBackgroundCopyJob2 *iface,
344 BG_JOB_PRIORITY *pVal)
346 FIXME("Not implemented\n");
347 return E_NOTIMPL;
350 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetNotifyFlags(
351 IBackgroundCopyJob2 *iface,
352 ULONG Val)
354 FIXME("Not implemented\n");
355 return E_NOTIMPL;
358 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetNotifyFlags(
359 IBackgroundCopyJob2 *iface,
360 ULONG *pVal)
362 FIXME("Not implemented\n");
363 return E_NOTIMPL;
366 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetNotifyInterface(
367 IBackgroundCopyJob2 *iface,
368 IUnknown *Val)
370 FIXME("Not implemented\n");
371 return E_NOTIMPL;
374 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetNotifyInterface(
375 IBackgroundCopyJob2 *iface,
376 IUnknown **pVal)
378 FIXME("Not implemented\n");
379 return E_NOTIMPL;
382 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetMinimumRetryDelay(
383 IBackgroundCopyJob2 *iface,
384 ULONG Seconds)
386 FIXME("%u\n", Seconds);
387 return S_OK;
390 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetMinimumRetryDelay(
391 IBackgroundCopyJob2 *iface,
392 ULONG *Seconds)
394 FIXME("%p\n", Seconds);
395 *Seconds = 30;
396 return S_OK;
399 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetNoProgressTimeout(
400 IBackgroundCopyJob2 *iface,
401 ULONG Seconds)
403 FIXME("%u\n", Seconds);
404 return S_OK;
407 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetNoProgressTimeout(
408 IBackgroundCopyJob2 *iface,
409 ULONG *Seconds)
411 FIXME("%p\n", Seconds);
412 *Seconds = 900;
413 return S_OK;
416 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetErrorCount(
417 IBackgroundCopyJob2 *iface,
418 ULONG *Errors)
420 FIXME("Not implemented\n");
421 return E_NOTIMPL;
424 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetProxySettings(
425 IBackgroundCopyJob2 *iface,
426 BG_JOB_PROXY_USAGE ProxyUsage,
427 const WCHAR *ProxyList,
428 const WCHAR *ProxyBypassList)
430 FIXME("Not implemented\n");
431 return E_NOTIMPL;
434 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetProxySettings(
435 IBackgroundCopyJob2 *iface,
436 BG_JOB_PROXY_USAGE *pProxyUsage,
437 LPWSTR *pProxyList,
438 LPWSTR *pProxyBypassList)
440 FIXME("Not implemented\n");
441 return E_NOTIMPL;
444 static HRESULT WINAPI BITS_IBackgroundCopyJob_TakeOwnership(
445 IBackgroundCopyJob2 *iface)
447 FIXME("Not implemented\n");
448 return E_NOTIMPL;
451 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetNotifyCmdLine(
452 IBackgroundCopyJob2 *iface,
453 LPCWSTR prog,
454 LPCWSTR params)
456 FIXME("Not implemented\n");
457 return E_NOTIMPL;
460 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetNotifyCmdLine(
461 IBackgroundCopyJob2 *iface,
462 LPWSTR *prog,
463 LPWSTR *params)
465 FIXME("Not implemented\n");
466 return E_NOTIMPL;
469 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetReplyProgress(
470 IBackgroundCopyJob2 *iface,
471 BG_JOB_REPLY_PROGRESS *progress)
473 FIXME("Not implemented\n");
474 return E_NOTIMPL;
477 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetReplyData(
478 IBackgroundCopyJob2 *iface,
479 byte **pBuffer,
480 UINT64 *pLength)
482 FIXME("Not implemented\n");
483 return E_NOTIMPL;
486 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetReplyFileName(
487 IBackgroundCopyJob2 *iface,
488 LPCWSTR filename)
490 FIXME("Not implemented\n");
491 return E_NOTIMPL;
494 static HRESULT WINAPI BITS_IBackgroundCopyJob_GetReplyFileName(
495 IBackgroundCopyJob2 *iface,
496 LPWSTR *pFilename)
498 FIXME("Not implemented\n");
499 return E_NOTIMPL;
502 static HRESULT WINAPI BITS_IBackgroundCopyJob_SetCredentials(
503 IBackgroundCopyJob2 *iface,
504 BG_AUTH_CREDENTIALS *cred)
506 FIXME("Not implemented\n");
507 return S_OK;
510 static HRESULT WINAPI BITS_IBackgroundCopyJob_RemoveCredentials(
511 IBackgroundCopyJob2 *iface,
512 BG_AUTH_TARGET target,
513 BG_AUTH_SCHEME scheme)
515 FIXME("Not implemented\n");
516 return S_OK;
519 static const IBackgroundCopyJob2Vtbl BITS_IBackgroundCopyJob_Vtbl =
521 BITS_IBackgroundCopyJob_QueryInterface,
522 BITS_IBackgroundCopyJob_AddRef,
523 BITS_IBackgroundCopyJob_Release,
524 BITS_IBackgroundCopyJob_AddFileSet,
525 BITS_IBackgroundCopyJob_AddFile,
526 BITS_IBackgroundCopyJob_EnumFiles,
527 BITS_IBackgroundCopyJob_Suspend,
528 BITS_IBackgroundCopyJob_Resume,
529 BITS_IBackgroundCopyJob_Cancel,
530 BITS_IBackgroundCopyJob_Complete,
531 BITS_IBackgroundCopyJob_GetId,
532 BITS_IBackgroundCopyJob_GetType,
533 BITS_IBackgroundCopyJob_GetProgress,
534 BITS_IBackgroundCopyJob_GetTimes,
535 BITS_IBackgroundCopyJob_GetState,
536 BITS_IBackgroundCopyJob_GetError,
537 BITS_IBackgroundCopyJob_GetOwner,
538 BITS_IBackgroundCopyJob_SetDisplayName,
539 BITS_IBackgroundCopyJob_GetDisplayName,
540 BITS_IBackgroundCopyJob_SetDescription,
541 BITS_IBackgroundCopyJob_GetDescription,
542 BITS_IBackgroundCopyJob_SetPriority,
543 BITS_IBackgroundCopyJob_GetPriority,
544 BITS_IBackgroundCopyJob_SetNotifyFlags,
545 BITS_IBackgroundCopyJob_GetNotifyFlags,
546 BITS_IBackgroundCopyJob_SetNotifyInterface,
547 BITS_IBackgroundCopyJob_GetNotifyInterface,
548 BITS_IBackgroundCopyJob_SetMinimumRetryDelay,
549 BITS_IBackgroundCopyJob_GetMinimumRetryDelay,
550 BITS_IBackgroundCopyJob_SetNoProgressTimeout,
551 BITS_IBackgroundCopyJob_GetNoProgressTimeout,
552 BITS_IBackgroundCopyJob_GetErrorCount,
553 BITS_IBackgroundCopyJob_SetProxySettings,
554 BITS_IBackgroundCopyJob_GetProxySettings,
555 BITS_IBackgroundCopyJob_TakeOwnership,
556 BITS_IBackgroundCopyJob_SetNotifyCmdLine,
557 BITS_IBackgroundCopyJob_GetNotifyCmdLine,
558 BITS_IBackgroundCopyJob_GetReplyProgress,
559 BITS_IBackgroundCopyJob_GetReplyData,
560 BITS_IBackgroundCopyJob_SetReplyFileName,
561 BITS_IBackgroundCopyJob_GetReplyFileName,
562 BITS_IBackgroundCopyJob_SetCredentials,
563 BITS_IBackgroundCopyJob_RemoveCredentials
566 HRESULT BackgroundCopyJobConstructor(LPCWSTR displayName, BG_JOB_TYPE type,
567 GUID *pJobId, LPVOID *ppObj)
569 HRESULT hr;
570 BackgroundCopyJobImpl *This;
571 int n;
573 TRACE("(%s,%d,%p)\n", debugstr_w(displayName), type, ppObj);
575 This = HeapAlloc(GetProcessHeap(), 0, sizeof *This);
576 if (!This)
577 return E_OUTOFMEMORY;
579 This->lpVtbl = &BITS_IBackgroundCopyJob_Vtbl;
580 InitializeCriticalSection(&This->cs);
581 This->cs.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": BackgroundCopyJobImpl.cs");
583 This->ref = 1;
584 This->type = type;
586 n = (lstrlenW(displayName) + 1) * sizeof *displayName;
587 This->displayName = HeapAlloc(GetProcessHeap(), 0, n);
588 if (!This->displayName)
590 This->cs.DebugInfo->Spare[0] = 0;
591 DeleteCriticalSection(&This->cs);
592 HeapFree(GetProcessHeap(), 0, This);
593 return E_OUTOFMEMORY;
595 memcpy(This->displayName, displayName, n);
597 hr = CoCreateGuid(&This->jobId);
598 if (FAILED(hr))
600 This->cs.DebugInfo->Spare[0] = 0;
601 DeleteCriticalSection(&This->cs);
602 HeapFree(GetProcessHeap(), 0, This->displayName);
603 HeapFree(GetProcessHeap(), 0, This);
604 return hr;
606 *pJobId = This->jobId;
608 list_init(&This->files);
609 This->jobProgress.BytesTotal = 0;
610 This->jobProgress.BytesTransferred = 0;
611 This->jobProgress.FilesTotal = 0;
612 This->jobProgress.FilesTransferred = 0;
614 This->state = BG_JOB_STATE_SUSPENDED;
616 *ppObj = &This->lpVtbl;
617 return S_OK;
620 void processJob(BackgroundCopyJobImpl *job)
622 for (;;)
624 BackgroundCopyFileImpl *file;
625 BOOL done = TRUE;
627 EnterCriticalSection(&job->cs);
628 LIST_FOR_EACH_ENTRY(file, &job->files, BackgroundCopyFileImpl, entryFromJob)
629 if (!file->fileProgress.Completed)
631 done = FALSE;
632 break;
634 LeaveCriticalSection(&job->cs);
635 if (done)
637 transitionJobState(job, BG_JOB_STATE_QUEUED, BG_JOB_STATE_TRANSFERRED);
638 return;
641 if (!processFile(file, job))
642 return;