Re: [fpc-pascal] Archive libraries
Tomas Hajny: > There are 3rd party Pascal units supporting work with > other archive formats (mostly listing and decompression) > either using shared libraries, or containing direct > implementation of certain functionality (there has been > e.g. unrar.pas containing a port of the original C > implementation to Pascal, although it wouldn't support > current RAR format versions) and which might be compiled > with FPC rather easily, but you're on your own there, of > course. As a last resort, one might invoke the required archiver executable, passing to it any necessary parameters. Far Manager's MultiArc universal plugin works exactly that way, and is easily configurable via invocation patterns with macros. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] [OT] inline procedures in TP 7.0
Florian Klampfl to Anton Shepelev: > > What about the other registers -- does Turbo Pascal take > > care of them, perhaps enveloping each expansion of an > > inline procedure into a POPs and PUSHes? > > No. Thank you for the reply, Florian. Does that mean that I must take utmost care to preserve every single register when using inline procedures and functions? -- Please, do not forward replies to the list to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
[fpc-pascal] [OT] inline procedures in TP 7.0
Hello, all I don't know a better place to ask this, and beg your pardon for an off-topic post. The Language Guide for Turbo Pascal 7.0 has this to say about `inline' statements and proceudres: When a normal procedure or function is called, the com- piler generates code that pushes the procedure's or function's parameters onto the stack and then generates a CALL instruction to call the procedure or function. When you call an inline procedure or function, the com- piler generates code from the inline directive instead of the CALL. Therefore, an inline procedure or function is expanded every time you refer to it, just like a macro in assembly language. [...] With inline directives, you can write procedures and functions that expand into a given sequence of machine code instructions whenever they are called. These are comparable to macros in assembly language. [...] Registers BP, SP, SS, and DS must be preserved by inline statements: all other registers can be modified. But which registers shall be preserved by inline proceudres and functions? In this example from the manual, the SP register is not preserved within the statement: function LongMul(X, Y: Integer): Longint; inline ( $5A/{POP AX} $58/{POP DX} $F7/$EA); {IMUL DX} Does it mean it shall reset SP to a position before the parameters? What about the other registers -- does Turbo Pascal take care of them, perhaps enveloping each expansion of an inline procedure into a POPs and PUSHes? -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] FpWaitPid() multiplies status by 256
Marco van de Voort to Anton Shepelev: > > may return the status multiplied by 256? If my child > > process terminates with Halt(1), the status is 256, if > > with Halt(2), the status is 512, etc. > > Entirely normal. Status is an opague format in POSIX, and > there are macros to pry them apart. Thank you. -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Order of Precedence: FPC/Delphi vs Java
Bernd Oppolzer: > The story is documented in more detail here (including the > Pascal source code of the rounding function): > > http://bernd-oppolzer.de/job9i032.htm Wirth introduced the capitalisation of keywords, and you have decided to invert his style and capitalise everything except keywords? -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
[fpc-pascal] FpWaitPid() multiplies status by 256
Hello, all Can anybody suggest why the function function FpWaitPid ( pid: TPid; var Status: cint; Options: cint ): TPid; may return the status multiplied by 256? If my child pro- cess terminates with Halt(1), the status is 256, if with Halt(2), the status is 512, etc. I am sorry to say that I observe it with an old version of FPC -- 2.6.4+dfsg-4, be- cause it is installed on the remote machine with Debian/GNU Linux 8 that I use over SSH. I have requested the maintain- er to upgrade FPC and, if or when he complies, I will test again. -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Custom file drivers
Marco van de Voort to Anton Shepelev: > > The documentation on the FILE and TEXT types > > says that "nothing prevents the programmer, from > > writing a file driver that stores its data for > > instance in memory." Is there a more detailed > > instruction or an example illustrating how to do > > it? > > Have a look at unit streamio in package fcl-base > (packages/fcl-base/src) which redirects a textfile > to a stream. Thanks. That one works with TEXT overriding its functions openfunc, inoutfunc, flushfunc, and closefunc, whereas the structure FileRec has none of them and contains only a THandle member. Does that mean that one can write a custom driver for TEXT but not for FILE? -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
[fpc-pascal] Custom file drivers
Hello, all The documentation on the FILE and TEXT types says that "nothing prevents the programmer, from writing a file driver that stores its data for instance in memory." Is there a more detailed instruction or an example illustrating how to do it? -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] TP compatibility: procedural type
Sven Barth: > The modes are for the case have code written for > other compilers (TP, MacPas, Delhi, ISO) work in > FPC (as good as reasonably possible). We do howev- > er *not* guarantee that code written in one of > these modes with FPC compiles or runs with the > corresponding compiler. Thank you and others for your explanations. I have a related question which seems unworthy of a new thread. I can't compile this program with -Miso: Program Test; var object: integer; begin end. Free Pascal tells me that test.pas(2,5) Fatal: Syntax error, "identifier" expected but "OBJECT" found. According to the documentation, in this mode the compiler complies with the requirements of level 0 and level 1 of ISO/IEC 7185. but ISO/IEC 7185 does not list 'object' as a re- served word. I have also failed to find an -M fea- ture responsible for the support of stack-based ob- jects. How can I disable it? -- Please, do not forward replies to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] TP compatibility: procedural type
Karoly Balogh to Anton Shepelev: >>But this is from the Language guide -- a document >>that descrbes the language in a platform-agnostic >>way... > >Then you have a very different TP manual than me. >Mine is really only for the specific 16-bit case, >and there is no platform agnostic allowance how it >would work on 32/64-bit in that manual. (or even in >different 16-bit models than implemented, e.g. >huge, something they did know, since Turbo C++ has >it) I used this one: http://turbopascal.org/files/Turbo_Pascal_Version_7.0_Language_Guide_1992.pdf and the built-in TP documentation: http://putka.upm.si/langref/turboPascal/ Neither source makes any exceptions about the 'far' and 'near' reserved words. Thence I concluded that even though on some platforms these concepts may be useless, they are still part of the Turbo Pascal language and shall be used as described regarldess of architecture even if for cross-platform compati- bility. I now see from other replies that the -Mtp mode helps compile TP programs in FPC but not vice versa, which makes me wonder why pointer arithmetics is so limited in -Mtp that one must use Inc and Dec in- stead of the direct '+' and '-' operators. -- Please, do not forward replies to the list to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] TP compatibility: procedural type
Karoly Balogh to Anton Shepelev: >>According to Borland's official language guide to >>Turbo Pascal 7.0, >> >> To be used as procedural values, procedures and >> functions must be declared with a 'far' directive >> or compiled in the '{$F+}' state. >> >>whereas Free Pascal in -Mtp seems to accept any >>non-system procedure or function as a value of a >>procedural type. Is it an instance of TP incompat- >>ibilty or am I missing something? > >It's documented, that Free Pascal ignores far and >near directives because they were for 16bit code, >and have no meaning in 32bit or 64bit code: > > https://www.freepascal.org/docs-html/user/usersu82.html > >Therefore it's logical that the compiler also ig- >nores their absence. Ignoring them in the sense of not affecting the gen- erated machine code is perfectly OK, but not requir- ing their presence in the source, to make the pro- gram compilable in Turbo Pascal, seems wrong when Free Pascal is in Turbo Pascal mode. A program that Free Pascal compiles successfully in TP mode should work with the actual Turbo Pascal compiler. Is it not the purpose of these modes? Do they guarranty only forward-compatibility? >Although this documentation should probably be up- >dated, because we now support some 16bit and 8bit >systems as well. There is more to correct, e.g.: In Free Pascal, you need to use the address @ opera- tor when assigning procedural variables. This is not true of TP mode. >But I'm pretty sure you can find a bunch of other >things, which FPC allows even in TP mode, but TP >disallows/doesn't support, just because the amount >of extra features in the language since TP was >out... I think such features should be available in Delphi and FPC modes, but not in TP, which should implement and enforce Pascal in exactly the way it was sup- ported in the historical Turbo Pascal compiler. -- Please, do not forward replies to the list to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] TP compatibility: procedural type
Sven Barth to Anton Shepelev: >>According to Borland's official language guide to >>Turbo Pascal 7.0, >> >> To be used as procedural values, procedures and >> functions must be declared with a 'far' direc- >> tive or compiled in the '{$F+}' state. >> >>whereas Free Pascal in -Mtp seems to accept any >>non-system procedure or function as a value of a >>procedural type. Is it an instance of TP incom- >>patibilty or am I missing something? > >That would probably be only relevant on i8086. All >the other targets don't have the distinction in >"near" and "far", so it's not necessary to artifi- >cially restrict everything. But this is from the Language guide -- a document that descrbes the language in a platform-agnostic way, except when the contrary is explicitly inidi- cated. Where Turbo Pascal did not accept a proce- dure without the 'far' modifier, one should expect Free Pascal to reject it also in 'TP' mode. -- Please, do not forward replies to the list to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
[fpc-pascal] TP compatibility: procedural type
Hello, all. According to Borland's official language guide to Turbo Pascal 7.0, To be used as procedural values, procedures and functions must be declared with a 'far' directive or compiled in the '{$F+}' state. whereas Free Pascal in -Mtp seems to accept any non- system procedure or function as a value of a proce- dural type. Is it an instance of TP incompatibilty or am I missing something? -- Please, do not forward replies to the list to my e-mail. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] using exceptions
Marcos Douglas: It's not difficult, but is boring have always a parameter or function return to return an error, and have to verify if error then... if not er- ror... if error and error then... etc If you mean having to write nested IFs to check all the errors, then there are several ways to make the error-checking in several calls linearized: http://www.digipedia.pl/usenet/thread/1169/284/ I prefer using GOTO statements: begin Result := false; // Success flag [...] errMsg := errorOne; if not procOne (...) then GOTO ERROR; errMsg := errTwo; if not procTwo (...) then GOTO ERROR; errMsg := errThree; if not procThree(...) then GOTO ERROR; [...] Result := true ERROR: end This way, the funtion returns an error flag and a correspoinding message, and I prefer it to throwing and catching Exceptions. I even wrap exception- based code using external libraries in such proce- dures to have an easier and cleaner error handling. Also see: http://www.theregister.co.uk/2006/01/11/exception_handling/ Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Forward declarations
Timothy Groves: Can anyone think of a situation in which you would *have* to use forward declared functions? I'm trying to come up with an example for such for my book, and I am drawing a blank. Pascal User Manual and Report says: Procecure (function) identifiers may be used be- fore the procedure (funtion) declaration if there is a forward declaration. Forward decla- rations are necessary to allow mutually recur- sive procedures and functions that are not nest- ed. The form is as follows: procedure Q(X:T); Forward; procedure P(Y:T); begin Q(A) end; procedure Q; { parameters and result types are not repeated } begin P(B) end; But are mutually recursive procedures and func- tions necessary? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Linux - ExecuteProcess versus fpSystem
Felipe Monteiro de Carvalho: If FPC Trunk also does not support this, then I'm sure a patch to improve StringToPPChar would be welcome. I have created issue # 0020279. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Linux - ExecuteProcess versus fpSystem
Andrew Haines: I suspect that the oggenc command is failing because TProcess behind the scenes is splitting --output=outputfile.ogg into two params. Yes, indeed. It is also mentioned on the WIKI: http://wiki.freepascal.org/Executing_External_Programs (see section Parameters which contain spaces (Replacing Shell Quotes) While the documentation on TProcess and fpExecV is more ambiguous: TProcess: If the command to be executed or any of the arguments contains whitespace (space, tab character, linefeed character) it should be enclosed in single or double quotes. fpExecV: In case ComLine is a single string, it will be split out in an array of strings, taking into account common whitespace and quote rules. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Linux - ExecuteProcess versus fpSystem
Marco van de Voort: It should now be possible to pass the parameters to tprocess separated. I don't remember if that change made it to 2.4.4 though, otherwise it will be in 2.6.0. Thanks for letting me know. Is the parameter separation algorithm intentionally made to split partially quoted arguments like '--file=my file'? If not, then, maybe the StringToPPChar() function should be fixed? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
[fpc-pascal] Problem linking a Windows DLL
Hello all, I have a plain Windows DLL made in Visual Studio C++ and working with other C applications. When I try to statically import it into an FPC program I get the following error: An unexpected error occurred while initializ- ing an application 0xc034 When using it dynamically, the LoadLibrary() func- tion returns NilHandle, indicating failure. I have checked that my code works with other DLLs -- kernel32.dll for example. Could you please help me fix make this DLL work with FPC? I can provide both the source and the binary of the DLL and of my program. Thank you in advnace, Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Problem linking a Windows DLL
Ludo Brands: Both errors indicate that the dll couldn't be loaded. Or the dll itself isn't found, or the dll has dependencies (probably c libraries) that aren't found. The DLL does work on another PC, so the problem must be with some dependencies. Many thanks. But how can determine what is missing? Elmar Haneke: Is there in addition an messagebox shown indicat- ing an problem with C runtime? If so you probably need an Manifest file for your FPC application No, there are no other messages. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : [fpc-pascal] Problem linking a Windows DLL
Ludo Brands: Both errors indicate that the dll couldn't be loaded. Or the dll itself isn't found, or the dll has dependencies (probably c libraries) that aren't found. OK, I have found the missing dependency using the Dependency Walker utility. Thank you, Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Linux - ExecuteProcess versus fpSystem
Brian: What's driving me crazy is that running the two commands via ExecuteProcess does the first step OK, but oggenc fails with an exit code of 1, oper- ation not permitted. If I replace the ExecuteProcess with a call to fpSystem, concatenating the CommandString and ParamString with a space as separator and passing that as the command, both steps work just fine. In the case of ExecuteProcess() parameter separation takes place on FPC side, while with fpSystem() the shell is responsible for it. Could a problem with FPC's parameter separation algorithm be causing this? Can you post both the commands you are executing? When I was learing processes, I wrote a unit to exe- cute a command using fpExecv -- just as ExecuteProcess() does. I'll dig it out and we'll see how (and whether) it works with your examples. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Pseudographics in FPC-IDE
Nikolay Nikolov: [kbd_mode] only works on the linux console. It doesn't work under xterm, gnome-terminal, konsole, etc and we still need a way to detect if they are in UTF-8 mode or not. But at least that will make the IDE work correctly in the true console... As for the graphical ones, to assume their mode as UTF-8 is much safer, but the vector fonts may not have the drawing characters anyway... IIRC, it only checks if the keyboard input is in UTF-8 mode. What we actually care about is whether the console output (not input) is in UTF-8 mode. But I guess it's ok to assume that if the input is UTF-8, then then output is also most likely to be UTF-8. As I understand, the console mode defines the way the input bytes are treated all the way from the initial keycode to the charater address in the font. Therefore, it must be taken into account when decid- ing what keycode to send to get an expected charac- ter: http://tldp.org/HOWTO/Keyboard-and-Console-HOWTO-6.html When not in unicode mode, an additional ACM is used to get the Unicode value of a keysym: http://www.tin.org/bin/man.cgi?section=8topic=consolechars I don't like the idea of having to invoke an external program and parse its output, but this could be done by directly invoking the ioctl that kbd_mode uses. Agree. I did mean to mimic the kbd_mode's mechanism of determining the console mode. Do you know how many linux distros (besides Puppy Linux) would need this? When I came up with the 'UTF-8' string check in the LANG variable, I tested Fedora, Ubuntu, openSUSE, Mandriva and Debian and they all worked this way, so I figured it's a de facto standard. No, I haven't done such a research, but I think it would be nice to have the IDE less dependent on the environment settings. Otherwise, this has to be a system requirement for FP-IDE. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Pseudographics in FPC-IDE
Nikolay Nikolov: Basically, all it does is, it checks if the LANG variable contains ґUTF-8' as a substring (not sure if it is the right way to do it, but it works for Fedora, Ubuntu, OpenSUSE, Mandriva and latest Debian) and if it does, it writes UTF-8 characters to the console, by using an internal CP437 to UTF-8 conversion table. Then my guessing was correct, but in this case there is a better solution. Instead of relying on the value of LANG, FP-IDE should directly check the con- sole mode. This can be done using the 'kbd_mode' command. If the mode reported is UTF-8, then use the translation table, otherwise assume CP437. At least, this will make it more reliable with UTF-8 consoles. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Pseudographics in FPC-IDE
Graeme Geldenhuys: You are welcome to add it to the wiki. I still do not fully understand the problem, so please, review what I have come up with: On Linux/Unix the FP-IDE calculates the addresses of the drawing charactes (also called pseudagraphics) based on the LANG environment variable, so for the IDE to work correctly, its value must correspond with the console mode which can be checked using the kbd_mode utility. If the reported console mode is UTF8 then the value of LANG must be of the form: ll_CC.UTF-8. For most cases en_US.UTF-8 should work. Now I don't know for sure what happens with other locales. From my own experiments, in this case the IDE simply tries to get the pseudographics charac- ters from their respective addresses as defined in CP437. Is this correct? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
[fpc-pascal] Pseudographics in FPC-IDE
Hello all, I have installed FPC on a Linux machine to find that in the virtual terminal (true text-mode, not GUI-based emulator) FP-IDE does not dispaly pseudographics correctly. It turned out that changes to the SFM (Screen Font Map) doesn't have any effect inside the IDE, and I count'd understand why. Then, in the WIKI I found this: On a terminal with VGA character set (currently only the Linux console), the video unit will enable the VGA char- acters and use them without translation. which answered my question. My console is in UTF8 mode, using an ISO8859-1 font, while the FP-IDE, as it seems, is accessing pseudographics symbols directly by glyph number (and bypassing the SFM table), expecting them to be at locations specified in the CP437 encoding: http://en.wikipedia.org/wiki/CP437 which means that it will only work with a CP437-encoded font. Why was this done and is there a workaround except re-encod- ing the console font into CP437? Thanks in advance, Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Pseudographics in FPC-IDE
Nikolay Nikolov: Modern FPC versions should support UTF-8 output for the IDE. I made a patch for this, that was included in fpc 2.4.2 IIRC. Which FPC version are you using and on which linux distro/version? What is the value of the LANG envi- ronment variable? I am using FPC 2.4.4 on Puppy Linux. LANG=en_US. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Pseudographics in FPC-IDE
Nikolay Nikolov: Try changing it to LANG=en_US.UTF-8 Thank you very much, it works well now. Maybe this should be mentioned on the WIKI? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Michael Van Canneyt: The interface of the pipes unit can be changed with a parameter with a default value, so existing code continues to work. Yes, but all the platform-specific pipe.inc files and pipes.pp will have to be changed anyway because the CreatePipeHandles will have a different proto- type. I wasn't sure if it would be OK to add a parameter to the definition of a cross-platform function that would be used only on one one platform and ignored on all the other ones. I will write a patch then. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Sorry, I forgot to say the patch is against verstion 2.4.2. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : [fpc-pascal] Redirecting input to a child process
A little update on the subject. Ludo Brands wrote: If you run 'more' in a cmd window you'll notice that 'more' echoes the input but only sends to stdout when a return is entered. I modified the program to send 'Anton'#10 and the program reads back 'Anton'#10 from std- out. After fixing an error in my WinApi program, it is no longer needed to terminate input with #10. Now that the write-end of the child process's input handle is correctly closed, more.com echoes whatever has been written to it requiring no additional terminal symbols. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Ludo Brands: You can file a bug at http://bugs.freepascal.org/. This is bug #0019325. ... I thought about writing a patch, but it seems that it is not enough to modify the implementation of the Windows-specific pipes.inc. The correct way to create pipes for the three channels (out, in and err) on Windows is to create non-inheritable handles and duplicate only the child process's ends of them into inheritable ones, which means that the CreatePipeHandles function must accept a third parameter indicating which end should be inherited: for OUT and ERR channels it will be the write-end and for IN -- the read-end. Here is a possible implementation: {--- changes to pipes.inc -} Interface {...} type TDupOpt = (dupIn, dupOut); TDupOpts = Set of TDupOpt; Implemenation {...} function DuplicateHandleFP(var handle: THandle): Boolean; var oldHandle: THandle; begin oldHandle := handle; Result := DuplicateHandle ( GetCurrentProcess(), oldHandle, GetCurrentProcess(), @handle, 0, true, DUPLICATE_SAME_ACCESS ); if Result then Result := CloseHandle(oldHandle); end; Function CreatePipeHandles (Var Inhandle,OutHandle : THandle; DupOpts: TDupOpts) : Boolean; begin Result := CreatePipe (Inhandle,OutHandle,@piNonInheritablePipe,0); if Result and (dupIn in DupOpts) then Result := DuplicateHandleFP(Inhandle); if Result and (dupOut in DupOpts) then Result := DuplicateHandleFP(OutHandle); end; {--- process.inc -} {CreatePipes will have these calls:} begin CreatePipeHandles(SI.hStdInput ,HI, [dupIn ]); CreatePipeHandles(HO,Si.hStdOutput, [dupOut]); if CE then CreatePipeHandles(HE,SI.hStdError, [dupOut]) {...} Unfortunately, the third parameter will have to be added to this function in all other platform-specific pipes.inc files, but these will just ignore it and work as before. If it is preferable to keep the interface of the pipes unit unchanged, the windows-specific part could just be chaged to create non-inheritable pipes, and the duplication could be moved into the windows-specific process.inc. Will you accept one of such patches? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
[fpc-pascal] Minimal Sylpheed plugin in FreePascal
Hello all, I have tried to create a Windows plugin dll for the Sylpheed e-mail client in FreePascal but couldn't get past a strange side effect: the mere fact of the plugin being loaded makes GTK's window-showing functions crash the whole program. This happens even with the smallest and emptiest plugin pos- sible, when it neither subscribes for any event nor calls any API functions. The minimal plugin only provides minimal implementations of the basic interface functions simply reporting the start of every function to the debug log, which is created when Sylpheed is invoked with the --debug option. Then I tried coding the same plugin in C, using the Tiny C Compiler, and it worked pretty well, wherefrom I concluded that something must be wrong with FreePascal's DLL genera- tion, so I have come here for help. Attached are the C and Pascal sources of the minimal plugin. A package with the same sources plus the binaries can be downloaded here: http://uploadbox.com/files/6d08a0b625/ This is the original report of the problem on the Sylpheed mailing list: http://www.sraoss.jp/pipermail/sylpheed/2011-May/004525.html After I had encountered the problem I started to strip the plugin of its functionality and dependencies until I had the bare skeleton which still didn't work and which I have attached. If you need any further information, please ask. Thanks in advnace, Anton #include io.h #include windows.h typedef void (*TEmptyCallBack)(void); // PEmptyCallBack = ^TEmptyCallBack; typedef char* PGChar; typedef void* GPointer; typedef long GInt; struct SylPluginInfo { PGChar name; PGChar version; PGChar author; PGChar description; pad1, pad2, pad3, pad4; }; typedef struct SylPluginInfo SylPluginInfo; typedef SylPluginInfo* PSylPluginInfo; //Below define is Tiny C Compiler's way of exporting DLL functions #define DLL __attribute__ ((dllexport)) const long SYL_PLUGIN_INTERFACE_VERSION = 0x0107; void plugin_load (void) DLL; void plugin_unload(void) DLL; PSylPluginInfo plugin_info (void) DLL; GInt plugin_interface_version (void) DLL; static SylPluginInfo info = { Test Plugin, 0.0.1, Anton Shepelev, It had better work }; void plugin_load(void) { printf(Ant: loaded.\n); } void plugin_unload(void) { printf(Ant: plugin unloaded.\n); } PSylPluginInfo plugin_info(void) { printf(Ant: Plugin info requested.\n); return (PSylPluginInfo)info; } GInt plugin_interface_version(void) { printf(Ant: Interface version requested.\n); return SYL_PLUGIN_INTERFACE_VERSION; }Library Test; Type TEmptyCallBack = procedure; PEmptyCallBack = ^TEmptyCallBack; PGChar = PChar; GPointer = Pointer; GInt = LongInt; SylPluginInfo = packed record name:PGChar; version: PGChar; author: PGChar; description: PGChar; pad1, pad2, pad3, pad4: GPointer; end; PSylPluginInfo = ^SylPluginInfo; const SYL_PLUGIN_INTERFACE_VERSION = $0107; var PI: SylPluginInfo; Procedure plugin_unload; CDecl; begin WriteLn('Ant: plugin unloaded!'); end; Function plugin_info(): PSylPluginInfo; CDecl; begin WriteLn('Ant: Plugin info is being requested...'); plugin_info := nil; end; Function plugin_interface_version():gint; CDecl; begin WriteLn('Ant: Interface version is being requested...'); plugin_interface_version := SYL_PLUGIN_INTERFACE_VERSION; end; Procedure plugin_load; CDecl; begin WriteLn('Ant: plugin loading...'); pi.name:= 'Test Plugin'; pi.version := '0.0.1'; pi.author := 'Anton'; pi.description := 'It had better work.'; WriteLn('Ant: plugin loaded.'); end; Exports plugin_load, plugin_unload, plugin_info, plugin_interface_version; end. ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Minimal Sylpheed plugin in FreePascal
Jonas Maebe: One likely potential cause is the fact that released FPC versions enable all floating point exceptions. Since libc does not do that, many C programs and frameworks contain invalid floating point operations. Wow! Many thanks. I thought that information would be use- less, but indeed, the crash is due to a floating-point exception. I have Visual Studio at work and it intercepted the error and said it was a floating point exception. And after it has been masked as you suggested my Pascal code works. Do I understand correctly, that at load my library was dis- abling the exception mask for the whole program? Is masking such exceptions a common practice in C? Will it be politically correct to ask the developer to fix the prob- lem? Thank you again, Jonas Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] accessing files from a function
Rainer Stratmann: Alternatively you can make a class or an object with the text variable in it. But if you need to work with only one file, you can get rid of a global variable in the main module by just extracting the relevant functions and the file handle into a separate unit: -- myfile.pas - Unit MyFile; Interface Procedure OpenFile(fullname: ShortString); Function ReadNextLine(): ShortString; Procedure CloseFile(); Function IsFileRead(): Boolean; Implementation var TheFile: TEXT; Procedure OpenFile(fullname: ShortString); begin Assign(TheFile, fullname); Reset(TheFile); end; Function ReadNextLine(): ShortString; var line: ShortString; begin ReadLn(TheFile, line); ReadNextLine := line; end; Procedure CloseFile(); begin Close(TheFile); end; Function IsFileRead(): Boolean; begin IsFileRead := Eof(TheFile); end; end. --- filetest.pas - Program ftest; uses MyFile; begin OpenFile('test.txt'); While not IsFileRead() do WriteLn(ReadNextLine()); CloseFile(); end. -- Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] PChar resize
In addition to what Mattias has said, the following works pretty well: Program StrTest; Var a:Pchar; Begin a:=PChar(nil); Reallocmem(a,20); //ko a[0] := 'A'; a[1] := 'n'; a[2] := 't'; a[3] := Chr(0); WriteLn('Done: ', a); End. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : [fpc-pascal] Redirecting input to a child process
Ludo Brands: You can file a bug at http://bugs.freepascal.org/ OK. Dupicating handles isn't apparently the only solution. The msdn sample creates non-inheritable pipes and hands these handles simply over to createprocess, without duplicating. There are two solutions, but only of them allows detection of EOF. On MSDN there are two examples. In this one: http://msdn.microsoft.com/en-us/library/ms682499(v=vs.85).aspx inheritable pipe handles are created using CreatePipe, just as I was doing in my initial WinApi code and as TProcess is doing. These pipes don't support the detection of EOF. In this one: http://support.microsoft.com/kb/190351/en-us?fr=1 non-inheritable pipes are created by CreatePipe, which are then duplicated into inheritable ones using DuplicateHandle. The duplicates are passed to CreateProcess, while the non- inheritable originals are used by the parent process, allow- ing it to issue EOF by closing them. This is what made my WinApi code work with more.com. You want to pass inheritable handles if you want the child to have full control of the pipe, which apparently isn't needed for RW. A handle must be inheritable in order to be passed from one process to another. There are two ways to make it so: 1. Specify a flag in CreateProcess 2. Duplicate a non-inheritablehandleusing DuplicateHandle The first MSDN example goes the former way and second the latter way. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : RE : RE : RE : [fpc-pascal] Redirecting input to a child process
Ludo Brands: If you need these handles from the child process use: InHnd:=GetStdHandle(STD_INPUT_HANDLE); OutHnd:=GetStdHandle(STD_OUTPUT_HANDLE); ErrHnd:=GetStdHandle(STD_ERROR_HANDLE); Thank you, that's what I need. By the way, it does work in a simple single-process applica- tion: Program Test; uses Windows; var hIn: LongWord; buf: ShortString; bytesRead: LongWord; begin hIn := GetStdHandle(STD_INPUT_HANDLE); while(true) do begin ReadFile(hIn, buf[1], 5, bytesRead, nil); buf[0] := Chr(bytesRead); write(buf); end; end. It is interesting to note that even this code reads input only after Enter is pressed. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
SteveG: Anton - I have attached an extract from some work- ing code (hopefully I didnt remove anything neces- sary) It may help you move on a bit further I turned your piece of code into a complete program, but it didn't work either. In fact, there is not much difference between your program and mine, except that in generality. But I am creating a process with redirected standard handles (poUsePipes) and am sending a tiny five-byte input to it, and expecitng a tiny output, so there's no need in the loop and in the various checks that your program has. Also, your program does not call CloseInput(), which makes me wonder how the process can ever end, because that way it is not going to get a EOF or error 109 (Pipe has been ended) on its standard input. What OS is the code you sent me working on? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
SteveG: This is working on Linux and WinXP I cut what I was hoping was just the relevant code from the unit, so it is missing a bit :) Here's a full program made from this code: http://pastebin.com/id90J1rY It doesn't work for me in WinXP. What about you? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Marco van de Voort: Why do you execute over the shell? You now pipe your information into the shell (since that is what you execute directly), not the program. Thanks for the note, Marco. Unfortunately, replacing that line with the direct path to more.com had no effect. When executing command-line programs via the shell, isn't the shell's input redirected to the program's? I have verified that the program's output is redi- rected to the shell's. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Marco van de Voort: When executing command-line programs via the shell, isn't the shell's input redirected to the program's? Maybe. I'm pretty sure about batchfiles, but never tried programs, that's why I thought I'd mention the observation. My program captures both the standard and error out- put of batchfiles and progams called therefrom just the same way as with regular programs run using the shell. So you don't see any evident errors? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
Marco van de Voort: I played a bit with it, but was unable to make it work. I added a writeln of outstream.size to the running while, and it seems output is written. Many thanks :) If I understood you correctly, you put WriteLn(MoreProcess.Output.Size); inside the waiting loop and it printeda nonzero value. I did the same, but it said zero. Hmmm. I tried actually read- ing the output inside the loop and the Read() function blocked, as expected when there's nothing to read. It seems the program somehow doesn't get the signal to close. (since I can see more.com is still running in the taskmgr) My hypothesis is that the more.com process is blocked at reading standard output, which it doesn't seem to get for some reason. This problem persists with any application expecting standard input, including my own test app. My next step will be to rewrite my original program, that uses plain WinAPI, in C and see what it yields. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
RE : [fpc-pascal] Redirecting input to a child process
Ludo Brands: If you run 'more' in a cmd window you'll notice that 'more' echoes the input but only sends to stdout when a return is entered. I modified the program to send 'Anton'#10 and the program reads back 'Anton'#10 from stdout. Thank you, Ludo, this is great! But why doesn't the process finish? I thought that the clos- ing of the write end of the StdIn pipe handle should cause a EOF to be 'seen' at the read end, but this does not happen. Maybe these's some explicit way to signal end of input? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : [fpc-pascal] Redirecting input to a child process
Ludo Brands: If you run 'more' in a cmd window you'll notice that 'more' echoes the input but only sends to stdout when a return is entered. I modified the program to send 'Anton'#10 and the program reads back 'Anton'#10 from stdout. Connected with this remark, is there a way to get the under- lying StdIn handle in a FreePascal program, so as to read from it per-character, or any other way using the OS's rou- tines? Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
waldo kitty: how about sending the ^Z line the CRLF is being sent to indicate line breaks?? This I had tried even before posting the question :) Ludo Brands: I don't see where you close the mProcess.input. In my original post I call: MoreProcess.CloseInput(); As for the program based on SteveG's code, I tried to keep his code as intact as possible, so I didn't close the input handle in it. Pipes.pp doesn't have any routines to clean up the pipe handles which is according to msdn not good. You mean reading from the pipes after the closing of the child process? According to msdn... the pipe handles should be created non-inheritable in order to detect EOF. Oh, I missed this. My WinApi program creates pipes with: SECURITY_ATTRIBUTES.bInheritHandle = true; in order for the handles to be properly inherited in the child process. That must be my problem. The only other way to do it is to use the DuplicateHandle function which will create in inherarable duplicate of the original handle, that can then be passed to the CreateProcess. The original handle will remain non-inheritable and should trigger EOF on clo- sure. Thank you for your investigation. I'll try duplicating the handles and report the results. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: RE : RE : [fpc-pascal] Redirecting input to a child process
Ludo Brands: Connected with this remark, is there a way to get the underlying StdIn handle in a FreePascal program, so as to read from it per-character, or any other way using the OS's routines? The handles are mProcess.Input.Handle and mProcess.Out- put.Handle I meant the program's own handles. Like instead of doing: Read(input, c); read directly from a handle: Windows.ReadFile(inputHandle, ...); Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Re: [fpc-pascal] Redirecting input to a child process
I wrote: I'll try duplicating the handles and report the results. Yes. It works now. I am creating a non-inheritable handle using CreatePipe, then duplicating it to an inheritable one using DuplicateHandle and pass the duplicate to the CreateProcess funtion. Does this mean that the Windows implementation of TProcess should be rewritten using DuplicateHandle? Thanks everybody for your help. Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal
[fpc-pascal] Redirecting input to a child process
Hello all, I have been experimenting with redirection of stan- dard I/O of child processes using FreePascal 2.4.2 on Windows. I have succeeded in capturing standard input and standard output, but failed to feed my own data to the child's standard input. The child process doesn't seem to receive any input at all, staying blocked forever. At first I thought it was a problem with my usage of WinApi, so I rewrote my program using the TProcess class... just to get the same result. The program feeds 'Anton' to the more.com program and captures part of its output: Program StrRedir; uses Classes, Process, Sysutils; const MaxByte = 255; type TStrBuf = packed record {As a way to read buffers into strings} case Boolean of true: ( size: Byte; buf: array[0..MaxByte] of Char; ); false:( txt: ShortString; ); end; var MoreProcess: TProcess; readCount: integer; strBuf: TStrBuf; begin MoreProcess := TProcess.Create(nil); MoreProcess.CommandLine := 'C:\WINDOWS\system32\cmd.exe /C more'; MoreProcess.Options := [poUsePipes]; MoreProcess.Execute; strBuf.txt := 'Anton'; MoreProcess.Input.Write(strBuf.buf, strBuf.size); MoreProcess.CloseInput(); writeLn('Waiting...');//This never ends while MoreProcess.Running do begin Sleep(50); end; writeLn('Wait finished.'); Sleep(100); strBuf.size := MoreProcess.Output.Read(strBuf.buf, 255); writeLn(strBuf.txt); end. Could you please help me to make it work? Thanks in advance, Anton ___ fpc-pascal maillist - fpc-pascal@lists.freepascal.org http://lists.freepascal.org/mailman/listinfo/fpc-pascal