winspool: Add a test for DocumentProperties.
[wine] / dlls / winspool / tests / info.c
1 /*
2  * Copyright (C) 2003, 2004 Stefan Leichter
3  * Copyright (C) 2005, 2006 Detlef Riekenberg
4  * Copyright (C) 2006 Dmitry Timoshkov
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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  */
20
21 #include <stdarg.h>
22
23 #include "wine/test.h"
24 #include "windef.h"
25 #include "winbase.h"
26 #include "winerror.h"
27 #include "wingdi.h"
28 #include "winuser.h"
29 #include "winreg.h"
30 #include "winspool.h"
31
32 #define MAGIC_DEAD  0x00dead00
33 #define DEFAULT_PRINTER_SIZE 1000
34
35 static char env_x86[] = "Windows NT x86";
36 static char env_win9x_case[] = "windowS 4.0";
37 static char winetest_monitor[] = "winetest";
38
39 static HANDLE  hwinspool;
40 static FARPROC pGetDefaultPrinterA;
41 static FARPROC pSetDefaultPrinterA;
42
43 struct monitor_entry {
44     LPSTR  env;
45     LPSTR  dllname;
46 };
47
48 /* report common behavior only once */
49 static DWORD report_deactivated_spooler = 1;
50 #define RETURN_ON_DEACTIVATED_SPOOLER(res) \
51     if((res == 0) && (GetLastError() == RPC_S_SERVER_UNAVAILABLE)) \
52     { \
53         if(report_deactivated_spooler > 0) { \
54             report_deactivated_spooler--; \
55             trace("The Service 'Spooler' is required for many test\n"); \
56         } \
57         return; \
58     }
59
60
61 static LPSTR find_default_printer(VOID)
62 {
63     static  LPSTR   default_printer = NULL;
64     static  char    buffer[DEFAULT_PRINTER_SIZE];
65     DWORD   needed;
66     DWORD   res;
67     LPSTR   ptr;
68
69     if ((default_printer == NULL) && (pGetDefaultPrinterA))
70     {
71         /* w2k and above */
72         needed = sizeof(buffer);
73         res = pGetDefaultPrinterA(buffer, &needed);
74         if(res)  default_printer = buffer;
75         trace("default_printer: '%s'\n", default_printer);
76     }
77     if (default_printer == NULL)
78     {
79         HKEY hwindows;
80         DWORD   type;
81         /* NT 3.x and above */
82         if (RegOpenKeyEx(HKEY_CURRENT_USER, 
83                         "Software\\Microsoft\\Windows NT\\CurrentVersion\\Windows",
84                         0, KEY_QUERY_VALUE, &hwindows) == NO_ERROR) {
85
86             needed = sizeof(buffer);
87             if (RegQueryValueEx(hwindows, "device", NULL, 
88                                 &type, (LPBYTE)buffer, &needed) == NO_ERROR) {
89
90                 ptr = strchr(buffer, ',');
91                 if (ptr) {
92                     ptr[0] = '\0';
93                     default_printer = buffer;
94                 }
95             }
96             RegCloseKey(hwindows);
97         }
98         trace("default_printer: '%s'\n", default_printer);
99     }
100     if (default_printer == NULL)
101     {
102         /* win9x */
103         needed = sizeof(buffer);
104         res = GetProfileStringA("windows", "device", "*", buffer, needed);
105         if(res) {
106             ptr = strchr(buffer, ',');
107             if (ptr) {
108                 ptr[0] = '\0';
109                 default_printer = buffer;
110             }
111         }
112         trace("default_printer: '%s'\n", default_printer);
113     }
114     return default_printer;
115 }
116
117
118 static struct monitor_entry * find_installed_monitor(void)
119 {
120     MONITOR_INFO_2A mi2a; 
121     static struct  monitor_entry * entry = NULL;
122     DWORD   res;
123     DWORD   num_tests;
124     DWORD   i = 0;
125
126     static struct monitor_entry  monitor_table[] = {
127         {env_win9x_case, "localspl.dll"},
128         {env_x86,        "localspl.dll"},
129         {env_win9x_case, "localmon.dll"},
130         {env_x86,        "localmon.dll"},
131         {env_win9x_case, "tcpmon.dll"},
132         {env_x86,        "tcpmon.dll"},
133         {env_win9x_case, "usbmon.dll"},
134         {env_x86,        "usbmon.dll"},
135         {env_win9x_case, "mspp32.dll"},
136         {env_x86,        "win32spl.dll"},
137         {env_x86,        "redmonnt.dll"},
138         {env_x86,        "redmon35.dll"},
139         {env_win9x_case, "redmon95.dll"},
140         {env_x86,        "pdfcmnnt.dll"},
141         {env_win9x_case, "pdfcmn95.dll"},
142     };
143
144     if (entry) return entry;
145
146     num_tests = (sizeof(monitor_table)/sizeof(struct monitor_entry));
147
148     SetLastError(MAGIC_DEAD);
149     res = DeleteMonitorA(NULL, NULL, NULL);
150     if (!res && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)) {
151         trace("DeleteMonitorA() not implemented yet\n");
152         return NULL;
153     }
154
155     SetLastError(MAGIC_DEAD);
156     res = AddMonitorA(NULL, 0, NULL);
157     if (!res && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)) {
158         trace("AddMonitorA() not implemented yet\n");
159         return NULL;
160     }
161
162     /* cleanup */
163     DeleteMonitorA(NULL, env_x86, winetest_monitor);
164     DeleteMonitorA(NULL, env_win9x_case, winetest_monitor);
165
166     /* find a usable monitor from the table */    
167     mi2a.pName = winetest_monitor;
168     while ((entry == NULL) && (i < num_tests)) {
169         entry = &monitor_table[i];
170         i++;
171         mi2a.pEnvironment = entry->env;
172         mi2a.pDLLName = entry->dllname;
173
174         if (AddMonitorA(NULL, 2, (LPBYTE) &mi2a)) {
175             /* we got one */
176             trace("using '%s', '%s'\n", entry->env, entry->dllname);
177             DeleteMonitorA(NULL, entry->env, winetest_monitor);
178         }
179         else
180         {
181             entry = NULL;
182         }
183     }
184     return entry;
185 }
186
187 /* ########################### */
188
189
190 static void test_AddMonitor(void)
191 {
192     MONITOR_INFO_2A mi2a; 
193     struct  monitor_entry * entry = NULL;
194     DWORD   res;
195
196     entry = find_installed_monitor();
197
198     SetLastError(MAGIC_DEAD);
199     res = AddMonitorA(NULL, 1, NULL);
200     ok(!res && (GetLastError() == ERROR_INVALID_LEVEL), 
201         "returned %ld with %ld (expected '0' with ERROR_INVALID_LEVEL)\n",
202         res, GetLastError());
203
204     SetLastError(MAGIC_DEAD);
205     res = AddMonitorA(NULL, 3, NULL);
206     ok(!res && (GetLastError() == ERROR_INVALID_LEVEL), 
207         "returned %ld with %ld (expected '0' with ERROR_INVALID_LEVEL)\n",
208         res, GetLastError());
209
210     SetLastError(MAGIC_DEAD);
211     res = AddMonitorA(NULL, 2, NULL);
212     /* NT: unchanged,  9x: ERROR_PRIVILEGE_NOT_HELD */
213     ok(!res &&
214         ((GetLastError() == MAGIC_DEAD) ||
215          (GetLastError() == ERROR_PRIVILEGE_NOT_HELD)), 
216         "returned %ld with %ld (expected '0' with: MAGIC_DEAD or " \
217         "ERROR_PRIVILEGE_NOT_HELD)\n", res, GetLastError());
218
219     ZeroMemory(&mi2a, sizeof(MONITOR_INFO_2A));
220     SetLastError(MAGIC_DEAD);
221     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
222     RETURN_ON_DEACTIVATED_SPOOLER(res)
223
224     if (!res && (GetLastError() == ERROR_ACCESS_DENIED)) {
225         trace("skip tests (ACCESS_DENIED)\n");
226         return;
227     }
228
229     /* NT: ERROR_INVALID_PARAMETER,  9x: ERROR_INVALID_ENVIRONMENT */
230     ok(!res && ((GetLastError() == ERROR_INVALID_PARAMETER) ||
231                 (GetLastError() == ERROR_INVALID_ENVIRONMENT)), 
232         "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or " \
233         "ERROR_INVALID_ENVIRONMENT)\n", res, GetLastError());
234
235     if (!entry) {
236         trace("No usable Monitor found: Skip tests\n");
237         return;
238     }
239
240 #if 0
241     /* The Test is deactivated, because when mi2a.pName is NULL, the subkey
242        HKLM\System\CurrentControlSet\Control\Print\Monitors\C:\WINDOWS\SYSTEM
243        or HKLM\System\CurrentControlSet\Control\Print\Monitors\ì
244        is created on win9x and we do not want to hit this bug here. */
245
246     mi2a.pEnvironment = entry->env;
247     SetLastError(MAGIC_DEAD);
248     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
249     /* NT: ERROR_INVALID_PARAMETER,  9x: ERROR_PRIVILEGE_NOT_HELD */
250 #endif
251
252     mi2a.pEnvironment = entry->env;
253     mi2a.pName = "";
254     SetLastError(MAGIC_DEAD);
255     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
256     /* NT: ERROR_INVALID_PARAMETER,  9x: ERROR_PRIVILEGE_NOT_HELD */
257     ok( !res &&
258         ((GetLastError() == ERROR_INVALID_PARAMETER) ||
259          (GetLastError() == ERROR_PRIVILEGE_NOT_HELD)), 
260         "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or " \
261         "ERROR_PRIVILEGE_NOT_HELD)\n",
262         res, GetLastError());
263
264     mi2a.pName = winetest_monitor;
265     SetLastError(MAGIC_DEAD);
266     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
267     /* NT: ERROR_INVALID_PARAMETER,  9x: ERROR_PRIVILEGE_NOT_HELD */
268     ok( !res &&
269         ((GetLastError() == ERROR_INVALID_PARAMETER) ||
270          (GetLastError() == ERROR_PRIVILEGE_NOT_HELD)), 
271         "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or " \
272         "ERROR_PRIVILEGE_NOT_HELD)\n",
273         res, GetLastError());
274
275     mi2a.pDLLName = "";
276     SetLastError(MAGIC_DEAD);
277     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
278     ok( !res && (GetLastError() == ERROR_INVALID_PARAMETER),
279         "returned %ld with %ld (expected '0' with ERROR_INVALID_PARAMETER)\n",
280         res, GetLastError());
281
282
283     mi2a.pDLLName = "does_not_exists.dll";
284     SetLastError(MAGIC_DEAD);
285     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
286     /* NT: ERROR_MOD_NOT_FOUND,  9x: ERROR_INVALID_PARAMETER */
287     ok( !res &&
288         ((GetLastError() == ERROR_MOD_NOT_FOUND) ||
289         (GetLastError() == ERROR_INVALID_PARAMETER)),
290         "returned %ld with %ld (expected '0' with: ERROR_MOD_NOT_FOUND or " \
291         "ERROR_INVALID_PARAMETER)\n", res, GetLastError());
292
293     mi2a.pDLLName = "version.dll";
294     SetLastError(MAGIC_DEAD);
295     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
296     /* NT: ERROR_PROC_NOT_FOUND,  9x: ERROR_INVALID_PARAMETER */
297     todo_wine {
298     ok( !res &&
299         ((GetLastError() == ERROR_PROC_NOT_FOUND) ||
300         (GetLastError() == ERROR_INVALID_PARAMETER)),
301         "returned %ld with %ld (expected '0' with: ERROR_PROC_NOT_FOUND or " \
302         "ERROR_INVALID_PARAMETER)\n", res, GetLastError());
303     if (res) DeleteMonitorA(NULL, entry->env, winetest_monitor); 
304     }
305
306    /* Test AddMonitor with real options */
307     mi2a.pDLLName = entry->dllname;
308     SetLastError(MAGIC_DEAD);
309     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
310     ok(res, "returned %ld with %ld (expected '!= 0')\n", res, GetLastError());
311     
312     /* add a monitor twice */
313     SetLastError(MAGIC_DEAD);
314     res = AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
315     /* NT: ERROR_PRINT_MONITOR_ALREADY_INSTALLED (3006), 9x: ERROR_ALREADY_EXISTS (183) */
316     ok( !res &&
317         ((GetLastError() == ERROR_PRINT_MONITOR_ALREADY_INSTALLED) ||
318         (GetLastError() == ERROR_ALREADY_EXISTS)), 
319         "returned %ld with %ld (expected '0' with: " \
320         "ERROR_PRINT_MONITOR_ALREADY_INSTALLED or ERROR_ALREADY_EXISTS)\n",
321         res, GetLastError());
322
323     DeleteMonitorA(NULL, entry->env, winetest_monitor); 
324     SetLastError(MAGIC_DEAD);
325     res = AddMonitorA("", 2, (LPBYTE) &mi2a);
326     ok(res, "returned %ld with %ld (expected '!= 0')\n", res, GetLastError());
327
328     /* cleanup */
329     DeleteMonitorA(NULL, entry->env, winetest_monitor);
330
331 }
332
333 /* ########################### */
334
335 static void test_DeleteMonitor(void)
336 {
337     MONITOR_INFO_2A mi2a; 
338     struct  monitor_entry * entry = NULL;
339     DWORD   res;
340
341     entry = find_installed_monitor();
342
343     if (!entry) {
344         trace("No usable Monitor found: Skip tests\n");
345         return;
346     }
347
348     mi2a.pName = winetest_monitor;
349     mi2a.pEnvironment = entry->env;
350     mi2a.pDLLName = entry->dllname;
351
352     /* Testing DeleteMonitor with real options */
353     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
354
355     SetLastError(MAGIC_DEAD);
356     res = DeleteMonitorA(NULL, entry->env, winetest_monitor);
357     ok(res, "returned %ld with %ld (expected '!= 0')\n", res, GetLastError());
358
359     /* Delete the Monitor twice */
360     SetLastError(MAGIC_DEAD);
361     res = DeleteMonitorA(NULL, entry->env, winetest_monitor);
362     /* NT: ERROR_UNKNOWN_PRINT_MONITOR (3000), 9x: ERROR_INVALID_PARAMETER (87) */
363     ok( !res &&
364         ((GetLastError() == ERROR_UNKNOWN_PRINT_MONITOR) ||
365         (GetLastError() == ERROR_INVALID_PARAMETER)), 
366         "returned %ld with %ld (expected '0' with: ERROR_UNKNOWN_PRINT_MONITOR" \
367         " or ERROR_INVALID_PARAMETER)\n", res, GetLastError());
368
369     /* the environment */
370     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
371     SetLastError(MAGIC_DEAD);
372     res = DeleteMonitorA(NULL, NULL, winetest_monitor);
373     ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
374
375     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
376     SetLastError(MAGIC_DEAD);
377     res = DeleteMonitorA(NULL, "", winetest_monitor);
378     ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
379
380     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
381     SetLastError(MAGIC_DEAD);
382     res = DeleteMonitorA(NULL, "bad_env", winetest_monitor);
383     ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
384
385     /* the monitor-name */
386     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
387     SetLastError(MAGIC_DEAD);
388     res = DeleteMonitorA(NULL, entry->env, NULL);
389     /* NT: ERROR_INVALID_PARAMETER (87),  9x: ERROR_INVALID_NAME (123)*/
390     ok( !res &&
391         ((GetLastError() == ERROR_INVALID_PARAMETER) ||
392         (GetLastError() == ERROR_INVALID_NAME)),
393         "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or " \
394         "ERROR_INVALID_NAME)\n", res, GetLastError());
395
396     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
397     SetLastError(MAGIC_DEAD);
398     res = DeleteMonitorA(NULL, entry->env, "");
399     /* NT: ERROR_INVALID_PARAMETER (87),  9x: ERROR_INVALID_NAME (123)*/
400     ok( !res && 
401         ((GetLastError() == ERROR_INVALID_PARAMETER) ||
402         (GetLastError() == ERROR_INVALID_NAME)),
403         "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or " \
404         "ERROR_INVALID_NAME)\n", res, GetLastError());
405
406     AddMonitorA(NULL, 2, (LPBYTE) &mi2a);
407     SetLastError(MAGIC_DEAD);
408     res = DeleteMonitorA("", entry->env, winetest_monitor);
409     ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
410
411     /* cleanup */
412     DeleteMonitorA(NULL, entry->env, winetest_monitor);
413 }
414
415
416 /* ########################### */
417
418 static void test_EnumMonitors(void)
419 {
420     DWORD   res;
421     LPBYTE  buffer;
422     DWORD   cbBuf;
423     DWORD   pcbNeeded;
424     DWORD   pcReturned;
425     DWORD   level;
426
427     /* valid levels are 1 and 2 */
428     for(level = 0; level < 4; level++) {
429         cbBuf = MAGIC_DEAD;
430         pcReturned = MAGIC_DEAD;
431         SetLastError(MAGIC_DEAD);
432         res = EnumMonitorsA(NULL, level, NULL, 0, &cbBuf, &pcReturned);
433
434         RETURN_ON_DEACTIVATED_SPOOLER(res)
435
436         /* not implemented yet in wine */
437         if (!res && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)) continue;
438
439
440         /* use only a short test, when we test with an invalid level */
441         if(!level || (level > 2)) {
442             ok( (!res && (GetLastError() == ERROR_INVALID_LEVEL)) ||
443                 (res && (pcReturned == 0)),
444                 "(%ld) returned %ld with %ld and 0x%08lx (expected '0' with " \
445                 "ERROR_INVALID_LEVEL or '!=0' and 0x0)\n",
446                 level, res, GetLastError(), pcReturned);
447             continue;
448         }        
449
450         /* Level 2 is not supported on win9x */
451         if (!res && (GetLastError() == ERROR_INVALID_LEVEL)) {
452             trace("Level %ld not supported, skipping tests\n", level);
453             continue;
454         }
455
456         ok((!res) && (GetLastError() == ERROR_INSUFFICIENT_BUFFER),
457             "(%ld) returned %ld with %ld (expected '0' with " \
458             "ERROR_INSUFFICIENT_BUFFER)\n", level, res, GetLastError());
459
460         if (!cbBuf) {
461             trace("no valid buffer size returned, skipping tests\n");
462             continue;
463         }
464
465         buffer = HeapAlloc(GetProcessHeap(), 0, cbBuf *2);
466         if (buffer == NULL) continue;
467
468         SetLastError(MAGIC_DEAD);
469         pcbNeeded = MAGIC_DEAD;
470         res = EnumMonitorsA(NULL, level, buffer, cbBuf, &pcbNeeded, &pcReturned);
471         ok(res, "(%ld) returned %ld with %ld (expected '!=0')\n",
472                 level, res, GetLastError());
473         ok(pcbNeeded == cbBuf, "(%ld) returned %ld (expected %ld)\n",
474                 level, pcbNeeded, cbBuf);
475         /* We can validate the returned Data with the Registry here */
476
477
478         SetLastError(MAGIC_DEAD);
479         pcReturned = MAGIC_DEAD;
480         pcbNeeded = MAGIC_DEAD;
481         res = EnumMonitorsA(NULL, level, buffer, cbBuf+1, &pcbNeeded, &pcReturned);
482         ok(res, "(%ld) returned %ld with %ld (expected '!=0')\n", level,
483                 res, GetLastError());
484         ok(pcbNeeded == cbBuf, "(%ld) returned %ld (expected %ld)\n", level,
485                 pcbNeeded, cbBuf);
486
487         SetLastError(MAGIC_DEAD);
488         pcbNeeded = MAGIC_DEAD;
489         res = EnumMonitorsA(NULL, level, buffer, cbBuf-1, &pcbNeeded, &pcReturned);
490         ok( !res && (GetLastError() == ERROR_INSUFFICIENT_BUFFER),
491             "(%ld) returned %ld with %ld (expected '0' with " \
492             "ERROR_INSUFFICIENT_BUFFER)\n", level, res, GetLastError());
493
494         ok(pcbNeeded == cbBuf, "(%ld) returned %ld (expected %ld)\n", level,
495                 pcbNeeded, cbBuf);
496
497 /*
498       Do not add the next test:
499       w2k+:  RPC_X_NULL_REF_POINTER 
500       NT3.5: ERROR_INVALID_USER_BUFFER
501       win9x: crash in winspool.drv
502
503       res = EnumMonitorsA(NULL, level, NULL, cbBuf, &pcbNeeded, &pcReturned);
504 */
505
506         SetLastError(MAGIC_DEAD);
507         pcbNeeded = MAGIC_DEAD;
508         pcReturned = MAGIC_DEAD;
509         res = EnumMonitorsA(NULL, level, buffer, cbBuf, NULL, &pcReturned);
510         ok( res || (!res && (GetLastError() == RPC_X_NULL_REF_POINTER)) ,
511             "(%ld) returned %ld with %ld (expected '!=0' or '0' with "\
512             "RPC_X_NULL_REF_POINTER)\n", level, res, GetLastError());
513
514         pcbNeeded = MAGIC_DEAD;
515         pcReturned = MAGIC_DEAD;
516         SetLastError(MAGIC_DEAD);
517         res = EnumMonitorsA(NULL, level, buffer, cbBuf, &pcbNeeded, NULL);
518         ok( res || (!res && (GetLastError() == RPC_X_NULL_REF_POINTER)) ,
519             "(%ld) returned %ld with %ld (expected '!=0' or '0' with "\
520             "RPC_X_NULL_REF_POINTER)\n", level, res, GetLastError());
521
522         HeapFree(GetProcessHeap(), 0, buffer);
523     } /* for(level ... */
524 }
525
526
527 static void test_GetDefaultPrinter(void)
528 {
529     BOOL    retval;
530     DWORD   exact = DEFAULT_PRINTER_SIZE;
531     DWORD   size;
532     char    buffer[DEFAULT_PRINTER_SIZE];
533
534     if (!pGetDefaultPrinterA)  return;
535         /* only supported on NT like OSes starting with win2k */
536
537     SetLastError(ERROR_SUCCESS);
538     retval = pGetDefaultPrinterA(buffer, &exact);
539     if (!retval || !exact || !strlen(buffer) ||
540         (ERROR_SUCCESS != GetLastError())) {
541         if ((ERROR_FILE_NOT_FOUND == GetLastError()) ||
542             (ERROR_INVALID_NAME == GetLastError()))
543             trace("this test requires a default printer to be set\n");
544         else {
545                 ok( 0, "function call GetDefaultPrinterA failed unexpected!\n"
546                 "function returned %s\n"
547                 "last error 0x%08lx\n"
548                 "returned buffer size 0x%08lx\n"
549                 "returned buffer content %s\n",
550                 retval ? "true" : "false", GetLastError(), exact, buffer);
551         }
552         return;
553     }
554     SetLastError(ERROR_SUCCESS);
555     retval = pGetDefaultPrinterA(NULL, NULL); 
556     ok( !retval, "function result wrong! False expected\n");
557     ok( ERROR_INVALID_PARAMETER == GetLastError(),
558         "Last error wrong! ERROR_INVALID_PARAMETER expected, got 0x%08lx\n",
559         GetLastError());
560
561     SetLastError(ERROR_SUCCESS);
562     retval = pGetDefaultPrinterA(buffer, NULL); 
563     ok( !retval, "function result wrong! False expected\n");
564     ok( ERROR_INVALID_PARAMETER == GetLastError(),
565         "Last error wrong! ERROR_INVALID_PARAMETER expected, got 0x%08lx\n",
566         GetLastError());
567
568     SetLastError(ERROR_SUCCESS);
569     size = 0;
570     retval = pGetDefaultPrinterA(NULL, &size); 
571     ok( !retval, "function result wrong! False expected\n");
572     ok( ERROR_INSUFFICIENT_BUFFER == GetLastError(),
573         "Last error wrong! ERROR_INSUFFICIENT_BUFFER expected, got 0x%08lx\n",
574         GetLastError());
575     ok( size == exact, "Parameter size wrong! %ld expected got %ld\n",
576         exact, size);
577
578     SetLastError(ERROR_SUCCESS);
579     size = DEFAULT_PRINTER_SIZE;
580     retval = pGetDefaultPrinterA(NULL, &size); 
581     ok( !retval, "function result wrong! False expected\n");
582     ok( ERROR_INSUFFICIENT_BUFFER == GetLastError(),
583         "Last error wrong! ERROR_INSUFFICIENT_BUFFER expected, got 0x%08lx\n",
584         GetLastError());
585     ok( size == exact, "Parameter size wrong! %ld expected got %ld\n",
586         exact, size);
587
588     size = 0;
589     retval = pGetDefaultPrinterA(buffer, &size); 
590     ok( !retval, "function result wrong! False expected\n");
591     ok( ERROR_INSUFFICIENT_BUFFER == GetLastError(),
592         "Last error wrong! ERROR_INSUFFICIENT_BUFFER expected, got 0x%08lx\n",
593         GetLastError());
594     ok( size == exact, "Parameter size wrong! %ld expected got %ld\n",
595         exact, size);
596
597     size = exact;
598     retval = pGetDefaultPrinterA(buffer, &size); 
599     ok( retval, "function result wrong! True expected\n");
600     ok( size == exact, "Parameter size wrong! %ld expected got %ld\n",
601         exact, size);
602 }
603
604 static void test_GetPrinterDriverDirectory(void)
605 {
606     LPBYTE buffer = NULL;
607     DWORD  cbBuf = 0, pcbNeeded = 0;
608     BOOL   res;
609
610     SetLastError(MAGIC_DEAD);
611     res = GetPrinterDriverDirectoryA( NULL, NULL, 1, NULL, 0, &cbBuf);
612     trace("first call returned 0x%04x, with %ld: buffer size 0x%08lx\n",
613     res, GetLastError(), cbBuf);
614
615     RETURN_ON_DEACTIVATED_SPOOLER(res)
616     ok((res == 0) && (GetLastError() == ERROR_INSUFFICIENT_BUFFER),
617         "returned %d with lasterror=%ld (expected '0' with " \
618         "ERROR_INSUFFICIENT_BUFFER)\n", res, GetLastError());
619
620     if (!cbBuf) {
621         trace("no valid buffer size returned, skipping tests\n");
622         return;
623     }
624
625     buffer = HeapAlloc( GetProcessHeap(), 0, cbBuf*2);
626     if (buffer == NULL)  return ;
627
628     res = GetPrinterDriverDirectoryA(NULL, NULL, 1, buffer, cbBuf, &pcbNeeded);
629     ok( res, "expected result != 0, got %d\n", res);
630     ok( cbBuf == pcbNeeded, "pcbNeeded set to %ld instead of %ld\n",
631                             pcbNeeded, cbBuf);
632
633     res = GetPrinterDriverDirectoryA(NULL, NULL, 1, buffer, cbBuf*2, &pcbNeeded);
634     ok( res, "expected result != 0, got %d\n", res);
635     ok( cbBuf == pcbNeeded, "pcbNeeded set to %ld instead of %ld\n",
636                             pcbNeeded, cbBuf);
637  
638     SetLastError(MAGIC_DEAD);
639     res = GetPrinterDriverDirectoryA( NULL, NULL, 1, buffer, cbBuf-1, &pcbNeeded);
640     ok( !res , "expected result == 0, got %d\n", res);
641     ok( cbBuf == pcbNeeded, "pcbNeeded set to %ld instead of %ld\n",
642                             pcbNeeded, cbBuf);
643     
644     ok( ERROR_INSUFFICIENT_BUFFER == GetLastError(),
645         "last error set to %ld instead of ERROR_INSUFFICIENT_BUFFER\n",
646         GetLastError());
647
648 /*
649     Do not add the next test:
650     XPsp2: crash in this app, when the spooler is not running 
651     NT3.5: ERROR_INVALID_USER_BUFFER
652     win9x: ERROR_INVALID_PARAMETER
653
654     pcbNeeded = MAGIC_DEAD;
655     SetLastError(MAGIC_DEAD);
656     res = GetPrinterDriverDirectoryA( NULL, NULL, 1, NULL, cbBuf, &pcbNeeded);
657 */
658
659     SetLastError(MAGIC_DEAD);
660     res = GetPrinterDriverDirectoryA( NULL, NULL, 1, buffer, cbBuf, NULL);
661     ok( (!res && RPC_X_NULL_REF_POINTER == GetLastError()) || res,
662          "expected either result == 0 and "
663          "last error == RPC_X_NULL_REF_POINTER or result != 0 "
664          "got result %d and last error == %ld\n", res, GetLastError());
665
666     SetLastError(MAGIC_DEAD);
667     res = GetPrinterDriverDirectoryA( NULL, NULL, 1, NULL, cbBuf, NULL);
668     ok(res || (GetLastError() == RPC_X_NULL_REF_POINTER),
669         "returned %d with %ld (expected '!=0' or '0' with " \
670         "RPC_X_NULL_REF_POINTER)\n", res, GetLastError());
671  
672  
673     /* with a valid buffer, but level is too large */
674     buffer[0] = '\0';
675     SetLastError(MAGIC_DEAD);
676     res = GetPrinterDriverDirectoryA(NULL, NULL, 2, buffer, cbBuf, &pcbNeeded);
677
678     /* Level not checked in win9x and wine:*/
679     if((res != FALSE) && buffer[0])
680     {
681         trace("Level '2' not checked '%s'\n", buffer);
682     }
683     else
684     {
685         ok( !res && (GetLastError() == ERROR_INVALID_LEVEL),
686         "returned %d with lasterror=%ld (expected '0' with " \
687         "ERROR_INVALID_LEVEL)\n", res, GetLastError());
688     }
689
690     /* printing environments are case insensitive */
691     /* "Windows 4.0" is valid for win9x and NT */
692     buffer[0] = '\0';
693     SetLastError(MAGIC_DEAD);
694     res = GetPrinterDriverDirectoryA(NULL, env_win9x_case, 1, 
695                                         buffer, cbBuf*2, &pcbNeeded);
696
697     if(!res && (GetLastError() == ERROR_INSUFFICIENT_BUFFER)) {
698         cbBuf = pcbNeeded;
699         buffer = HeapReAlloc(GetProcessHeap(), 0, buffer, cbBuf*2);
700         if (buffer == NULL)  return ;
701
702         SetLastError(MAGIC_DEAD);
703         res = GetPrinterDriverDirectoryA(NULL, env_win9x_case, 1, 
704                                         buffer, cbBuf*2, &pcbNeeded);
705     }
706
707     ok(res && buffer[0], "returned %d with " \
708         "lasterror=%ld and len=%d (expected '1' with 'len > 0')\n", 
709         res, GetLastError(), lstrlenA((char *)buffer));
710
711     buffer[0] = '\0';
712     SetLastError(MAGIC_DEAD);
713     res = GetPrinterDriverDirectoryA(NULL, env_x86, 1, 
714                                         buffer, cbBuf*2, &pcbNeeded);
715
716     if(!res && (GetLastError() == ERROR_INSUFFICIENT_BUFFER)) {
717         cbBuf = pcbNeeded;
718         buffer = HeapReAlloc(GetProcessHeap(), 0, buffer, cbBuf*2);
719         if (buffer == NULL)  return ;
720
721         buffer[0] = '\0';
722         SetLastError(MAGIC_DEAD);
723         res = GetPrinterDriverDirectoryA(NULL, env_x86, 1, 
724                                         buffer, cbBuf*2, &pcbNeeded);
725     }
726
727     /* "Windows NT x86" is invalid for win9x */
728     ok( (res && buffer[0]) ||
729         (!res && (GetLastError() == ERROR_INVALID_ENVIRONMENT)), 
730         "returned %d with lasterror=%ld and len=%d (expected '!= 0' with " \
731         "'len > 0' or '0' with ERROR_INVALID_ENVIRONMENT)\n",
732         res, GetLastError(), lstrlenA((char *)buffer));
733
734     /* A Setup-Programm (PDFCreator_0.8.0) use empty strings */
735     SetLastError(MAGIC_DEAD);
736     res = GetPrinterDriverDirectoryA("", "", 1, buffer, cbBuf*2, &pcbNeeded);
737     ok(res, "returned %d with %ld (expected '!=0')\n", res, GetLastError() );
738
739     SetLastError(MAGIC_DEAD);
740     res = GetPrinterDriverDirectoryA(NULL, "", 1, buffer, cbBuf*2, &pcbNeeded);
741     ok(res, "returned %d with %ld (expected '!=0')\n", res, GetLastError() );
742
743     SetLastError(MAGIC_DEAD);
744     res = GetPrinterDriverDirectoryA("", NULL, 1, buffer, cbBuf*2, &pcbNeeded);
745     ok(res, "returned %d with %ld (expected '!=0')\n", res, GetLastError() );
746
747     HeapFree( GetProcessHeap(), 0, buffer);
748 }
749
750 static void test_OpenPrinter(void)
751 {
752     PRINTER_DEFAULTSA defaults;
753     HANDLE  hprinter;
754     LPSTR   default_printer;
755     DWORD   res;
756     DWORD   size;
757     CHAR    buffer[DEFAULT_PRINTER_SIZE];
758     LPSTR   ptr;
759
760     SetLastError(MAGIC_DEAD);
761     res = OpenPrinter(NULL, NULL, NULL);    
762     /* The deactivated Spooler is catched here on NT3.51 */
763     RETURN_ON_DEACTIVATED_SPOOLER(res)
764     ok(!res && (GetLastError() == ERROR_INVALID_PARAMETER),
765         "returned %ld with %ld (expected '0' with ERROR_INVALID_PARAMETER)\n",
766         res, GetLastError());
767
768
769     /* Get Handle for the local Printserver (NT only)*/
770     hprinter = (HANDLE) MAGIC_DEAD;
771     SetLastError(MAGIC_DEAD);
772     res = OpenPrinter(NULL, &hprinter, NULL);
773     /* The deactivated Spooler is catched here on XPsp2 */
774     RETURN_ON_DEACTIVATED_SPOOLER(res)
775     ok(res || (!res && GetLastError() == ERROR_INVALID_PARAMETER),
776         "returned %ld with %ld (expected '!=0' or '0' with ERROR_INVALID_PARAMETER)\n",
777         res, GetLastError());
778     if(res) {
779         ClosePrinter(hprinter);
780
781         defaults.pDatatype=NULL;
782         defaults.pDevMode=NULL;
783
784         defaults.DesiredAccess=0;
785         hprinter = (HANDLE) MAGIC_DEAD;
786         SetLastError(MAGIC_DEAD);
787         res = OpenPrinter(NULL, &hprinter, &defaults);
788         ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
789         if (res) ClosePrinter(hprinter);
790
791         defaults.DesiredAccess=-1;
792         hprinter = (HANDLE) MAGIC_DEAD;
793         SetLastError(MAGIC_DEAD);
794         res = OpenPrinter(NULL, &hprinter, &defaults);
795         ok(!res && GetLastError() == ERROR_ACCESS_DENIED,
796             "returned %ld with %ld (expected '0' with ERROR_ACCESS_DENIED)\n", 
797             res, GetLastError());
798         if (res) ClosePrinter(hprinter);
799
800     }
801
802     size = sizeof(buffer) - 3 ;
803     ptr = buffer;
804     ptr[0] = '\\';
805     ptr++;
806     ptr[0] = '\\';
807     ptr++;
808     if (GetComputerNameA(ptr, &size)) {
809
810         hprinter = (HANDLE) MAGIC_DEAD;
811         SetLastError(MAGIC_DEAD);
812         res = OpenPrinter(buffer, &hprinter, NULL);
813         todo_wine {
814         ok(res || (!res && GetLastError() == ERROR_INVALID_PARAMETER),
815             "returned %ld with %ld (expected '!=0' or '0' with ERROR_INVALID_PARAMETER)\n",
816             res, GetLastError());
817         }
818         if(res) ClosePrinter(hprinter);
819     }
820
821     /* Invalid Printername */
822     hprinter = (HANDLE) MAGIC_DEAD;
823     SetLastError(MAGIC_DEAD);
824     res = OpenPrinter("illegal,name", &hprinter, NULL);
825     ok(!res && ((GetLastError() == ERROR_INVALID_PRINTER_NAME) || 
826                 (GetLastError() == ERROR_INVALID_PARAMETER) ),
827        "returned %ld with %ld (expected '0' with: ERROR_INVALID_PARAMETER or" \
828        "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
829     if(res) ClosePrinter(hprinter);
830
831
832     /* Get Handle for the default Printer */
833     if ((default_printer = find_default_printer()))
834     {
835         hprinter = (HANDLE) MAGIC_DEAD;
836         SetLastError(MAGIC_DEAD);
837         res = OpenPrinter(default_printer, &hprinter, NULL);
838         if((!res) && (GetLastError() == RPC_S_SERVER_UNAVAILABLE))
839         {
840                 trace("The Service 'Spooler' is required for '%s'\n", default_printer);
841             return;
842         }
843         ok(res, "returned %ld with %ld (expected '!=0')\n", res, GetLastError());
844         if(res) ClosePrinter(hprinter);
845
846         defaults.pDatatype=NULL;
847         defaults.pDevMode=NULL;
848         defaults.DesiredAccess=0;
849
850         hprinter = (HANDLE) MAGIC_DEAD;
851         SetLastError(MAGIC_DEAD);
852         res = OpenPrinter(default_printer, &hprinter, &defaults);
853         ok(res || GetLastError() == ERROR_ACCESS_DENIED,
854             "returned %ld with %ld (expected '!=0' or '0' with " \
855             "ERROR_ACCESS_DENIED)\n", res, GetLastError());
856         if(res) ClosePrinter(hprinter);
857
858         defaults.pDatatype="";
859
860         hprinter = (HANDLE) MAGIC_DEAD;
861         SetLastError(MAGIC_DEAD);
862         res = OpenPrinter(default_printer, &hprinter, &defaults);
863         /* stop here, when a remote Printserver has no RPC-Service running */
864         RETURN_ON_DEACTIVATED_SPOOLER(res)
865         ok(res || ((GetLastError() == ERROR_INVALID_DATATYPE) ||
866                    (GetLastError() == ERROR_ACCESS_DENIED)),
867             "returned %ld with %ld (expected '!=0' or '0' with: " \
868             "ERROR_INVALID_DATATYPE or ERROR_ACCESS_DENIED)\n",
869             res, GetLastError());
870         if(res) ClosePrinter(hprinter);
871
872
873         defaults.pDatatype=NULL;
874         defaults.DesiredAccess=PRINTER_ACCESS_USE;
875
876         hprinter = (HANDLE) MAGIC_DEAD;
877         SetLastError(MAGIC_DEAD);
878         res = OpenPrinter(default_printer, &hprinter, &defaults);
879         ok(res || GetLastError() == ERROR_ACCESS_DENIED,
880             "returned %ld with %ld (expected '!=0' or '0' with " \
881             "ERROR_ACCESS_DENIED)\n", res, GetLastError());
882         if(res) ClosePrinter(hprinter);
883
884
885         defaults.DesiredAccess=PRINTER_ALL_ACCESS;
886         hprinter = (HANDLE) MAGIC_DEAD;
887         SetLastError(MAGIC_DEAD);
888         res = OpenPrinter(default_printer, &hprinter, &defaults);
889         ok(res || GetLastError() == ERROR_ACCESS_DENIED,
890             "returned %ld with %ld (expected '!=0' or '0' with " \
891             "ERROR_ACCESS_DENIED)\n", res, GetLastError());
892         if(res) ClosePrinter(hprinter);
893     }
894
895 }
896
897
898 static void test_SetDefaultPrinter(void)
899 {
900     DWORD   res;
901     LPSTR   default_printer;
902     DWORD   size = DEFAULT_PRINTER_SIZE;
903     CHAR    buffer[DEFAULT_PRINTER_SIZE];
904     CHAR    org_value[DEFAULT_PRINTER_SIZE];
905
906
907     if (!pSetDefaultPrinterA)  return;
908         /* only supported on win2k and above */
909
910     default_printer = find_default_printer();
911
912     /* backup the original value */
913     org_value[0] = '\0';
914     SetLastError(MAGIC_DEAD);
915     res = GetProfileStringA("windows", "device", NULL, org_value, size);
916
917     /* first part: with the default Printer */
918     SetLastError(MAGIC_DEAD);
919     res = pSetDefaultPrinterA("no_printer_with_this_name");
920
921     RETURN_ON_DEACTIVATED_SPOOLER(res)
922     /* spooler is running or we have no spooler here*/
923
924     /* Not implemented in wine */
925     if (!res && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)) {
926         trace("SetDefaultPrinterA() not implemented yet.\n");
927         return;
928     }
929
930     ok(!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME),
931         "returned %ld with %ld (expected '0' with " \
932         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
933
934     WriteProfileStringA("windows", "device", org_value);
935     SetLastError(MAGIC_DEAD);
936     res = pSetDefaultPrinterA("");
937     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
938         "returned %ld with %ld (expected '!=0' or '0' with " \
939         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
940
941     WriteProfileStringA("windows", "device", org_value);
942     SetLastError(MAGIC_DEAD);
943     res = pSetDefaultPrinterA(NULL);
944     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
945         "returned %ld with %ld (expected '!=0' or '0' with " \
946         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
947
948     WriteProfileStringA("windows", "device", org_value);
949     SetLastError(MAGIC_DEAD);
950     res = pSetDefaultPrinterA(default_printer);
951     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
952         "returned %ld with %ld (expected '!=0' or '0' with " \
953         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
954
955
956     /* second part: always without a default Printer */
957     WriteProfileStringA("windows", "device", NULL);    
958     SetLastError(MAGIC_DEAD);
959     res = pSetDefaultPrinterA("no_printer_with_this_name");
960
961     ok(!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME),
962         "returned %ld with %ld (expected '0' with " \
963         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
964
965     WriteProfileStringA("windows", "device", NULL);    
966     SetLastError(MAGIC_DEAD);
967     res = pSetDefaultPrinterA("");
968     /* we get ERROR_INVALID_PRINTER_NAME when no printer is installed */
969     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
970          "returned %ld with %ld (expected '!=0' or '0' with " \
971          "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
972
973     WriteProfileStringA("windows", "device", NULL);    
974     SetLastError(MAGIC_DEAD);
975     res = pSetDefaultPrinterA(NULL);
976     /* we get ERROR_INVALID_PRINTER_NAME when no printer is installed */
977     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
978         "returned %ld with %ld (expected '!=0' or '0' with " \
979         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
980
981     WriteProfileStringA("windows", "device", NULL);    
982     SetLastError(MAGIC_DEAD);
983     res = pSetDefaultPrinterA(default_printer);
984     ok(res || (!res && (GetLastError() == ERROR_INVALID_PRINTER_NAME)),
985         "returned %ld with %ld (expected '!=0' or '0' with " \
986         "ERROR_INVALID_PRINTER_NAME)\n", res, GetLastError());
987
988     /* restore the original value */
989     res = pSetDefaultPrinterA(default_printer);          /* the nice way */
990     WriteProfileStringA("windows", "device", org_value); /* the old way */
991
992     buffer[0] = '\0';
993     SetLastError(MAGIC_DEAD);
994     res = GetProfileStringA("windows", "device", NULL, buffer, size);
995     ok(!lstrcmpA(org_value, buffer), "'%s' (expected '%s')\n", buffer, org_value);
996
997 }
998
999 static void test_GetPrinterDriver(void)
1000 {
1001     LPSTR default_printer;
1002     HANDLE hprn;
1003     BOOL ret;
1004     BYTE *buf;
1005     INT level;
1006     DWORD needed, filled;
1007
1008     default_printer = find_default_printer();
1009     if (!default_printer)
1010     {
1011         trace("There is no default printer installed, skiping the test\n");
1012         return;
1013     }
1014
1015     hprn = 0;
1016     ret = OpenPrinter(default_printer, &hprn, NULL);
1017     if (!ret)
1018     {
1019         trace("There is no printers installed, skiping the test\n");
1020         return;
1021     }
1022     ok(hprn != 0, "wrong hprn %p\n", hprn);
1023
1024     for (level = -1; level <= 7; level++)
1025     {
1026         SetLastError(0xdeadbeef);
1027         needed = (DWORD)-1;
1028         ret = GetPrinterDriver(hprn, NULL, level, NULL, 0, &needed);
1029         ok(!ret, "level %d: GetPrinterDriver should fail\n", level);
1030         if (level >= 1 && level <= 6)
1031         {
1032             ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "wrong error %ld\n", GetLastError());
1033             ok(needed > 0,"not expected needed buffer size %ld\n", needed);
1034         }
1035         else
1036         {
1037             ok(GetLastError() == ERROR_INVALID_LEVEL, "wrong error %ld\n", GetLastError());
1038             ok(needed == (DWORD)-1,"not expected needed buffer size %ld\n", needed);
1039             continue;
1040         }
1041
1042         buf = HeapAlloc(GetProcessHeap(), 0, needed);
1043
1044         SetLastError(0xdeadbeef);
1045         filled = -1;
1046         ret = GetPrinterDriver(hprn, NULL, level, buf, needed, &filled);
1047         ok(ret, "level %d: GetPrinterDriver error %ld\n", level, GetLastError());
1048         ok(needed == filled, "needed %ld != filled %ld\n", needed, filled);
1049
1050         if (level == 2)
1051         {
1052             DRIVER_INFO_2 *di_2 = (DRIVER_INFO_2 *)buf;
1053             DWORD calculated = sizeof(*di_2);
1054
1055             ok(di_2->cVersion >= 0 && di_2->cVersion <= 3, "di_2->cVersion = %ld\n", di_2->cVersion);
1056             ok(di_2->pName != NULL, "not expected NULL ptr\n");
1057             ok(di_2->pEnvironment != NULL, "not expected NULL ptr\n");
1058             ok(di_2->pDriverPath != NULL, "not expected NULL ptr\n");
1059             ok(di_2->pDataFile != NULL, "not expected NULL ptr\n");
1060             ok(di_2->pConfigFile != NULL, "not expected NULL ptr\n");
1061
1062             trace("cVersion %ld\n", di_2->cVersion);
1063             trace("pName %s\n", di_2->pName);
1064             calculated += strlen(di_2->pName) + 1;
1065             trace("pEnvironment %s\n", di_2->pEnvironment);
1066             calculated += strlen(di_2->pEnvironment) + 1;
1067             trace("pDriverPath %s\n", di_2->pDriverPath);
1068             calculated += strlen(di_2->pDriverPath) + 1;
1069             trace("pDataFile %s\n", di_2->pDataFile);
1070             calculated += strlen(di_2->pDataFile) + 1;
1071             trace("pConfigFile %s\n", di_2->pConfigFile);
1072             calculated += strlen(di_2->pConfigFile) + 1;
1073
1074             /* XP allocates memory for both ANSI and unicode names */
1075             ok(filled >= calculated,"calculated %ld != filled %ld\n", calculated, filled);
1076         }
1077
1078         HeapFree(GetProcessHeap(), 0, buf);
1079     }
1080
1081     SetLastError(0xdeadbeef);
1082     ret = ClosePrinter(hprn);
1083     ok(ret, "ClosePrinter error %ld\n", GetLastError());
1084 }
1085
1086 static void test_DEVMODE(const DEVMODE *dm, LONG dmSize, LPCSTR exp_prn_name)
1087 {
1088     ok(!strcmp(exp_prn_name, (LPCSTR)dm->dmDeviceName), "expected %s, got %s\n", exp_prn_name, dm->dmDeviceName);
1089     ok(dm->dmSize + dm->dmDriverExtra == dmSize, "%u != %ld\n", dm->dmSize + dm->dmDriverExtra, dmSize);
1090     trace("dmFields %08lx\n", dm->dmFields);
1091 }
1092
1093 static void test_DocumentProperties(void)
1094 {
1095     LPSTR default_printer;
1096     HANDLE hprn;
1097     LONG dm_size, ret;
1098     DEVMODE *dm;
1099
1100     default_printer = find_default_printer();
1101     if (!default_printer)
1102     {
1103         trace("There is no default printer installed, skiping the test\n");
1104         return;
1105     }
1106
1107     hprn = 0;
1108     ret = OpenPrinter(default_printer, &hprn, NULL);
1109     if (!ret)
1110     {
1111         trace("There is no printers installed, skiping the test\n");
1112         return;
1113     }
1114     ok(hprn != 0, "wrong hprn %p\n", hprn);
1115
1116     dm_size = DocumentProperties(0, hprn, NULL, NULL, NULL, 0);
1117     trace("DEVMODE required size %ld\n", dm_size);
1118     ok(dm_size >= sizeof(DEVMODE), "unexpected DocumentProperties ret value %ld\n", dm_size);
1119
1120     dm = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, dm_size);
1121
1122     ret = DocumentProperties(0, hprn, NULL, dm, dm, DM_OUT_BUFFER);
1123     ok(ret == IDOK, "DocumentProperties ret value %ld != expected IDOK\n", ret);
1124
1125     test_DEVMODE(dm, dm_size, default_printer);
1126
1127     HeapFree(GetProcessHeap(), 0, dm);
1128
1129     SetLastError(0xdeadbeef);
1130     ret = ClosePrinter(hprn);
1131     ok(ret, "ClosePrinter error %ld\n", GetLastError());
1132 }
1133
1134 START_TEST(info)
1135 {
1136     hwinspool = GetModuleHandleA("winspool.drv");
1137     pGetDefaultPrinterA = (void *) GetProcAddress(hwinspool, "GetDefaultPrinterA");
1138     pSetDefaultPrinterA = (void *) GetProcAddress(hwinspool, "SetDefaultPrinterA");
1139
1140     find_default_printer();
1141
1142     test_AddMonitor();
1143     test_DeleteMonitor();
1144     test_DocumentProperties();
1145     test_EnumMonitors(); 
1146     test_GetDefaultPrinter();
1147     test_GetPrinterDriverDirectory();
1148     test_OpenPrinter();
1149     test_GetPrinterDriver();
1150     test_SetDefaultPrinter();
1151 }