CSDN首页 空间 新闻 论坛 Blog 下载 读书 网摘 搜索 .NET Java 视频 接项目 求职 在线学习 买书 程序员 通知
山寨机中的战斗机! 程序优化工程师到底对IT界有没有贡献
CSDN社区
搜索 收藏 打印 关闭
CSDN社区 >  PowerBuilder >  API 调用

pb高手

楼主2934046(wy520)2002-11-28 08:55:56 在 PowerBuilder / API 调用 提问

第一次调用VC的dll  
  extern   "C"   _declspec(dllexport)   int   testdll(char   pp[128])  
  {  
  for(int   i=0;i<128;i++)  
  {  
  pp[i]=i;  
  }  
  return   0;  
  }  
  在pb下调用  
  integer   ii  
  char   pp[128]  
  ii=testdll(pp)  
  系统出现参数不对,我该怎样处理????  
  问题点数:20、回复次数:5Top

1 楼ken2002(尖刀)回复于 2002-11-28 08:59:47 得分 20

如何用VC创建可在PB中调用的DLL      
        
     
  DLLs:   An   Overview    
  A   dynamic-link   library   (DLL)   is   an   executable   file   that   acts   as   a   shared   library   of   functions.   Dynamic   linking   provides   a   way   for   a   process   to   call   a   function   that   is   not   part   of   its   executable   code.   The   executable   code   for   the   function   is   located   in   a   DLL,   which   contains   one   or   more   functions   that   are   compiled,   linked,   and   stored   separately   from   the   processes   that   use   them.   DLLs   also   facilitate   the   sharing   of   data   and   resources.   Multiple   applications   can   simultaneously   access   the   contents   of   a   single   copy   of   a   DLL   in   memory.   This   code   can   be   called   from   a   PowerBuilder   program   even   though   it   is   written   in   another   language   such   as   C/C++,   Pascal   or   in   any   other   language   that   supports   the   pascal,   WINAPI   macro   calling   sequence   for   16-bit   and   the   standard   calling   sequence   for   32-bit.    
  Dynamic   linking   differs   from   static   linking   in   that   it   allows   an   executable   module   (either   a   .DLL   or   .EXE   file)   to   include   only   the   information   needed   at   run   time   to   locate   the   executable   code   for   a   DLL   function.   In   static   linking,   the   linker   gets   all   the   referenced   functions   from   the   static   link   library   and   places   it   with   your   code   into   your   executable.   Using   DLLs   instead   of   static   link   libraries   makes   the   size   of   the   executable   file   smaller.   If   several   applications   use   the   same   DLL,   this   can   be   a   big   savings   in   disk   space   and   memory.    
  A   .DLL   file   has   a   layout   very   similar   to   an   .EXE   file,   with   one   important   difference   -   a   DLL   file   contains   an   exports   table.   The   exports   table   contains   the   name   of   every   function   that   the   DLL   exports   to   other   executables.   These   functions   are   the   entry   points   into   the   DLL;   only   the   functions   in   the   exports   table   can   be   accessed   by   other   executables.   Any   other   functions   in   the   DLL   are   private   to   the   DLL.    
  You   can   export   functions   from   a   DLL   with   two   methods:    
  1)   Create   a   module   definition   (.DEF)   file   and   use   the   .DEF   file   when   building   the   DLL.    
  2)   Use   the   keyword   __declspec(dllexport)   in   the   function's   definition.   When   exporting   functions   with   either   method,   make   sure   to   use   the   __stdcall   calling   convention.    
  The   __stdcall   calling   convention   is   used   to   call   Win32   API   functions.    
  __stdcall   pushes   parameters   on   the   stack,   in   reverse   order   (right   to   left)    
  Functions   that   use   this   calling   convention   require   a   function   prototype.   The   following   list   shows   the   implementation   of   this   calling   convention.    
  Element   Implementation    
  Argument-passing   order   Right   to   left.    
  Argument-passing   convention   By   value,   unless   a   pointer   or    
  reference   type   is   passed.    
  Stack-maintenance   responsibility   Called   function   pops   its   own    
  arguments   from   the   stack.    
  Name-decoration   convention   An   underscore   (_)   is   prefixed   to   the    
  name.   The   name   is   followed   by   the   at    
  sign   (@)   followed   by   the   number   of    
  bytes   (in   decimal)   in   the   argument   list.    
  Therefore,   the   function   declared   as    
  int   func(   int   a,   double   b   )   is   decorated    
  as   follows:   _func@12    
  Case-translation   convention   None    
  Example    
  In   the   following   example,   use   of   __stdcall   results   in   all   WINAPI   function   types   being   handled   as   a   standard   call:    
  //   Example   of   the   __stdcall   keyword    
  #define   WINAPI   __stdcall    
  Export   from   a   DLL   Using   .DEF   Files    
  The   most   common   methods   for   exporting   a   definition:    
  1.The   __declspec(dllexport)   keyword   in   the   source   code    
  2.An   EXPORTS   statement   in   a   .DEF   file    
  You   can   export   data,   functions,   classes,   or   class   member   functions   from   a   DLL   by   using   the   __declspec(dllexport)   keyword.   If   you   use   __declspec(dllexport),   you   do   not   need   a   .DEF   file   for   exports.    
  To   export   functions,   the   __declspec(dllexport)   keyword   must   appear   to   the   left   of   the   calling-convention   keyword,   if   a   keyword   is   specified.   For   example:    
  void   __declspec(dllexport)   __cdecl   Function1(void);    
  To   export   all   the   public   data   members   and   member   functions   in   a   class,   the   keyword   must   appear   to   the   left   of   the   class   name   as   follows:    
  class   __declspec(dllexport)   CExampleExport   :   public   CObject    
  {   ...   class   definition   ...   };    
  When   building   your   DLL,   you   typically   create   a   header   file   that   contains   the   function   prototypes   and/or   classes   you   are   exporting,   and   add   the   __declspec(dllexport)   to   the   declarations   in   the   header   file.   To   make   your   code   more   readable,   define   a   macro   for   __declspec(dllexport)   and   then   use   the   macro   with   each   symbol   you   are   exporting:    
  #define   DllExport   __declspec(   dllexport   )    
  Pros   and   Cons   of   Using   __declspec(dllexport)    
  Using   __declspec(dllexport)   is   convenient   because   you   do   not   have   to   worry   about   maintaining   a   .DEF   file   and   obtaining   the   decorated   names   of   the   exported   functions.   However,   you   do   not   have   control   over   the   export   ordinals   that   the   compiler   generates.   This   method   is   suitable   if,   for   example,   you   are   designing   a   DLL   for   use   with   an   application   that   you   control;   if   you   rebuild   the   DLL   with   new   exports,   you   will   also   have   to   rebuild   the   application.    
  Exporting   functions   using   .DEF   file    
  A   module-definition   (.DEF)   file   is   a   text   file   containing   one   or   more   module   statements   that   describe   various   attributes   of   a   DLL.   If   you   are   not   using   the   __declspec(dllexport)   keyword   to   export   the   DLL's   functions,   then   the   DLL   requires   a   .DEF   file.    
  A   minimal   .DEF   file   must   contain   the   following   module-definition   statements:    
  The   first   statement   in   the   file   must   be   the   LIBRARY   statement.   This   statement   identifies   the   .DEF   file   as   belonging   to   a   DLL.   The   LIBRARY   statement   is   followed   by   the   name   of   the   DLL.   The   linker   places   this   name   in   the   DLL's   import   library.    
  The   EXPORTS   statement   lists   the   names   and,   optionally,   the   ordinal   values   of   the   functions   exported   by   the   DLL.   You   assign   the   function   an   ordinal   value   by   following   the   function's   name   with   an   at   sign   (@)   and   a   number.   When   you   specify   ordinal   values,   they   must   be   in   the   range   1   through   N,   where   N   is   the   number   of   functions   exported   by   the   DLL.    
  Although   not   required,   typically   a   .DEF   file   also   contains   a   DESCRIPTION   statement   that   describes   the   purpose   of   the   DLL.    
  For   example,   a   DLL   that   contains   the   code   to   implement   a   binary   search   tree   might   look   like   the   following:    
  Top

2 楼ken2002(尖刀)回复于 2002-11-28 09:00:20 得分 0

LIBRARY   BTREE    
  DESCRIPTION   "Implements   a   binary   tree."    
  EXPORTS    
  Insert   @1    
  Delete   @2    
  Member   @3    
  Min   @4    
  If   you   are   exporting   functions   in   a   C++   file,   you   will   have   to   either   place   the   decorated   names   in   the   .DEF   file   or   define   your   exported   functions   with   standard   C   linkage   by   using   extern   "C".   If   you   need   to   place   the   decorated   names   in   the   .DEF   file,   you   can   obtain   them   by   using   the   tool   DUMPBIN   or   by   using   the   linker   switch   /MAP.   Note   that   the   decorated   names   produced   by   the   compiler   are   compiler   specific.   If   you   place   the   decorated   names   produced   by   the   Visual   C++   compiler   into   a   .DEF   file,   applications   that   link   to   your   DLL   must   also   be   built   using   the   same   version   of   Visual   C++   so   that   the   decorated   names   in   the   calling   application   match   the   exported   names   in   the   DLL's   .DEF   file.    
  When   building   the   DLL,   the   linker   uses   the   .DEF   file   to   create   an   export   (.EXP)   file   and   an   import   library   (.LIB)   file.   The   linker   then   uses   the   export   file   to   build   the   .DLL   file.   Executables   that   implicitly   link   to   the   DLL   link   to   the   import   library   when   they   are   built.    
  Note   :   When   porting   DLL   source   code   from   Win16   to   Win32,   replace   each   instance   of   __export   with   __declspec(dllexport).    
  Pros   and   Cons   of   Using   .DEF   Files    
  Exporting   functions   in   a   .DEF   file   gives   you   control   over   what   the   export   ordinals   are.   When   you   add   additional   exported   functions   to   your   DLL,   you   can   assign   them   higher   ordinal   values   (higher   than   any   other   exported   function).   When   you   do   this,   applications   using   implicit   linking   do   not   have   to   relink   with   the   new   import   library   that   contains   the   new   functions.   This   is   very   important,   for   example,   if   you   are   designing   a   third-party   DLL   for   use   by   many   applications.   You   can   continue   to   enhance   your   DLL   by   adding   additional   functionality   while   at   the   same   time   ensuring   that   existing   applications   will   continue   to   work   properly   with   the   new   DLL.    
  Another   advantage   to   using   a   .DEF   file   is   that   you   can   export   functions   using   the   NONAME   attribute,   which   places   only   the   ordinal   in   the   exports   table   in   the   DLL.   For   DLLs   with   a   large   number   of   exported   functions,   using   the   NONAME   attribute   can   reduce   the   size   of   the   DLL   file.    
  The   major   disadvantage   of   using   .a   DEF   file   is   that   if   you   are   exporting   functions   in   a   C++   file,   you   will   either   have   to   place   the   decorated   names   in   the   .DEF   file   or   define   your   exported   functions   with   standard   C   linkage   by   using   extern   "C"   to   avoid   the   name   decoration   done   by   the   compiler.    
  If   you   need   to   place   the   decorated   names   in   the   .DEF   file,   you   can   obtain   them   by   using   the   tool   DUMPBIN   or   by   using   the   link   switch   /MAP.   Note   that   the   decorated   names   produced   by   the   compiler   are   compiler   specific.    
  To   determine   which   method   to   use   to   export   functions   (a   .DEF   file   or   the   __declspec(dllexport)   keyword),   answer   the   following   questions:    
  1/   Will   you   be   continuing   to   add   additional   exported   functions?    
  2/   Who   is   using   your   DLL?   For   example,   is   it   a   third   party   DLL   used   by   many   executables   that   you   cannot   rebuild,   or   is   the   DLL   used   only   by   applications   that   you   can   easily   rebuild?    
  Writing   a   source   code    
  .C   or   .CPP   file    
  #include   <windows.h>    
  #include   "first.h"    
  long   __declspec(dllexport)   __stdcall   foo3(long   mylong1,   long   mylong2,long   mylong3)    
  {    
  long   calc;    
  calc   =   (mylong1   +   mylong2   +   mylong3);    
  return(calc);    
  };    
  short   __declspec(dllexport)   __stdcall   foo4(long   arg1,   long   arg2)    
  {    
  short   rtn;    
  if   (arg1   >   arg2)    
  rtn   =   1;    
  else    
  rtn   =   0;    
  if   (arg1   ==   arg2)    
  rtn   =   2;    
  return(rtn);    
  };    
  void   __declspec(dllexport)   __stdcall   foo5(void   *   p_structure)    
  {    
  strFromPB   *   pb_struct;    
  pb_struct   =   (strFromPB   *)   p_structure;    
  pb_struct->val1   =   pb_struct->val1   -   1;    
  pb_struct->val2   =   pb_struct->val2   +   1;    
  }    
  Header   File    
  //Includes   functions   declarations,   variables   and   structures   declaration   and   //initialization.    
  long   __declspec(dllexport)   __stdcall   foo3(long   mylong1,   long    
  mylong2,long   mylong3);    
  short   __declspec(dllexport)   __stdcall   foo4(long   arg1,   long   arg2);    
  void   __declspec(dllexport)   __stdcall   foo5(void   *   strFromPB);    
  typedef   struct   mystruct{    
  long   val1;    
  long   val2;    
  }   strFromPB;    
  .Def   file    
  //"Undecorates   "   functions   names   decorated   by   __stdcall    
  LIBRARY   first.dll    
  EXPORTS   foo3   =   _foo3@12    
  EXPORTS   foo4   =   _foo4@8    
  EXPORTS   foo5   =   _foo5@4    
  In   PowerBuilder    
  Note:   the   name   of   the   function   used   in   the   declaration   section   should   be   the   same   as   exported   function   name.   If   the   .DEF   file   was   not   included   within   the   .DLL,   the   function   will   be   exported   decorated   and   has   to   be   prototyped   decorated   as   well.    
  If   you   are   using   some   third   party   DLLs   and   rae   not   sure   how   the   function   you   are   calling   is   exported,   you   can   use   Exported   Function   section   of   Quick   View.    
  Top

3 楼ken2002(尖刀)回复于 2002-11-28 09:00:30 得分 0

//Prototype   function   call   in   Local   or   Global   External   Functions   Declaration   section:    
  FUNCTION   Int   foo4(   long   arg1,   long   arg2)   Library"d:\API   CALLS\first.dll"    
  FUNCTION   Long   foo3(   long   arg1,   long   arg2,   long   arg3)Library"d:\API   CALLS\first.dll"    
  SUBROUTINE   foo5(ref   mystruct   struct2)LIBRARY"d:\API   CALLS\first.dll"    
  //   Calling   function   foo4()    
  Integer   li_rtn    
  Long   ll_arg1,   ll_arg2    
  ll_arg1   =   Long(sle_arg1.text)    
  ll_arg2   =   Long(sle_arg2.text)    
  li_rtn   =   foo4(ll_arg1,   ll_arg2)    
  st_result.text   =   String(li_rtn)    
  //Calling   function   foo3()    
  Long   ll_arg1,   ll_arg2,   ll_arg3,   ll_rtn    
  ll_arg1   =   Long(sle_arg1.text)    
  ll_arg2   =   Long(sle_arg2.text)    
  ll_arg3   =   Long(sle_arg3.text)    
  ll_rtn   =   foo3(ll_arg1,   ll_arg2,   ll_arg3)    
  st_result.text   =   String(ll_rtn)    
  To   call   subroutine   foo5(),   which   takes   a   structure   by   reference   as   a   parameter,   create   a   structure:    
  mystruct   val1   long    
  val2   long    
  //Calling   subrutine   foo5   from   PowerBuilder    
  mystruct   pb_struct   //Instanciate   mystruct    
  pb_struct.val1   =   long(sle_3.text)    
  pb_struct.val2   =   long(sle_4.text)    
  foo5(pb_struct)    
  //Display   results   of   subroutine   calculations    
  sle_3.text   =   string(pb_struct.val1)    
  sle_4.text   =   string(pb_struct.val2)    
  Setting   the   Byte   Alignment   on   MSVC++    
  Microsoft   compilers   provides   two   methods   to   specify   structure   packing:   a   command-line   option   (/Zp)   and   a   pragma   (pack).    
  When   the   compiler   packs   a   structure,   it   aligns   the   elements   of   the   structure   on   a   1-,   2-,   or   4-byte   boundary   in   memory.    
  An   application   can   use   packing   for   indexing   purposes   or   to   decrease   processor   access   time.    
  Unless   an   application   specifies   a   different   value,   the   default   structure   packing   value   is   two.    
  The   field   size   and   packing   value   determine   the   amount   of   padding   required   before   a   field   appears   in   the   structure.    
  The   padding   can   change   the   offset   of   a   particular   member   of   the   structure.    
  The   compiler   calculates   each   offset   of   a   structure   member   relative   to   zero   (0).   The   compiler   compares   the   size   of   each   member   to   the   packing   value   (which   is   also   known   as   the   alignment   value).   The   compiler   aligns   the   element   on   the   boundary   of   the   smaller   of   the   field   size   and   the   packing   value.    
  Finally,   the   compiler   can   pad   the   entire   structure   to   properly   align   arrays   of   structures.   The   compiler   usually   pads   all   structures   to   a   multiple   of   the   packing   size.   However,   if   the   specified   packing   size   is   four,   but   the   structure   does   not   contain   any   element   larger   than   2   bytes,   the   structure   is   padded   to   a   multiple   of   two.    
  The   structures   are   not   packed   to   a   multiple   of   the   packing   size   whenever   the   structure   does   not   contain   any   elements   (or   elements   of   arrays)that   are   equal   to   or   greater   than   the   packing   size.   For   example,   structs   of   just   chars   or   arrays   of   chars   are   never   padded.    
  Powerbuilder   favores   when   dlla   are   compiled   with   1-byte   alignment.    
   
  Select   the   desired   target   from   MSVC    
  Right   mouse   click   and   select   Settings    
  Select   the   C/C++   tabpage    
  Select   Code   Generation   from   the   Category   dropdown   list    
  Select   desired   byte   alignment   from   the   Struct   Member   Alignment   dropdown   list.    
   
  Glossary:    
  Stack   is   a   region   of   reserved   memory,   organized   as   a   stack,   in   which   programs   temporarily   store   status   data   such   as   procedure   and   function   call   return   addresses,   passed   parameters,   and   local   variables.    
  stack   frame   -   or   frame   allocation.   An   area   of   memory   set   up   whenever   a   function   is   called   that   temporarily   holds   the   arguments   to   the   function   as   well   as   any   variables   that   are   defined   local   to   the   function.   There   are   two   key   characteristics   of   frame   allocations.   First,   when   a   local   variable   is   defined,   enough   space   is   allocated   on   the   stack   frame   to   hold   the   entire   variable,   even   if   it   is   a   large   array   or   data   structure.   Second,   frame   variables   are   automatically   deleted   when   they   go   out   of   scope  
  References:  
  Technical   Document   44474:   External   Function   Calls;  
  Technical   Document   44538:   Passing   a   32-bit   PowerBuilder   structure   to   a   32-bit   C   DLL   Created   in   Power++;    
  Top

4 楼2934046(wy520)回复于 2002-11-28 09:06:23 得分 0

请问在我这个例子里,该如何处理?????  
  Top

5 楼jonseyc(chinasms)回复于 2002-11-28 09:12:12 得分 0

在函数前面加上win即可Top

相关问题

  • pb and com
  • pb+oracle
  • PB 9.0 ?
  • pb+flash
  • PB+Flash.ocx
  • pb打印
  • PB同mail
  • PB与Web
  • pb 难否?
  • 放弃PB!!!

关键词

  • 32-bit
  • pb
  • mylong
  • dllexport
  • strfrompb
  • declspec
  • rtn
  • stdcall foo
  • val
  • long

得分解答快速导航

  • 帖主:2934046
  • ken2002

相关链接

  • PowerBuilder类图书
  • PowerBuilder类源码下载

广告也精彩

反馈

请通过下述方式给我们反馈
反馈
提问
网站简介|广告服务|VIP资费标准|银行汇款帐号|网站地图|帮助|联系方式|诚聘英才|English|问题报告
北京创新乐知广告有限公司 版权所有, 京 ICP 证 070598 号
世纪乐知(北京)网络技术有限公司 提供技术支持
Copyright © 2000-2008, CSDN.NET, All Rights Reserved
GongshangLogo