146b91659SColin Finck /*
246b91659SColin Finck * PROJECT: ReactOS Spooler API
346b91659SColin Finck * LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+)
446b91659SColin Finck * PURPOSE: Functions related to Forms
546b91659SColin Finck * COPYRIGHT: Copyright 2017 Colin Finck (colin@reactos.org)
646b91659SColin Finck */
746b91659SColin Finck
846b91659SColin Finck #include "precomp.h"
97bffb703SJames Tabor #include <marshalling/forms.h>
1046b91659SColin Finck
1146b91659SColin Finck BOOL WINAPI
AddFormA(HANDLE hPrinter,DWORD Level,PBYTE pForm)1246b91659SColin Finck AddFormA(HANDLE hPrinter, DWORD Level, PBYTE pForm)
1346b91659SColin Finck {
147bffb703SJames Tabor FORM_INFO_2W pfi2W;
157bffb703SJames Tabor PFORM_INFO_2A pfi2A;
167bffb703SJames Tabor DWORD len;
177bffb703SJames Tabor BOOL res;
187bffb703SJames Tabor
197bffb703SJames Tabor pfi2A = (PFORM_INFO_2A)pForm;
207bffb703SJames Tabor
2146b91659SColin Finck TRACE("AddFormA(%p, %lu, %p)\n", hPrinter, Level, pForm);
227bffb703SJames Tabor
237bffb703SJames Tabor if ((Level < 1) || (Level > 2))
247bffb703SJames Tabor {
257bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
267bffb703SJames Tabor SetLastError(ERROR_INVALID_LEVEL);
2746b91659SColin Finck return FALSE;
2846b91659SColin Finck }
2946b91659SColin Finck
307bffb703SJames Tabor if (!pfi2A)
317bffb703SJames Tabor {
327bffb703SJames Tabor SetLastError(ERROR_INVALID_PARAMETER);
337bffb703SJames Tabor return FALSE;
347bffb703SJames Tabor }
357bffb703SJames Tabor
367bffb703SJames Tabor ZeroMemory(&pfi2W, sizeof(FORM_INFO_2W));
377bffb703SJames Tabor
387bffb703SJames Tabor if (pfi2A->pName)
397bffb703SJames Tabor {
407bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pName, -1, NULL, 0);
417bffb703SJames Tabor pfi2W.pName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
427bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pName, -1, pfi2W.pName, len);
437bffb703SJames Tabor }
447bffb703SJames Tabor
457bffb703SJames Tabor pfi2W.Flags = pfi2A->Flags;
467bffb703SJames Tabor pfi2W.Size = pfi2A->Size;
477bffb703SJames Tabor pfi2W.ImageableArea = pfi2A->ImageableArea;
487bffb703SJames Tabor
497bffb703SJames Tabor if (Level > 1)
507bffb703SJames Tabor {
517bffb703SJames Tabor if (pfi2A->pKeyword)
527bffb703SJames Tabor {
537bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pKeyword, -1, NULL, 0);
547bffb703SJames Tabor pfi2W.pKeyword = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
557bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pKeyword, -1, (LPWSTR)pfi2W.pKeyword, len);
567bffb703SJames Tabor }
577bffb703SJames Tabor
587bffb703SJames Tabor if (pfi2A->pMuiDll)
597bffb703SJames Tabor {
607bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pMuiDll, -1, NULL, 0);
617bffb703SJames Tabor pfi2W.pMuiDll = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
627bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pMuiDll, -1, (LPWSTR)pfi2W.pMuiDll, len);
637bffb703SJames Tabor }
647bffb703SJames Tabor
657bffb703SJames Tabor if (pfi2A->pDisplayName)
667bffb703SJames Tabor {
677bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pDisplayName, -1, NULL, 0);
687bffb703SJames Tabor pfi2W.pDisplayName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
697bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pDisplayName, -1, (LPWSTR)pfi2W.pDisplayName, len);
707bffb703SJames Tabor }
717bffb703SJames Tabor pfi2W.StringType = pfi2A->StringType;
727bffb703SJames Tabor pfi2W.dwResourceId = pfi2A->dwResourceId;
737bffb703SJames Tabor pfi2W.wLangId = pfi2A->wLangId;
747bffb703SJames Tabor }
757bffb703SJames Tabor
767bffb703SJames Tabor res = AddFormW( hPrinter, Level, (PBYTE)&pfi2W );
777bffb703SJames Tabor
787bffb703SJames Tabor if (pfi2W.pName) HeapFree(GetProcessHeap(), 0, pfi2W.pName);
797bffb703SJames Tabor if (pfi2W.pKeyword) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pKeyword);
807bffb703SJames Tabor if (pfi2W.pMuiDll) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pMuiDll);
817bffb703SJames Tabor if (pfi2W.pDisplayName) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pDisplayName);
827bffb703SJames Tabor
837bffb703SJames Tabor return res;
847bffb703SJames Tabor }
857bffb703SJames Tabor
8646b91659SColin Finck BOOL WINAPI
AddFormW(HANDLE hPrinter,DWORD Level,PBYTE pForm)8746b91659SColin Finck AddFormW(HANDLE hPrinter, DWORD Level, PBYTE pForm)
8846b91659SColin Finck {
897bffb703SJames Tabor DWORD dwErrorCode;
907bffb703SJames Tabor WINSPOOL_FORM_CONTAINER FormInfoContainer;
917bffb703SJames Tabor PSPOOLER_HANDLE pHandle = (PSPOOLER_HANDLE)hPrinter;
927bffb703SJames Tabor
9346b91659SColin Finck TRACE("AddFormW(%p, %lu, %p)\n", hPrinter, Level, pForm);
947bffb703SJames Tabor
957bffb703SJames Tabor // Sanity checks.
967bffb703SJames Tabor if (!pHandle)
977bffb703SJames Tabor {
987bffb703SJames Tabor dwErrorCode = ERROR_INVALID_HANDLE;
9946b91659SColin Finck return FALSE;
10046b91659SColin Finck }
10146b91659SColin Finck
1027bffb703SJames Tabor if ((Level < 1) || (Level > 2))
1037bffb703SJames Tabor {
1047bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
1057bffb703SJames Tabor SetLastError(ERROR_INVALID_LEVEL);
1067bffb703SJames Tabor return FALSE;
1077bffb703SJames Tabor }
1087bffb703SJames Tabor
1097bffb703SJames Tabor FormInfoContainer.FormInfo.pFormInfo1 = (WINSPOOL_FORM_INFO_1*)pForm;
1107bffb703SJames Tabor FormInfoContainer.Level = Level;
1117bffb703SJames Tabor
1127bffb703SJames Tabor // Do the RPC call
1137bffb703SJames Tabor RpcTryExcept
1147bffb703SJames Tabor {
1157bffb703SJames Tabor dwErrorCode = _RpcAddForm(pHandle->hPrinter, &FormInfoContainer);
1167bffb703SJames Tabor }
1177bffb703SJames Tabor RpcExcept(EXCEPTION_EXECUTE_HANDLER)
1187bffb703SJames Tabor {
1197bffb703SJames Tabor dwErrorCode = RpcExceptionCode();
1207bffb703SJames Tabor ERR("_RpcAddForm failed with exception code %lu!\n", dwErrorCode);
1217bffb703SJames Tabor }
1227bffb703SJames Tabor RpcEndExcept;
1237bffb703SJames Tabor
1247bffb703SJames Tabor SetLastError(dwErrorCode);
1257bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
1267bffb703SJames Tabor }
1277bffb703SJames Tabor
12846b91659SColin Finck BOOL WINAPI
DeleteFormA(HANDLE hPrinter,PSTR pFormName)12946b91659SColin Finck DeleteFormA(HANDLE hPrinter, PSTR pFormName)
13046b91659SColin Finck {
1317bffb703SJames Tabor UNICODE_STRING FormNameW;
1327bffb703SJames Tabor BOOL Ret;
1337bffb703SJames Tabor
13446b91659SColin Finck TRACE("DeleteFormA(%p, %s)\n", hPrinter, pFormName);
1357bffb703SJames Tabor
1367bffb703SJames Tabor AsciiToUnicode(&FormNameW, pFormName);
1377bffb703SJames Tabor
1387bffb703SJames Tabor Ret = DeleteFormW( hPrinter, FormNameW.Buffer );
1397bffb703SJames Tabor
1407bffb703SJames Tabor RtlFreeUnicodeString(&FormNameW);
1417bffb703SJames Tabor
1427bffb703SJames Tabor return Ret;
14346b91659SColin Finck }
14446b91659SColin Finck
14546b91659SColin Finck BOOL WINAPI
DeleteFormW(HANDLE hPrinter,PWSTR pFormName)14646b91659SColin Finck DeleteFormW(HANDLE hPrinter, PWSTR pFormName)
14746b91659SColin Finck {
1487bffb703SJames Tabor DWORD dwErrorCode;
1497bffb703SJames Tabor PSPOOLER_HANDLE pHandle = (PSPOOLER_HANDLE)hPrinter;
1507bffb703SJames Tabor
15146b91659SColin Finck TRACE("DeleteFormW(%p, %S)\n", hPrinter, pFormName);
1527bffb703SJames Tabor
1537bffb703SJames Tabor // Sanity checks.
1547bffb703SJames Tabor if (!pHandle)
1557bffb703SJames Tabor {
1567bffb703SJames Tabor dwErrorCode = ERROR_INVALID_HANDLE;
15746b91659SColin Finck return FALSE;
15846b91659SColin Finck }
15946b91659SColin Finck
1607bffb703SJames Tabor // Do the RPC call
1617bffb703SJames Tabor RpcTryExcept
1627bffb703SJames Tabor {
1637bffb703SJames Tabor dwErrorCode = _RpcDeleteForm(pHandle->hPrinter, pFormName);
1647bffb703SJames Tabor }
1657bffb703SJames Tabor RpcExcept(EXCEPTION_EXECUTE_HANDLER)
1667bffb703SJames Tabor {
1677bffb703SJames Tabor dwErrorCode = RpcExceptionCode();
1687bffb703SJames Tabor ERR("_RpcDeleteForm failed with exception code %lu!\n", dwErrorCode);
1697bffb703SJames Tabor }
1707bffb703SJames Tabor RpcEndExcept;
1717bffb703SJames Tabor
1727bffb703SJames Tabor SetLastError(dwErrorCode);
1737bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
1747bffb703SJames Tabor }
1757bffb703SJames Tabor
17646b91659SColin Finck BOOL WINAPI
EnumFormsA(HANDLE hPrinter,DWORD Level,PBYTE pForm,DWORD cbBuf,PDWORD pcbNeeded,PDWORD pcReturned)17746b91659SColin Finck EnumFormsA(HANDLE hPrinter, DWORD Level, PBYTE pForm, DWORD cbBuf, PDWORD pcbNeeded, PDWORD pcReturned)
17846b91659SColin Finck {
1797bffb703SJames Tabor DWORD dwErrorCode, i;
180*62c4b828SJames Tabor PFORM_INFO_1W pfi1w = (PFORM_INFO_1W)pForm;
1817bffb703SJames Tabor PFORM_INFO_2W pfi2w = (PFORM_INFO_2W)pForm;
1827bffb703SJames Tabor
18346b91659SColin Finck TRACE("EnumFormsA(%p, %lu, %p, %lu, %p, %p)\n", hPrinter, Level, pForm, cbBuf, pcbNeeded, pcReturned);
1847bffb703SJames Tabor
1857bffb703SJames Tabor if ( EnumFormsW( hPrinter, Level, pForm, cbBuf, pcbNeeded, pcReturned ) )
1867bffb703SJames Tabor {
1877bffb703SJames Tabor for ( i = 0; i < *pcReturned; i++ )
1887bffb703SJames Tabor {
1897bffb703SJames Tabor switch ( Level )
1907bffb703SJames Tabor {
1917bffb703SJames Tabor case 2:
1927bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w[i].pKeyword);
1937bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
1947bffb703SJames Tabor {
1957bffb703SJames Tabor goto Cleanup;
1967bffb703SJames Tabor }
1977bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w[i].pMuiDll);
1987bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
1997bffb703SJames Tabor {
2007bffb703SJames Tabor goto Cleanup;
2017bffb703SJames Tabor }
2027bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w[i].pDisplayName);
2037bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
2047bffb703SJames Tabor {
2057bffb703SJames Tabor goto Cleanup;
2067bffb703SJames Tabor }
2077bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace(pfi2w[i].pName);
2087bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
2097bffb703SJames Tabor {
2107bffb703SJames Tabor goto Cleanup;
2117bffb703SJames Tabor }
212*62c4b828SJames Tabor break;
213*62c4b828SJames Tabor case 1:
214*62c4b828SJames Tabor dwErrorCode = UnicodeToAnsiInPlace(pfi1w[i].pName);
215*62c4b828SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
216*62c4b828SJames Tabor {
217*62c4b828SJames Tabor goto Cleanup;
218*62c4b828SJames Tabor }
2197bffb703SJames Tabor }
2207bffb703SJames Tabor }
2217bffb703SJames Tabor return TRUE;
2227bffb703SJames Tabor }
2237bffb703SJames Tabor Cleanup:
22446b91659SColin Finck return FALSE;
22546b91659SColin Finck }
22646b91659SColin Finck
22746b91659SColin Finck BOOL WINAPI
EnumFormsW(HANDLE hPrinter,DWORD Level,PBYTE pForm,DWORD cbBuf,PDWORD pcbNeeded,PDWORD pcReturned)22846b91659SColin Finck EnumFormsW(HANDLE hPrinter, DWORD Level, PBYTE pForm, DWORD cbBuf, PDWORD pcbNeeded, PDWORD pcReturned)
22946b91659SColin Finck {
2307bffb703SJames Tabor DWORD dwErrorCode;
2317bffb703SJames Tabor PSPOOLER_HANDLE pHandle = (PSPOOLER_HANDLE)hPrinter;
2327bffb703SJames Tabor
23346b91659SColin Finck TRACE("EnumFormsW(%p, %lu, %p, %lu, %p, %p)\n", hPrinter, Level, pForm, cbBuf, pcbNeeded, pcReturned);
2347bffb703SJames Tabor
2357bffb703SJames Tabor // Sanity checks.
2367bffb703SJames Tabor if (!pHandle)
2377bffb703SJames Tabor {
2387bffb703SJames Tabor dwErrorCode = ERROR_INVALID_HANDLE;
2397bffb703SJames Tabor goto Cleanup;
2407bffb703SJames Tabor }
2417bffb703SJames Tabor
2427bffb703SJames Tabor if ((Level < 1) || (Level > 2))
2437bffb703SJames Tabor {
2447bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
2457bffb703SJames Tabor dwErrorCode = ERROR_INVALID_LEVEL;
2467bffb703SJames Tabor goto Cleanup;
2477bffb703SJames Tabor }
2487bffb703SJames Tabor
2497bffb703SJames Tabor // Do the RPC call
2507bffb703SJames Tabor RpcTryExcept
2517bffb703SJames Tabor {
2527bffb703SJames Tabor dwErrorCode = _RpcEnumForms(pHandle->hPrinter, Level, pForm, cbBuf, pcbNeeded, pcReturned);
2537bffb703SJames Tabor }
2547bffb703SJames Tabor RpcExcept(EXCEPTION_EXECUTE_HANDLER)
2557bffb703SJames Tabor {
2567bffb703SJames Tabor dwErrorCode = RpcExceptionCode();
2577bffb703SJames Tabor ERR("_RpcEnumForms failed with exception code %lu!\n", dwErrorCode);
2587bffb703SJames Tabor }
2597bffb703SJames Tabor RpcEndExcept;
2607bffb703SJames Tabor
2617bffb703SJames Tabor if (dwErrorCode == ERROR_SUCCESS)
2627bffb703SJames Tabor {
2637bffb703SJames Tabor // Replace relative offset addresses in the output by absolute pointers.
2647bffb703SJames Tabor ASSERT(Level >= 1 && Level <= 2);
2657bffb703SJames Tabor MarshallUpStructuresArray(cbBuf, pForm, *pcReturned, pFormInfoMarshalling[Level]->pInfo, pFormInfoMarshalling[Level]->cbStructureSize, TRUE);
2667bffb703SJames Tabor }
2677bffb703SJames Tabor
2687bffb703SJames Tabor Cleanup:
2697bffb703SJames Tabor SetLastError(dwErrorCode);
2707bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
27146b91659SColin Finck }
27246b91659SColin Finck
27346b91659SColin Finck BOOL WINAPI
GetFormA(HANDLE hPrinter,PSTR pFormName,DWORD Level,PBYTE pForm,DWORD cbBuf,PDWORD pcbNeeded)27446b91659SColin Finck GetFormA(HANDLE hPrinter, PSTR pFormName, DWORD Level, PBYTE pForm, DWORD cbBuf, PDWORD pcbNeeded)
27546b91659SColin Finck {
2767bffb703SJames Tabor DWORD dwErrorCode, len;
2777bffb703SJames Tabor LPWSTR FormNameW = NULL;
278*62c4b828SJames Tabor PFORM_INFO_1W pfi1w = (PFORM_INFO_1W)pForm;
279*62c4b828SJames Tabor PFORM_INFO_2W pfi2w = (PFORM_INFO_2W)pForm;
2807bffb703SJames Tabor
28146b91659SColin Finck TRACE("GetFormA(%p, %s, %lu, %p, %lu, %p)\n", hPrinter, pFormName, Level, pForm, cbBuf, pcbNeeded);
2827bffb703SJames Tabor
2837bffb703SJames Tabor if (pFormName)
2847bffb703SJames Tabor {
2857bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pFormName, -1, NULL, 0);
2867bffb703SJames Tabor FormNameW = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
2877bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pFormName, -1, FormNameW, len);
2887bffb703SJames Tabor }
2897bffb703SJames Tabor
2907bffb703SJames Tabor if ( GetFormW( hPrinter, FormNameW, Level, pForm, cbBuf, pcbNeeded ) )
2917bffb703SJames Tabor {
2927bffb703SJames Tabor switch ( Level )
2937bffb703SJames Tabor {
2947bffb703SJames Tabor case 2:
2957bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w->pKeyword);
2967bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
2977bffb703SJames Tabor {
2987bffb703SJames Tabor goto Cleanup;
2997bffb703SJames Tabor }
3007bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w->pMuiDll);
3017bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
3027bffb703SJames Tabor {
3037bffb703SJames Tabor goto Cleanup;
3047bffb703SJames Tabor }
3057bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace((LPWSTR)pfi2w->pDisplayName);
3067bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
3077bffb703SJames Tabor {
3087bffb703SJames Tabor goto Cleanup;
3097bffb703SJames Tabor }
3107bffb703SJames Tabor dwErrorCode = UnicodeToAnsiInPlace(pfi2w->pName);
3117bffb703SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
3127bffb703SJames Tabor {
3137bffb703SJames Tabor goto Cleanup;
3147bffb703SJames Tabor }
3157bffb703SJames Tabor break;
316*62c4b828SJames Tabor case 1:
317*62c4b828SJames Tabor dwErrorCode = UnicodeToAnsiInPlace(pfi1w->pName);
318*62c4b828SJames Tabor if (dwErrorCode != ERROR_SUCCESS)
319*62c4b828SJames Tabor {
320*62c4b828SJames Tabor goto Cleanup;
321*62c4b828SJames Tabor }
3227bffb703SJames Tabor }
3237bffb703SJames Tabor }
3247bffb703SJames Tabor Cleanup:
3257bffb703SJames Tabor if (FormNameW) HeapFree(GetProcessHeap(), 0, FormNameW);
3267bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
32746b91659SColin Finck }
32846b91659SColin Finck
32946b91659SColin Finck BOOL WINAPI
GetFormW(HANDLE hPrinter,PWSTR pFormName,DWORD Level,PBYTE pForm,DWORD cbBuf,PDWORD pcbNeeded)33046b91659SColin Finck GetFormW(HANDLE hPrinter, PWSTR pFormName, DWORD Level, PBYTE pForm, DWORD cbBuf, PDWORD pcbNeeded)
33146b91659SColin Finck {
3327bffb703SJames Tabor DWORD dwErrorCode;
3337bffb703SJames Tabor PSPOOLER_HANDLE pHandle = (PSPOOLER_HANDLE)hPrinter;
3347bffb703SJames Tabor
33546b91659SColin Finck TRACE("GetFormW(%p, %S, %lu, %p, %lu, %p)\n", hPrinter, pFormName, Level, pForm, cbBuf, pcbNeeded);
3367bffb703SJames Tabor
3377bffb703SJames Tabor // Sanity checks.
3387bffb703SJames Tabor if (!pHandle)
3397bffb703SJames Tabor {
3407bffb703SJames Tabor dwErrorCode = ERROR_INVALID_HANDLE;
3417bffb703SJames Tabor goto Cleanup;
3427bffb703SJames Tabor }
3437bffb703SJames Tabor
3447bffb703SJames Tabor // Dismiss invalid levels already at this point.
3457bffb703SJames Tabor if ((Level < 1) || (Level > 2))
3467bffb703SJames Tabor {
3477bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
3487bffb703SJames Tabor dwErrorCode = ERROR_INVALID_LEVEL;
3497bffb703SJames Tabor goto Cleanup;
3507bffb703SJames Tabor }
3517bffb703SJames Tabor
3527bffb703SJames Tabor if (cbBuf && pForm)
3537bffb703SJames Tabor ZeroMemory(pForm, cbBuf);
3547bffb703SJames Tabor
3557bffb703SJames Tabor // Do the RPC call
3567bffb703SJames Tabor RpcTryExcept
3577bffb703SJames Tabor {
3587bffb703SJames Tabor dwErrorCode = _RpcGetForm(pHandle->hPrinter, pFormName, Level, pForm, cbBuf, pcbNeeded);
3597bffb703SJames Tabor }
3607bffb703SJames Tabor RpcExcept(EXCEPTION_EXECUTE_HANDLER)
3617bffb703SJames Tabor {
3627bffb703SJames Tabor dwErrorCode = RpcExceptionCode();
3637bffb703SJames Tabor ERR("_RpcGetForm failed with exception code %lu!\n", dwErrorCode);
3647bffb703SJames Tabor }
3657bffb703SJames Tabor RpcEndExcept;
3667bffb703SJames Tabor
3677bffb703SJames Tabor if (dwErrorCode == ERROR_SUCCESS)
3687bffb703SJames Tabor {
3697bffb703SJames Tabor // Replace relative offset addresses in the output by absolute pointers.
3707bffb703SJames Tabor ASSERT(Level >= 1 && Level <= 2);
3717bffb703SJames Tabor MarshallUpStructure(cbBuf, pForm, pFormInfoMarshalling[Level]->pInfo, pFormInfoMarshalling[Level]->cbStructureSize, TRUE);
3727bffb703SJames Tabor }
3737bffb703SJames Tabor
3747bffb703SJames Tabor Cleanup:
3757bffb703SJames Tabor SetLastError(dwErrorCode);
3767bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
37746b91659SColin Finck }
37846b91659SColin Finck
37946b91659SColin Finck BOOL WINAPI
SetFormA(HANDLE hPrinter,PSTR pFormName,DWORD Level,PBYTE pForm)38046b91659SColin Finck SetFormA(HANDLE hPrinter, PSTR pFormName, DWORD Level, PBYTE pForm)
38146b91659SColin Finck {
3827bffb703SJames Tabor FORM_INFO_2W pfi2W;
3837bffb703SJames Tabor FORM_INFO_2A * pfi2A;
3847bffb703SJames Tabor LPWSTR FormNameW = NULL;
3857bffb703SJames Tabor DWORD len;
3867bffb703SJames Tabor BOOL res;
3877bffb703SJames Tabor
3887bffb703SJames Tabor pfi2A = (FORM_INFO_2A *) pForm;
3897bffb703SJames Tabor
39046b91659SColin Finck TRACE("SetFormA(%p, %s, %lu, %p)\n", hPrinter, pFormName, Level, pForm);
3917bffb703SJames Tabor
3927bffb703SJames Tabor if ((Level < 1) || (Level > 2))
3937bffb703SJames Tabor {
3947bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
3957bffb703SJames Tabor SetLastError(ERROR_INVALID_LEVEL);
39646b91659SColin Finck return FALSE;
39746b91659SColin Finck }
39846b91659SColin Finck
3997bffb703SJames Tabor if (!pfi2A)
4007bffb703SJames Tabor {
4017bffb703SJames Tabor SetLastError(ERROR_INVALID_PARAMETER);
4027bffb703SJames Tabor return FALSE;
4037bffb703SJames Tabor }
4047bffb703SJames Tabor
4057bffb703SJames Tabor if (pFormName)
4067bffb703SJames Tabor {
4077bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pFormName, -1, NULL, 0);
4087bffb703SJames Tabor FormNameW = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
4097bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pFormName, -1, FormNameW, len);
4107bffb703SJames Tabor }
4117bffb703SJames Tabor
4127bffb703SJames Tabor ZeroMemory(&pfi2W, sizeof(FORM_INFO_2W));
4137bffb703SJames Tabor
4147bffb703SJames Tabor if (pfi2A->pName)
4157bffb703SJames Tabor {
4167bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pName, -1, NULL, 0);
4177bffb703SJames Tabor pfi2W.pName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
4187bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pName, -1, pfi2W.pName, len);
4197bffb703SJames Tabor }
4207bffb703SJames Tabor
4217bffb703SJames Tabor pfi2W.Flags = pfi2A->Flags;
4227bffb703SJames Tabor pfi2W.Size = pfi2A->Size;
4237bffb703SJames Tabor pfi2W.ImageableArea = pfi2A->ImageableArea;
4247bffb703SJames Tabor
4257bffb703SJames Tabor if (Level > 1)
4267bffb703SJames Tabor {
4277bffb703SJames Tabor if (pfi2A->pKeyword)
4287bffb703SJames Tabor {
4297bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pKeyword, -1, NULL, 0);
4307bffb703SJames Tabor pfi2W.pKeyword = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
4317bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pKeyword, -1, (LPWSTR)pfi2W.pKeyword, len);
4327bffb703SJames Tabor }
4337bffb703SJames Tabor
4347bffb703SJames Tabor if (pfi2A->pMuiDll)
4357bffb703SJames Tabor {
4367bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pMuiDll, -1, NULL, 0);
4377bffb703SJames Tabor pfi2W.pMuiDll = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
4387bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pMuiDll, -1, (LPWSTR)pfi2W.pMuiDll, len);
4397bffb703SJames Tabor }
4407bffb703SJames Tabor
4417bffb703SJames Tabor if (pfi2A->pDisplayName)
4427bffb703SJames Tabor {
4437bffb703SJames Tabor len = MultiByteToWideChar(CP_ACP, 0, pfi2A->pDisplayName, -1, NULL, 0);
4447bffb703SJames Tabor pfi2W.pDisplayName = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
4457bffb703SJames Tabor MultiByteToWideChar(CP_ACP, 0, pfi2A->pDisplayName, -1, (LPWSTR)pfi2W.pDisplayName, len);
4467bffb703SJames Tabor }
4477bffb703SJames Tabor pfi2W.StringType = pfi2A->StringType;
4487bffb703SJames Tabor pfi2W.dwResourceId = pfi2A->dwResourceId;
4497bffb703SJames Tabor pfi2W.wLangId = pfi2A->wLangId;
4507bffb703SJames Tabor }
4517bffb703SJames Tabor
4527bffb703SJames Tabor res = SetFormW( hPrinter, FormNameW, Level, (PBYTE)&pfi2W );
4537bffb703SJames Tabor
4547bffb703SJames Tabor if (FormNameW) HeapFree(GetProcessHeap(), 0, FormNameW);
4557bffb703SJames Tabor if (pfi2W.pName) HeapFree(GetProcessHeap(), 0, pfi2W.pName);
4567bffb703SJames Tabor if (pfi2W.pKeyword) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pKeyword);
4577bffb703SJames Tabor if (pfi2W.pMuiDll) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pMuiDll);
4587bffb703SJames Tabor if (pfi2W.pDisplayName) HeapFree(GetProcessHeap(), 0, (LPWSTR)pfi2W.pDisplayName);
4597bffb703SJames Tabor
4607bffb703SJames Tabor return res;
4617bffb703SJames Tabor }
4627bffb703SJames Tabor
46346b91659SColin Finck BOOL WINAPI
SetFormW(HANDLE hPrinter,PWSTR pFormName,DWORD Level,PBYTE pForm)46446b91659SColin Finck SetFormW(HANDLE hPrinter, PWSTR pFormName, DWORD Level, PBYTE pForm)
46546b91659SColin Finck {
4667bffb703SJames Tabor DWORD dwErrorCode;
4677bffb703SJames Tabor WINSPOOL_FORM_CONTAINER FormInfoContainer;
4687bffb703SJames Tabor PSPOOLER_HANDLE pHandle = (PSPOOLER_HANDLE)hPrinter;
4697bffb703SJames Tabor
47046b91659SColin Finck TRACE("SetFormW(%p, %S, %lu, %p)\n", hPrinter, pFormName, Level, pForm);
4717bffb703SJames Tabor
4727bffb703SJames Tabor // Sanity checks.
4737bffb703SJames Tabor if (!pHandle)
4747bffb703SJames Tabor {
4757bffb703SJames Tabor ERR("Level = %d, unsupported!\n", Level);
4767bffb703SJames Tabor dwErrorCode = ERROR_INVALID_HANDLE;
47746b91659SColin Finck return FALSE;
47846b91659SColin Finck }
4797bffb703SJames Tabor
4807bffb703SJames Tabor FormInfoContainer.FormInfo.pFormInfo1 = (WINSPOOL_FORM_INFO_1*)pForm;
4817bffb703SJames Tabor FormInfoContainer.Level = Level;
4827bffb703SJames Tabor
4837bffb703SJames Tabor // Do the RPC call
4847bffb703SJames Tabor RpcTryExcept
4857bffb703SJames Tabor {
4867bffb703SJames Tabor dwErrorCode = _RpcSetForm(pHandle->hPrinter, pFormName, &FormInfoContainer);
4877bffb703SJames Tabor }
4887bffb703SJames Tabor RpcExcept(EXCEPTION_EXECUTE_HANDLER)
4897bffb703SJames Tabor {
4907bffb703SJames Tabor dwErrorCode = RpcExceptionCode();
4917bffb703SJames Tabor }
4927bffb703SJames Tabor RpcEndExcept;
4937bffb703SJames Tabor
4947bffb703SJames Tabor SetLastError(dwErrorCode);
4957bffb703SJames Tabor return (dwErrorCode == ERROR_SUCCESS);
4967bffb703SJames Tabor }
497