External Interfacing

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
6 messages Options
pax
Reply | Threaded
Open this post in threaded view
|

External Interfacing

pax
I need to interface to an external api which returns a pointer to a
struct defined in C. I created a subclass of ExternalStructure and
provide a char/string as the argument for the method call.

<stdcall: FDHardware fdOpen char>
^self invalidCall

When I call this method, I get a walkback: The Specified Procedure
Cannot Be Found. Ok, something is incorrect here and I haven't figured
it out. The C code shows:

fdHardware *fdOpen(char *pPort);

where fdHardware is defined as:

typedef struct
{
        void           *m_pStuff;
} fdHardware;

Any ideas?

Thanks,

pax


Reply | Threaded
Open this post in threaded view
|

Re: External Interfacing

Ian Bartholomew-8
Pax,

> Any ideas?

One common problem, when the argument is any sort of character array, is
that you need to specify if it is ASCII or Unicode (Wide). This is done by
appending an A or W to the function name. e.g. from the image

UserLibrary>>charLower: aCharacter
"Answer the lowercase equivalent of aCharacter. This will be dependent on
the semantics of the
language selected by the user during setup or by using Control Panel.
N.B. We ignore the return value as it will be a pointer to the argument.
LPTSTR CharLower(LPTSTR lpsz); // single character or pointer to string"

<stdcall: char CharLowerA char>
^self invalidCall

So the OS function (in the comment) is CharLower but the definition uses
CharLowerA to indicate that the argument is an ASCII string.

Try using the following in the interface method, you never know...

<stdcall: FDHardware fdOpenA char>
^self invalidCall

Another possibility might be that the arg needs to be defined as "lpstr" or
"lpvoid" or ... Try the above first though.

Ian


Reply | Threaded
Open this post in threaded view
|

Re: External Interfacing

Ian Bartholomew-8
In reply to this post by pax
Pax,

> Any ideas?

One common problem, when the argument is any sort of character array, is
that you need to specify if it is ASCII or Unicode (Wide). This is done by
appending an A or W to the function name. e.g. from the image

UserLibrary>>charLower: aCharacter
"Answer the lowercase equivalent of aCharacter. This will be dependent on
the semantics of the
language selected by the user during setup or by using Control Panel.
N.B. We ignore the return value as it will be a pointer to the argument.
LPTSTR CharLower(LPTSTR lpsz); // single character or pointer to string"

<stdcall: char CharLowerA char>
^self invalidCall

So the OS function (in the comment) is CharLower but the definition uses
CharLowerA to indicate that the argument is an ASCII string.

Try using the following in the interface method, you never know...

<stdcall: FDHardware fdOpenA char>
^self invalidCall

Another possibility might be that the arg needs to be defined as "lpstr" or
"lpvoid" or ... Try the above first though.

Ian


Reply | Threaded
Open this post in threaded view
|

Re: External Interfacing

Blair McGlashan
In reply to this post by pax
"pax" <[hidden email]> wrote in message
news:[hidden email]...

> I need to interface to an external api which returns a pointer to a
> struct defined in C. I created a subclass of ExternalStructure and
> provide a char/string as the argument for the method call.
>
> <stdcall: FDHardware fdOpen char>
> ^self invalidCall
>
> When I call this method, I get a walkback: The Specified Procedure
> Cannot Be Found. Ok, something is incorrect here and I haven't figured
> it out. The C code shows:
>...

The actual name of the procedure exported from the procedure will be
mangled, and will almost certainly not match that in the header file. The
degree of mangling depends on the language (C vs C++), how the function is
declared (its calling convention, _cdecl or _stdcall), and finally how it is
exported. To find out the exact name you really have to use a utility like
'dumpbin' with the /exports flag, but in the case of a C function you could
try just prefixing the name with an underscore, i.e.

 <stdcall: FDHardware fdOpen char>
 ^self invalidCall

Regards

Blair


pax
Reply | Threaded
Open this post in threaded view
|

Re: External Interfacing

pax
"Blair McGlashan" <[hidden email]> wrote in message news:<aa0th7$70451$[hidden email]>...

> "pax" <[hidden email]> wrote in message
> news:[hidden email]...
> > I need to interface to an external api which returns a pointer to a
> > struct defined in C. I created a subclass of ExternalStructure and
> > provide a char/string as the argument for the method call.
> >
> > <stdcall: FDHardware fdOpen char>
> > ^self invalidCall
> >
> > When I call this method, I get a walkback: The Specified Procedure
> > Cannot Be Found. Ok, something is incorrect here and I haven't figured
> > it out. The C code shows:
> >...
>
> The actual name of the procedure exported from the procedure will be
> mangled, and will almost certainly not match that in the header file. The
> degree of mangling depends on the language (C vs C++), how the function is
> declared (its calling convention, _cdecl or _stdcall), and finally how it is
> exported. To find out the exact name you really have to use a utility like
> 'dumpbin' with the /exports flag, but in the case of a C function you could
> try just prefixing the name with an underscore, i.e.
>
>  <stdcall: FDHardware fdOpen char>
>  ^self invalidCall
>
> Regards
>
> Blair


Ok, looks like it's time to install VC++ to look at the *.lib export
table... Arrrrggggghhhh! At least I still get to write smalltalk code.

Thanks


Reply | Threaded
Open this post in threaded view
|

Re: External Interfacing

Bill Schwab-2
> Ok, looks like it's time to install VC++ to look at the *.lib export
> table... Arrrrggggghhhh! At least I still get to write smalltalk code.

No luck with dumpbin?  The attached might help - it uses the MS "Image Help"
(image as in binary/executable, not pictures) library to unmangle names.  I
used it one time, and it worked, but no warranties :)

If you are "reduced" to C/C++ programming, keep extern "C" in mind.  At the
risk of telling you what you already know, it's possible to write functions
that use all C++ features internally but are C-callable (the function
parameters are restricted of course) and therefore relatively easy to call
from Dolphin.

Have a good one,

Bill

--
Wilhelm K. Schwab, Ph.D.
[hidden email]










begin 666 ImageHelpLibrary.cls
M(D9I;&5D(&]U="!F<F]M($1O;'!H:6X@4VUA;&QT86QK(#(P,# @<F5L96%S
M92 T+C Q(B$-"@T*17AT97)N86Q,:6)R87)Y('-U8F-L87-S.B C26UA9V5(
M96QP3&EB<F%R>0T*"6EN<W1A;F-E5F%R:6%B;&5.86UE<SH@)R<-"@EC;&%S
M<U9A<FEA8FQE3F%M97,Z("<G#0H)<&]O;$1I8W1I;VYA<FEE<SH@)R<-"@EC
M;&%S<TEN<W1A;F-E5F%R:6%B;&5.86UE<SH@)R<A#0I);6%G94AE;'!,:6)R
M87)Y(&-O;6UE;G0Z("=4:&ES(&ES('5S969U;"!F;W(@=6YM86YG;&EN9R!-
M4R!#*RL@9G5N8W1I;VX@;F%M97,N)R$-"@T*26UA9V5(96QP3&EB<F%R>2!G
M=6ED.B H1U5)1"!F<F]M4W1R:6YG.B G>T8W0C)$1#(P+3E#04,M,3%$-2TX
M-3DV+3 P,#!"-#E$,D-&,GTG*2$-"@T*(4EM86=E2&5L<$QI8G)A<GD@8V%T
M96=O<FEE<T9O<D-L87-S(55N8VQA<W-I9FEE9"$@(0T*(4EM86=E2&5L<$QI
M8G)A<GD@;65T:&]D<T9O<B$-"@T*=6YM86YG;&4Z;6%N9VQE9$YA;64-"@DB
M06YS=V5R('1H92!U;FUA;F=L960@;F%M92 H86QL(&]P=&EO;G,@96YA8FQE
M9"DB#0H-"@E><V5L9B!U;FUA;F=L93IM86YG;&5D3F%M92!F;&%G<SHP+@T*
M(0T*#0IU;FUA;F=L93IM86YG;&5D3F%M92!F;&%G<SIA;DEN=&5G97(-"@DB
M06YS=V5R('1H92!U;FUA;F=L960@;F%M92(-"@T*"0E\(&%3=')I;F<@? T*
M#0H)85-T<FEN9R Z/2!3=')I;F<@;F5W.C,P,"X-"@ES96QF('5N;F%N9VQE
M.FUA;F=L961.86UE('5N;6%N9VQE9$YA;65"=69F97(Z85-T<FEN9R!U;FUA
M;F=L961"=69F97),96YG=&@Z85-T<FEN9R!S:7IE(&9L86=S.F%N26YT96=E
M<BX-"@T*"5YA4W1R:6YG('1R:6U.=6QL<PT*#0HA#0H-"G5N;F%N9VQE.FUA
M;F=L961.86UE('5N;6%N9VQE9$YA;65"=69F97(Z85-T<FEN9R!U;FUA;F=L
M961"=69F97),96YG=&@Z;&5N9W1H(&9L86=S.F9L86=S#0H)(E5N;6%N9VQE
M('1H92!#*RL@9G5N8W1I;VX@;F%M90T*"0E$5T]21"!)34%'14%022!724Y!
M4$D-"@D)"55N1&5C;W)A=&53>6UB;VQ.86UE* T*"0D)(" @($Q00U-44B @
M($1E8V]R871E9$YA;64L(" @(" @(" @+R\@3F%M92!T;R!U;F1E8V]R871E
M#0H)"0D@(" @3%!35%(@(" @56Y$96-O<F%T961.86UE+" @(" @(" O+R!)
M9B!.54Q,+"!I="!W:6QL(&)E(&%L;&]C871E9 T*"0D)(" @($173U)$(" @
M(%5N9&5C;W)A=&5D3&5N9W1H+" @(" @+R\@5&AE(&UA>&EM>6T@;&5N9W1H
M#0H)"0D@(" @1%=/4D0@(" @1FQA9W,@(" @(" @(" @(" @(" @(" O+R!3
M964@86)O=F4N#0H)(" @("D[#0H)(@T*#0H@(" @/'-T9&-A;&PZ(&1W;W)D
M(%5N1&5C;W)A=&53>6UB;VQ.86UE(&QP<W1R(&QP<W1R(&1W;W)D(&1W;W)D
M/@T*(" @(%YS96QF(&EN=F%L:61#86QL(2 A#0HA26UA9V5(96QP3&EB<F%R
M>2!C871E9V]R:65S1F]R.B C=6YM86YG;&4Z(6]P97)A=&EO;G,A<')I=F%T
M92$@(0T*(4EM86=E2&5L<$QI8G)A<GD@8V%T96=O<FEE<T9O<CH@(W5N;6%N
M9VQE.F9L86=S.B%O<&5R871I;VYS(7!R:79A=&4A("$-"B%);6%G94AE;'!,
M:6)R87)Y(&-A=&5G;W)I97-&;W(Z("-U;FYA;F=L93IU;FUA;F=L961.86UE
M0G5F9F5R.G5N;6%N9VQE9$)U9F9E<DQE;F=T:#IF;&%G<SHA*BUP<FEM:71I
M=F5S(6]P97)A=&EO;G,A<')I=F%T92$@(0T*#0HA26UA9V5(96QP3&EB<F%R
M>2!C;&%S<R!M971H;V1S1F]R(0T*#0IF:6QE3F%M90T*"2)!;G-W97(@=&AE
M(&AO<W0@<WES=&5M(&9I;&4@;F%M92!O9B!T:&4@97AT97)N86P@;&EB<F%R
M>2!W:&EC:"!T:&4@#0H)<F5C96EV97(@<F5P<F5S96YT<R(-"@T*"5XG:6UA
M9V5H;' G#0HA("$-"B%);6%G94AE;'!,:6)R87)Y(&-L87-S(&-A=&5G;W)I
H97-&;W(Z("-F:6QE3F%M92%C;VYS=&%N=',A<'5B;&EC(2 A#0H-"@``
`
end