ReactOS  0.4.14-dev-342-gdc047f9
schtasks.c
Go to the documentation of this file.
1 /*
2  * Copyright 2012 Detlef Riekenberg
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 #define COBJMACROS
20 
21 #include "initguid.h"
22 #include "taskschd.h"
23 
24 #include "wine/debug.h"
25 #include "wine/unicode.h"
26 
28 
29 static const WCHAR change_optW[] = {'/','c','h','a','n','g','e',0};
30 static const WCHAR create_optW[] = {'/','c','r','e','a','t','e',0};
31 static const WCHAR delete_optW[] = {'/','d','e','l','e','t','e',0};
32 static const WCHAR enable_optW[] = {'/','e','n','a','b','l','e',0};
33 static const WCHAR f_optW[] = {'/','f',0};
34 static const WCHAR ru_optW[] = {'/','r','u',0};
35 static const WCHAR tn_optW[] = {'/','t','n',0};
36 static const WCHAR tr_optW[] = {'/','t','r',0};
37 static const WCHAR xml_optW[] = {'/','x','m','l',0};
38 
39 static ITaskFolder *get_tasks_root_folder(void)
40 {
41  ITaskService *service;
42  ITaskFolder *root;
43  VARIANT empty;
44  HRESULT hres;
45 
46  hres = CoCreateInstance(&CLSID_TaskScheduler, NULL, CLSCTX_INPROC_SERVER,
47  &IID_ITaskService, (void**)&service);
48  if (FAILED(hres))
49  return NULL;
50 
51  V_VT(&empty) = VT_EMPTY;
52  hres = ITaskService_Connect(service, empty, empty, empty, empty);
53  if (FAILED(hres)) {
54  FIXME("Connect failed: %08x\n", hres);
55  return NULL;
56  }
57 
58  hres = ITaskService_GetFolder(service, NULL, &root);
59  ITaskService_Release(service);
60  if (FAILED(hres)) {
61  FIXME("GetFolder failed: %08x\n", hres);
62  return NULL;
63  }
64 
65  return root;
66 }
67 
68 static IRegisteredTask *get_registered_task(const WCHAR *name)
69 {
70  IRegisteredTask *registered_task;
71  ITaskFolder *root;
72  BSTR str;
73  HRESULT hres;
74 
76  if (!root)
77  return NULL;
78 
80  hres = ITaskFolder_GetTask(root, str, &registered_task);
82  ITaskFolder_Release(root);
83  if (FAILED(hres)) {
84  FIXME("GetTask failed: %08x\n", hres);
85  return NULL;
86  }
87 
88  return registered_task;
89 }
90 
92 {
94  DWORD read_size, size;
95  unsigned char *data;
96  HANDLE file;
97  BOOL r = FALSE;
98  BSTR ret;
99 
102  if (file == INVALID_HANDLE_VALUE) {
103  FIXME("Could not open file\n");
104  return NULL;
105  }
106 
107  if (!GetFileSizeEx(file, &file_size) || !file_size.QuadPart) {
108  FIXME("Empty file\n");
109  CloseHandle(file);
110  return NULL;
111  }
112 
113  data = HeapAlloc(GetProcessHeap(), 0, file_size.QuadPart);
114  if (data)
115  r = ReadFile(file, data, file_size.QuadPart, &read_size, NULL);
116  CloseHandle(file);
117  if (!r) {
118  FIXME("Read filed\n");
120  return NULL;
121  }
122 
123  if (read_size > 2 && data[0] == 0xff && data[1] == 0xfe) { /* UTF-16 BOM */
124  ret = SysAllocStringLen((const WCHAR *)(data + 2), (read_size - 2) / sizeof(WCHAR));
125  }else {
126  size = MultiByteToWideChar(CP_ACP, 0, (const char *)data, read_size, NULL, 0);
128  if (ret)
129  MultiByteToWideChar(CP_ACP, 0, (const char *)data, read_size, ret, size);
130  }
132 
133  return ret;
134 }
135 
136 static int change_command(int argc, WCHAR *argv[])
137 {
138  BOOL have_option = FALSE, enable = FALSE;
139  const WCHAR *task_name = NULL;
140  IRegisteredTask *task;
141  HRESULT hres;
142 
143  while (argc) {
144  if(!strcmpiW(argv[0], tn_optW)) {
145  if (argc < 2) {
146  FIXME("Missing /tn value\n");
147  return 1;
148  }
149 
150  if (task_name) {
151  FIXME("Duplicated /tn argument\n");
152  return 1;
153  }
154 
155  task_name = argv[1];
156  argc -= 2;
157  argv += 2;
158  }else if (!strcmpiW(argv[0], enable_optW)) {
159  enable = TRUE;
160  have_option = TRUE;
161  argc--;
162  argv++;
163  }else if (!strcmpiW(argv[0], tr_optW)) {
164  if (argc < 2) {
165  FIXME("Missing /tr value\n");
166  return 1;
167  }
168 
169  FIXME("Unsupported /tr option %s\n", debugstr_w(argv[1]));
170  have_option = TRUE;
171  argc -= 2;
172  argv += 2;
173  }else {
174  FIXME("Unsupported arguments %s\n", debugstr_w(argv[0]));
175  return 1;
176  }
177  }
178 
179  if (!task_name) {
180  FIXME("Missing /tn option\n");
181  return 1;
182  }
183 
184  if (!have_option) {
185  FIXME("Missing change options\n");
186  return 1;
187  }
188 
189  task = get_registered_task(task_name);
190  if (!task)
191  return 1;
192 
193  if (enable) {
194  hres = IRegisteredTask_put_Enabled(task, VARIANT_TRUE);
195  if (FAILED(hres)) {
196  IRegisteredTask_Release(task);
197  FIXME("put_Enabled failed: %08x\n", hres);
198  return 1;
199  }
200  }
201 
202  IRegisteredTask_Release(task);
203  return 0;
204 }
205 
206 static int create_command(int argc, WCHAR *argv[])
207 {
208  const WCHAR *task_name = NULL, *xml_file = NULL;
209  ITaskFolder *root = NULL;
211  IRegisteredTask *task;
212  VARIANT empty;
213  BSTR str, xml;
214  HRESULT hres;
215 
216  while (argc) {
217  if (!strcmpiW(argv[0], xml_optW)) {
218  if (argc < 2) {
219  FIXME("Missing /xml value\n");
220  return 1;
221  }
222 
223  if (xml_file) {
224  FIXME("Duplicated /xml argument\n");
225  return 1;
226  }
227 
228  xml_file = argv[1];
229  argc -= 2;
230  argv += 2;
231  }else if(!strcmpiW(argv[0], tn_optW)) {
232  if (argc < 2) {
233  FIXME("Missing /tn value\n");
234  return 1;
235  }
236 
237  if (task_name) {
238  FIXME("Duplicated /tn argument\n");
239  return 1;
240  }
241 
242  task_name = argv[1];
243  argc -= 2;
244  argv += 2;
245  }else if(!strcmpiW(argv[0], f_optW)) {
247  argc--;
248  argv++;
249  }else if (!strcmpiW(argv[0], ru_optW)) {
250  if (argc < 2) {
251  FIXME("Missing /ru value\n");
252  return 1;
253  }
254 
255  FIXME("Unsupported /ru option %s\n", debugstr_w(argv[1]));
256  argc -= 2;
257  argv += 2;
258  }else {
259  FIXME("Unsupported argument %s\n", debugstr_w(argv[0]));
260  return 1;
261  }
262  }
263 
264  if (!task_name) {
265  FIXME("Missing /tn argument\n");
266  return 1;
267  }
268 
269  if (!xml_file) {
270  FIXME("Missing /xml argument\n");
271  return E_FAIL;
272  }
273 
274  xml = read_file_to_bstr(xml_file);
275  if (!xml)
276  return 1;
277 
279  if (!root) {
280  SysFreeString(xml);
281  return 1;
282  }
283 
284  V_VT(&empty) = VT_EMPTY;
285  str = SysAllocString(task_name);
286  hres = ITaskFolder_RegisterTask(root, str, xml, flags, empty, empty,
287  TASK_LOGON_NONE, empty, &task);
289  SysFreeString(xml);
290  ITaskFolder_Release(root);
291  if (FAILED(hres))
292  return 1;
293 
294  IRegisteredTask_Release(task);
295  return 0;
296 }
297 
298 static int delete_command(int argc, WCHAR *argv[])
299 {
300  const WCHAR *task_name = NULL;
301  ITaskFolder *root = NULL;
302  BSTR str;
303  HRESULT hres;
304 
305  while (argc) {
306  if (!strcmpiW(argv[0], f_optW)) {
307  TRACE("force opt\n");
308  argc--;
309  argv++;
310  }else if(!strcmpiW(argv[0], tn_optW)) {
311  if (argc < 2) {
312  FIXME("Missing /tn value\n");
313  return 1;
314  }
315 
316  if (task_name) {
317  FIXME("Duplicated /tn argument\n");
318  return 1;
319  }
320 
321  task_name = argv[1];
322  argc -= 2;
323  argv += 2;
324  }else {
325  FIXME("Unsupported argument %s\n", debugstr_w(argv[0]));
326  return 1;
327  }
328  }
329 
330  if (!task_name) {
331  FIXME("Missing /tn argument\n");
332  return 1;
333  }
334 
336  if (!root)
337  return 1;
338 
339  str = SysAllocString(task_name);
340  hres = ITaskFolder_DeleteTask(root, str, 0);
342  ITaskFolder_Release(root);
343  if (FAILED(hres))
344  return 1;
345 
346  return 0;
347 }
348 
349 int wmain(int argc, WCHAR *argv[])
350 {
351  int i, ret = 0;
352 
353  for (i = 0; i < argc; i++)
354  TRACE(" %s", wine_dbgstr_w(argv[i]));
355  TRACE("\n");
356 
358 
359  if (argc < 2)
360  FIXME("Print current tasks state\n");
361  else if (!strcmpiW(argv[1], change_optW))
362  ret = change_command(argc - 2, argv + 2);
363  else if (!strcmpiW(argv[1], create_optW))
364  ret = create_command(argc - 2, argv + 2);
365  else if (!strcmpiW(argv[1], delete_optW))
366  ret = delete_command(argc - 2, argv + 2);
367  else
368  FIXME("Unsupported command %s\n", debugstr_w(argv[1]));
369 
370  CoUninitialize();
371  return ret;
372 }
static const WCHAR ru_optW[]
Definition: schtasks.c:34
static int argc
Definition: ServiceArgs.c:12
#define TRUE
Definition: types.h:120
#define CloseHandle
Definition: compat.h:406
BSTR WINAPI SysAllocStringLen(const OLECHAR *str, unsigned int len)
Definition: oleaut.c:342
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
char * wine_dbgstr_w(const wchar_t *wstr)
Definition: atltest.h:87
#define CP_ACP
Definition: compat.h:99
struct _root root
static const WCHAR enable_optW[]
Definition: schtasks.c:32
#define INVALID_HANDLE_VALUE
Definition: compat.h:399
static const WCHAR xml_optW[]
Definition: schtasks.c:37
int wmain(int argc, WCHAR *argv[])
Definition: schtasks.c:349
OLECHAR * BSTR
Definition: compat.h:1942
#define argv
Definition: mplay32.c:18
#define E_FAIL
Definition: ddrawi.h:102
#define FILE_SHARE_READ
Definition: compat.h:125
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
unsigned int BOOL
Definition: ntddk_ex.h:94
long LONG
Definition: pedump.c:60
#define debugstr_w
Definition: kernel32.h:32
#define FIXME(fmt,...)
Definition: debug.h:110
const WCHAR * str
smooth NULL
Definition: ftsmooth.c:416
BSTR WINAPI SysAllocString(LPCOLESTR str)
Definition: oleaut.c:241
static const WCHAR change_optW[]
Definition: schtasks.c:29
static const WCHAR tr_optW[]
Definition: schtasks.c:36
#define OPEN_EXISTING
Definition: compat.h:434
static ITaskFolder * get_tasks_root_folder(void)
Definition: schtasks.c:39
#define TRACE(s)
Definition: solgame.cpp:4
GLsizeiptr size
Definition: glext.h:5919
HRESULT hres
Definition: protocol.c:465
#define GetProcessHeap()
Definition: compat.h:403
PVOID WINAPI HeapAlloc(HANDLE, DWORD, SIZE_T)
WINE_DEFAULT_DEBUG_CHANNEL(schtasks)
__wchar_t WCHAR
Definition: xmlstorage.h:180
LONG HRESULT
Definition: typedefs.h:77
const char file[]
Definition: icontest.c:11
unsigned long DWORD
Definition: ntddk_ex.h:95
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLbitfield flags
Definition: glext.h:7161
#define GetFileSizeEx
Definition: compat.h:422
int ret
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:126
#define V_VT(A)
Definition: oleauto.h:211
static int delete_command(int argc, WCHAR *argv[])
Definition: schtasks.c:298
#define GENERIC_READ
Definition: compat.h:124
static const WCHAR create_optW[]
Definition: schtasks.c:30
#define strcmpiW(s1, s2)
Definition: unicode.h:39
HRESULT WINAPI DECLSPEC_HOTPATCH CoCreateInstance(REFCLSID rclsid, LPUNKNOWN pUnkOuter, DWORD dwClsContext, REFIID iid, LPVOID *ppv)
Definition: compobj.c:3325
static const WCHAR f_optW[]
Definition: schtasks.c:33
GLboolean enable
Definition: glext.h:11120
void WINAPI DECLSPEC_HOTPATCH CoUninitialize(void)
Definition: compobj.c:2067
static IRegisteredTask * get_registered_task(const WCHAR *name)
Definition: schtasks.c:68
void WINAPI DECLSPEC_HOTPATCH SysFreeString(BSTR str)
Definition: oleaut.c:274
BOOL empty
Definition: button.c:170
#define MultiByteToWideChar
Definition: compat.h:100
static LPCWSTR file_name
Definition: protocol.c:146
#define CreateFileW
Definition: compat.h:408
HRESULT WINAPI CoInitialize(LPVOID lpReserved)
Definition: compobj.c:1964
Definition: name.c:36
static int change_command(int argc, WCHAR *argv[])
Definition: schtasks.c:136
static const WCHAR delete_optW[]
Definition: schtasks.c:31
static BSTR read_file_to_bstr(const WCHAR *file_name)
Definition: schtasks.c:91
BOOL WINAPI ReadFile(IN HANDLE hFile, IN LPVOID lpBuffer, IN DWORD nNumberOfBytesToRead, OUT LPDWORD lpNumberOfBytesRead OPTIONAL, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:123
#define HeapFree(x, y, z)
Definition: compat.h:402
static const WCHAR tn_optW[]
Definition: schtasks.c:35
#define file_size(inode)
Definition: reiserfs_fs.h:1869
static int create_command(int argc, WCHAR *argv[])
Definition: schtasks.c:206
Definition: fci.c:126