BBS: Inland Empire Archive Date: 04-24-92 (04:24) Number: 154 From: LAWRENCE GORDON Refer#: NONE To: DARYL POSNETT Recvd: YES Subj: Re: Powerbasic & QuickBa Conf: (2) Quik_Bas
On 04-19-92 Daryl Posnett wrote to Lawrence Gordon... DP> LG>PowerBasic can't use these libraries because of inherent DP> incompatibilities DP> LG>with the BC compiler; yet it has no trouble linking C and ASM .OBJ DP> LG>files, provided that compatible calling conventions and memory models DP> LG>are used. DP> DP> That's good to know, It is a real problem with QB. I have tried to do DP> fun stuff with QB and C, only to end up reaching for the big red switch. Daryl - here's how to link in Turbo C routines with PowerBasic: 1. Set Options/Compiler/Model to Huge. <---necessary 2. Set Options/Compiler/Defines, do nothing here 3. Set Options/Compiler/Code Generation as follows: Calling convention C Instruction set 8088/8086 Floating Point Emulation Default char type Signed Alignment Byte <---necessary Generate underbars OFF <---necessary Merge duplicate strings OFF Standard Stack Frame ON Test stack overflow OFF Line numbers OFF Obj debug information ON <---not necessary 4. Set Options/Compiler/Optimization Optimize for Size Use register variables On Register optimization Off Jump optimization Off 5. Set Options/Compiler/Source Identifier length 32 Nested comments Off ANSI keywords Off 6. Set Options/Compiler/Names/Code Names/Segment name to CSEG. Set Options/Compiler/Names/Code Names/Group name to Set Options/Compiler/Names/Code Names/Class name to (yes, even remove the '*', it defaults to it->*.) 7. Set Options/Compiler/Names/Data names/Segment name to DSEG. Set Options/Compiler/Names/Data Names/Group name to Set Options/Compiler/Names/Data Names/Class name to (yes, even remove the '*', it defaults to it-> *.) 8. Set Options/Compiler/Names/BSS Names/Segment name to Set Options/Compiler/Names/BSS Names/Group name to Set Options/Compiler/Names/BSS Names/Class name to (yes, even remove the '*', it defaults to it-> *.) (not necessary but recommended.) 9. You DO NOT have to Options/Linker/Initialize segments). Map file OFF <---not necessary Initialize segments ON Default libraries OFF Graphics Library ON <---not necessary Warn duplicate symbols OFF Stack warning ON Case-sensitive link ON 10. Set Options/Directories Set this as needed 11. Set Options/Arguments this is not used 12. After selection all your options be sure to save them. Now you can $LINK the .OBJ module into your PB program as usual. Source code is shown below. Here's a simple example of a C function that takes an integer as a parameter, adds 100 to it, and returns it to the PB program: TC: PBINT.C /* compile this to PBINT.OBJ */ int pascal DOCALC (int far *pbvar) { return (*pbvar)+100; } PB: INTEXAMP.BAS $link "pbint.obj" declare function DOCALC%(integer) print DOCALC%(5) 'prints 105 (5+100) Some things to note: the C function is declared to use PASCAL calling conventions (the C function must clean up the stack after the call, not PB, and because of the way C pushes variables onto the stack); the parameter PBVAR is declared to be a far pointer to an integer since PB passes all parameters as far pointers; the function has a return type of INT which causes the returned integer to be placed in the AX register upon return (which is what PB expects of an external function that returns an integer); and PB's DECLARE statement must explicitly specify that the C function is an integer function that takes an integer as a parameter. Here's a simple example of a C routine that changes the first character of a PB string passed to it as a parameter: TC: PBSTRING.C /* compile this to PBSTRING.OBJ */ #include <dos.h> void pascal DOSTR(unsigned far *stseg, unsigned far *stofs, int far *stlen) { char far *stdata; /* will point to actual string data */ if (*stlen) { /* if string length > 0 */ stdata = (char far *) MK_FP(*stseg, *stofs); /* get data pointer */ if (stdata) /* if valid string */ *stdata = 'J'; /* change 1st char of string to 'J' */ } } PB: CSTRING.BAS $link "pbstring.obj" declare sub DOSTR(integer,integer,integer) a$="Hello!" call DOSTR(strseg(a$),strptr(a$),len(a$)) 'pass segment/offset/length print a$ 'will print "Jello!" Note: The C routine must not change the length of the string passed to it. Also, this example works for both regular and flex strings. Larry. ... OFFLINE 1.36 --- Maximus 2.00 * Origin: St. Louis User's Group BBS (1:100/4)
Books at Amazon:
Back to BASIC: The History, Corruption, and Future of the Language
Hackers: Heroes of the Computer Revolution (including Tiny BASIC)
Go to: The Story of the Math Majors, Bridge Players, Engineers, Chess Wizards, Scientists and Iconoclasts who were the Hero Programmers of the Software Revolution
The Advent of the Algorithm: The Idea that Rules the World
Moths in the Machine: The Power and Perils of Programming
Mastering Visual Basic .NET