Página 1 de 2
Usar uma DLL externa
Enviado: 27 Dez 2015 22:54
por Clipper
Boa noite prezados colegas.
Alguém tem um exemplo prático de como fazer uso de uma DLL externa com o Harbour ?
Obrigado e até logo.
Marcelo
Usar uma DLL externa
Enviado: 28 Dez 2015 19:55
por janio
nDll := dllload("Bemafi32.dll")
oRet := DllCall( nDll, 32, "Bematech_FI_DownloadMF", "C:\CriaSoftWare\" + ArquivoDestino )
If oRet != 1
MsgErro()
Endif
DllUnload( nDll )
Usar uma DLL externa
Enviado: 28 Dez 2015 21:40
por JoséQuintas
Jãnio, se não me engano isso faz parte da compatibilidade com xHarbour, não sei se prefere a função direta do Harbour.
Como exemplo, pra pegar o usuário do Windows:
Código: Selecionar todos
FUNCTION mywin_GetUserName()
LOCAL cUserName := Space(255), nSize := 250
CallDll( "GetUserNameA", "advapi32.dll", @cUserName, @nSize )
RETURN AllTrim( cUserName )
No Harbour 3.2 é CallDll32(), e no Harbour 3.4 é CallDll()
Quanto às variáveis, tudo está relacionado com as funções da DLL.
Tem casos em que o parâmetro é do tipo "pointer", igual acima, algo como passar a localização dentro da memória.
Nestes casos o tamanho faz diferença, senão causa GPF porque o resultado pode invadir memória que não deveria..
Nestes casos, é obrigatório passar por referência.
Tem casos aonde é a variável comum, porque vai ser passado somente o conteúdo dela.
E a chamada de DLL também pode retornar um valor.
x = CallDll(...)
Se os parâmetros não estiverem de acordo, tipo de variável/parâmetro, pode gerar GPF.
Usar uma DLL externa
Enviado: 29 Dez 2015 16:07
por asimoes
Código: Selecionar todos
#include "hbdyn.ch"
FUNCTION BaixarURLMON
nHandleDLL:=hb_LibLoad("UrlMon.dll")
nStatus:=hb_dynCall( { "URLDownloadToFileA", nHandleDLL,HB_DYN_CALLCONV_STDCALL},0,"http://www1.caixa.gov.br/loterias/_arquivos/loterias/D_lotfac.zip","D_lotfac.zip",0,0)
hb_LibFree(nHandleDLL)
RETURN Nil
Usar uma DLL externa
Enviado: 29 Dez 2015 16:46
por JoséQuintas
O fonte fica mais enxuto usando a função própria do Harbour
Código: Selecionar todos
UrlDownloadFile( "http://www1.caixa.gov.br/loterias/_arquivos/loterias/D_lotfac.zip", "D_lotfac.zip" )
...
FUNCTION mywin_UrlDownloadToFile( cUrl, cFileName )
LOCAL nErrorCode, pCaller := 0, lpIndStatusCallBack := 0 // para indicador de progresso
nErrorCode := CallDll( "URLDownloadToFileA", "urlmon.dll", pCaller, cURL, cFileName, 0, lpIndStatusCallBack )
RETURN nErrorCode == 0
Usar uma DLL externa
Enviado: 29 Dez 2015 16:56
por asimoes
Quintas,
hb_libLoad é do harbour, se não me engano calldll só na versão 3.2
Usar uma DLL externa
Enviado: 29 Dez 2015 16:57
por asimoes
Segundo o changelog da versão fork:
* contrib/xhb/xhb.hbp
* contrib/xhb/xhb.hbx
+ contrib/xhb/xhbdll.prg
+ added CallDll() compatibility function. Unfortunately it
collides with the name used in hbmisc lib, so use it with
care. [UNTESTED]
Usar uma DLL externa
Enviado: 29 Dez 2015 17:09
por asimoes
CallDll na versão fork só funciona com hbmisc.
Usar uma DLL externa
Enviado: 29 Dez 2015 17:33
por JoséQuintas
O cuidado é por ter CallDll() em hbmisc.lib e xhb.lib, mas diferentes.
changelog:
Criação da CallDll32() no Harbour 3.2
2010-05-27 19:57 UTC+0200 Viktor Szakats (vszakats.net/harbour)
* contrib/hbmisc/Makefile
+ contrib/hbmisc/calldll.prg
+ Added CALLDLL compatibility API interface:
CALLDLL32(), HB_DYNACALL1(), STRPTR(), PTRSTR(), UNLOADALLDLL().
; Lightly tested, it's based on core .dll functions, so it may only
need easy tweaking. Notice that this API support all platforms,
not just 32-bit Windows.
The original library is found in MINIGUI f.e.
Mudança do nome de CallDll32() pra CallDll() já no Harbour 3.4
2013-12-26 13:25 UTC+0100 Viktor Szakáts (vszakats users.noreply.github.com)
* contrib/hbmisc/calldll.prg
* contrib/hbmisc/hbmisc.hbx
* contrib/hbmisc/tests/calldll.prg
+ renamed CallDll32() to CallDll() [INCOMPATIBLE]
; CallDll32() kept for compatibility under HB_LEGACY_LEVEL4
Adição de outra CallDll() pra compatibilidade xHarbour, que resultou em nome repetido
2014-09-17 21:50 UTC+0200 Viktor Szakats (vszakats users.noreply.github.com)
+ contrib/xhb/xhbdll.prg
+ added CallDll() compatibility function. Unfortunately it
collides with the name used in hbmisc lib, so use it with
care. [UNTESTED]
Usar uma DLL externa
Enviado: 29 Dez 2015 18:56
por asimoes
Quintas,
A modificação na versão Fork eu testei com xhb e hbmisc, com xhb não funcionou, com hbmisc funcionou.
Usar uma DLL externa
Enviado: 29 Dez 2015 21:01
por JoséQuintas
É porque são diferentes. Foi isso que o VSzakats alertou no changelog.
Só por curiosidade, a função de compatibilidade está em contrib\xhb\xhbdll.prg
Código: Selecionar todos
#include "hbdyn.ch"
/* NOTE: This compatibility function is clashing with a function
using a similar name but different parameter list in hbmisc */
FUNCTION CallDll( pFunc, ... )
RETURN iif( Empty( pFunc ),, hb_DynCall( { pFunc, HB_DYN_CALLCONV_STDCALL }, ... ) )
Essa foi criada apenas pra compatibilidade com xHarbour.
Acho que é a única função repetida que existe no Harbour, em bibliotecas diferentes.
Não sei se basta colocar a hbmisc.lib antes de xhb.lib pra evitar essa função diferente.
A intenção da biblioteca de compatibilidade é pra conversão inicial, não pra ser usada pra sempre, acho que por isso foi mantido o mesmo nome.
Mas é um negócio perigoso manter duas funções diferentes com nome igual.
Usar uma DLL externa
Enviado: 29 Dez 2015 21:08
por asimoes
Quintas,
Isso mesmo, testei agora hbmisc antes de xhb funcionou.
Usar uma DLL externa
Enviado: 29 Dez 2015 21:10
por asimoes
O interessante neste caso é que não dá erro na compilação sobre nome de função duplicada.
Usar uma DLL externa
Enviado: 30 Dez 2015 01:39
por JoséQuintas
Regra tradicional de linqueditor:
Não achou a função, busca nas LIBs indicadas, seguindo a ordem das LIBs.
E não junta a LIB inteira, somente as partes necessárias.
Por exemplo:
Um PRG pode conter várias funções, e ao compilar vira um objeto, e esse objeto vai pra LIB.
Um outro PRG tem várias funções e mais essa repetida do primeiro, vira um objeto, vai pra LIB.
Ao linqueditar, se usar função só de um, só aquele vai para o EXE e não dá duplicidade.
Se usar função dos dois, os dois vão para o EXE, e aí sim dá duplicidade.
Mas isso se o linqueditor acusar erro quando é duplicidade de LIB.
Interessante isso.
Tantos avanços, e continua valendo a regra de 30 anos atrás.
Usar uma DLL externa
Enviado: 30 Dez 2015 09:19
por asimoes
Quintas e isso é perigoso, funções com o mesmo nome com funcionamento diferente, os resultados podem ser catastróficos, teriamos que olhar todos os fontes da lib para saber onde faz o certo/errado como no caso tbrowse lembra? método :setkey