I'm writing open source C# Ghostscript wrapper. You can try it and take a look at (http://ghostscriptnet.codeplex.com). Most of the functionality is implemented and it works on both versions (x86/x64). The problem i'm having is when i'm initializing a display device to render pdf directly to the screen (i successfully implemented gsapi_set_display_callback callback). Arguments that i'm using are following: string[] args = new string[] { "", "-sDEVICE=display", "-dTextAlphaBits=4", "-dGraphicAlphaBits=4", "-dDisplayHandle=1234", "-dDisplayResolution=72", "-dDisplayFormat=" + ((int)DISPLAY_FORMAT_COLOR.DISPLAY_COLORS_RGB | (int)DISPLAY_FORMAT_ALPHA.DISPLAY_ALPHA_NONE | (int)DISPLAY_FORMAT_DEPTH.DISPLAY_DEPTH_8 | (int)DISPLAY_FORMAT_ENDIAN.DISPLAY_LITTLEENDIAN | (int)DISPLAY_FORMAT_FIRSTROW.DISPLAY_BOTTOMFIRST).ToString() }; This arguments works well on 32 bit version and i'm able to render pdf page to the screen. Initialization works fine. When i switch to the 64 bit version i get typecheck (e_typecheck = -20) error. I know that 64 bit version uses -sDisplayFormat and i tried that also but with no luck. Anyone has any idea how to initialize device as display on 64 bit version Ghostscript library? I dont think i'm missing something. Is this a bug in 64 bit version of the ghostscript library? I tried earlier versions of Ghostscript library and i get a same error on 64 bit version. Current version that i use is 9.09. Class where you can take a look at the code: https://ghostscriptnet.codeplex.com/SourceControl/latest#Ghostscript.NET/Ghostscript.NET/Viewer/GhostscriptViewer.cs
I'm not a C# programmer. I'm prepared to look at the problem, and I can at least run a C# app under the debugger. However, I only have the express version of VS 2012 and when I try to load your application it gives me a number of warnings and errors, and then crashes Visual Studio. I doubt that I need the full complexity of your application to investigate this. Can you please instead supply a minimal application to demonstrate the problem. FWIW our own 64-bit executable uses the gsapi_init_with_args routine, so it *does* work under 64-bit Windows.
On 64 bit systems the "DisplayHandle" parameter is a string, because these params are integers which are (mostly) 32 bit. You'll need to convert the pointer value into a string, and pass it with "-sDisplayHandle=<string>" See: http://git.ghostscript.com/?p=ghostpdl.git;a=blob;f=gs/devices/gdevdsp.c and search for "DisplayHandle as a string"
Its also even documented in API.htm: " -sDisplayHandle=1234 Where "1234" is a string. The API was changed to use a string rather than an integer/long value when support for 64 bit systems arrived. A display "handle" is often a pointer, and since these command line options have to survive being processed by Postscript machinery, and Postscript only permits 32 bit number values, a different representation was required." Thanks Chris
Created attachment 10154 [details] Test source code Minimal source code for test.
Thank you, i will check, try what you suggested me and let you know.
This are my 32 bit arguments: string[] args_x86 = new string[] { "", "-sDEVICE=display", "-dTextAlphaBits=4", "-dGraphicAlphaBits=4", "-dDisplayHandle=0", "-dDisplayResolution=72", "-dDisplayFormat=" + ((int)DISPLAY_FORMAT_COLOR.DISPLAY_COLORS_RGB | (int)DISPLAY_FORMAT_ALPHA.DISPLAY_ALPHA_NONE | (int)DISPLAY_FORMAT_DEPTH.DISPLAY_DEPTH_8 | (int)DISPLAY_FORMAT_ENDIAN.DISPLAY_LITTLEENDIAN | (int)DISPLAY_FORMAT_FIRSTROW.DISPLAY_BOTTOMFIRST).ToString() }; And this are 64 bit: string[] args_x64 = new string[] { "", "-sDEVICE=display", "-dTextAlphaBits=4", "-dGraphicAlphaBits=4", "-sDisplayHandle=0", "-dDisplayResolution=72", "-sDisplayFormat=" + ((int)DISPLAY_FORMAT_COLOR.DISPLAY_COLORS_RGB | (int)DISPLAY_FORMAT_ALPHA.DISPLAY_ALPHA_NONE | (int)DISPLAY_FORMAT_DEPTH.DISPLAY_DEPTH_8 | (int)DISPLAY_FORMAT_ENDIAN.DISPLAY_LITTLEENDIAN | (int)DISPLAY_FORMAT_FIRSTROW.DISPLAY_BOTTOMFIRST).ToString() }; 32 bit works file, 64 returns: Unrecoverable error: typecheck in .putdeviceprops I want display handle to be 0.
(In reply to comment #6) > This are my 32 bit arguments: > > string[] args_x86 = new string[] { > "", > "-sDEVICE=display", > "-dTextAlphaBits=4", > "-dGraphicAlphaBits=4", > "-dDisplayHandle=0", > "-dDisplayResolution=72", > "-dDisplayFormat=" + > ((int)DISPLAY_FORMAT_COLOR.DISPLAY_COLORS_RGB | > > (int)DISPLAY_FORMAT_ALPHA.DISPLAY_ALPHA_NONE | > > (int)DISPLAY_FORMAT_DEPTH.DISPLAY_DEPTH_8 | > > (int)DISPLAY_FORMAT_ENDIAN.DISPLAY_LITTLEENDIAN | > > (int)DISPLAY_FORMAT_FIRSTROW.DISPLAY_BOTTOMFIRST).ToString() }; > > And this are 64 bit: > > string[] args_x64 = new string[] { > "", > "-sDEVICE=display", > "-dTextAlphaBits=4", > "-dGraphicAlphaBits=4", > "-sDisplayHandle=0", > "-dDisplayResolution=72", > "-sDisplayFormat=" + > ((int)DISPLAY_FORMAT_COLOR.DISPLAY_COLORS_RGB | > > (int)DISPLAY_FORMAT_ALPHA.DISPLAY_ALPHA_NONE | > > (int)DISPLAY_FORMAT_DEPTH.DISPLAY_DEPTH_8 | > > (int)DISPLAY_FORMAT_ENDIAN.DISPLAY_LITTLEENDIAN | > > (int)DISPLAY_FORMAT_FIRSTROW.DISPLAY_BOTTOMFIRST).ToString() }; > > 32 bit works file, 64 returns: Unrecoverable error: typecheck in > .putdeviceprops > > I want display handle to be 0. Well, 0 is still an integer, not a string..... I *think* you'll need a string containing '0'.
I solved the "string" "number" problem. for 64 bit i'm now using -dDisplayFormat and -dDisplayHandle as suggested in API docs. The error i now get is: -15 **** Unable to open the display device, quitting. Chris, the 0 in this case is a string. For instance: "-sDEVICE=display" - value is string "-sDisplayHandle=0" - value is string "-dDisplayHandle=0" - value is integer
Well, you can get the Ghostscript source, and you can see where the parameter is being read, so you can debug why it's throwing an error. *Or* you could create a very minimal C app which shows the error, so we can debug it.
If it will be easier for you to see my screen, click on this: https://join.me/580-140-202 (it's web broser based screen sharing)
I'm not C/C++ developer, can any of you please try if this works on 64 bit version? char **nargv; char arg1[64]; char arg2[64]; char arg3[64]; code = gsapi_new_instance(&minst, NULL); gsapi_set_stdio(minst, gsdll_stdin, gsdll_stdout, gsdll_stderr); code = gsapi_set_display_callback(minst, &display_callback); sprintf(arg1, "-sDEVICE=display"); sprintf(arg2, "-sDisplayHandle=%d", 0); sprintf(arg3, "-dDisplayFormat=%d", DISPLAY_COLORS_RGB | DISPLAY_ALPHA_NONE | DISPLAY_DEPTH_8 | DISPLAY_LITTLEENDIAN | DISPLAY_BOTTOMFIRST); nargv = (char **)malloc((argc + 4) * sizeof(char *)); nargv[0] = argv[0]; nargv[1] = arg1; nargv[2] = arg2; nargv[3] = arg3; memcpy(nargv + 4, argv + 1, argc * sizeof(char *)); argc += 3; code = gsapi_init_with_args(minst, argc, nargv); Thanks, Josip
(In reply to comment #11) > I'm not C/C++ developer, can any of you please try if this works on 64 bit > version? That doesn't work on either 32 or 64-bits. This works on both: sprintf(arg1, "-sDEVICE=display"); sprintf(arg2, "-sDisplayHandle=%d", 0); sprintf(arg3, "-dDisplayFormat=%d", DISPLAY_COLORS_RGB | DISPLAY_ALPHA_NONE | DISPLAY_DEPTH_8 | DISPLAY_LITTLEENDIAN | DISPLAY_BOTTOMFIRST); nargc = argc + 3; nargv = (char **)malloc((nargc + 1) * sizeof(char *)); nargv[0] = argv[0]; nargv[1] = arg1; nargv[2] = arg2; nargv[3] = arg3; memcpy(&nargv[4], &argv[1], argc * sizeof(char *));
Created attachment 10157 [details] Simple display device test code Yours has a fair amount missing, so I've attached a complete example, which can drop in replacing the existing psi\dwmainc.c source file. You need to use the 64 bit Visual Studio command prompt, and build with: nmake -f psi\msvc.mak DEVSTUDIO= BUILD_SYSTEM=64 WIN64=1 MAKEDLL=0 Running gswin64c.exe after that outputs: GPL Ghostscript GIT PRERELEASE 9.10 (2013-08-14) Copyright (C) 2013 Artifex Software, Inc. All rights reserved. This software comes with NO WARRANTY: see the file PUBLIC for details. code = 0 Which is what I'd expect. So the setting of -sDisplayHandle=0 works as it should. So it would seem something about the C#->C/C++ binding is possibly the culprit. Is it possible the string is being converted to some Unicode variant, rather than being in plain ASCII. Possibly, you could build the GS DLL with the "GS_NO_UTF8=1" setting, thus: nmake -f psi\msvc.mak DEVSTUDIO= BUILD_SYSTEM=64 WIN64=1 MAKEDLL=0 GS_NO_UTF8=1 again in the VS 64 bit tools command prompt window.
Ken, the sample i posted was the sample from the current API doc. Chris, thanks, you were right. I managed to solve my problem by setting aligning fields to the default packing size for the current platform for the display_device structure callback. 32-bit works with A value of 1 indicates that data alignment occurs on byte boundaries. There are no gaps between fields with a packing value of 1. Default is 0 that indicates that the packing alignment is set to the default for the current platform. Packing values of 2 and higher will cause each field to be aligned on a byte offset relative to the beginning of the structure. Therefore, data fields will start on offsets that are multiples of the requested packing value. Thank you both.