PDA

Ver la Versión Completa : Descargando DLLs


ALfrediKruger
26-12-2006, 11:34:11
Vale, un poblema:

Tengo una DLL de fabricacion propia q va bien, hace todo lo q tiene q hacer pero a la hora de cerrar la aplicacion q la utiliza me da un error (access violation) q me trae loco,

La dll se carga asi:


result := 0;
// if LibHand = 0 then
LibHand := LoadLibrary('myDLL.dll');
if LibHand <> 0 then
begin
@DisplayModalForm := GetProcAddress(LibHand, 'DisplayModalForm');
//cambio esto a funciones, devuelve un entero
result := integer(DisplayModalForm(Pchar(AstrFormulario),VarrIdiomas, AintIdioma));
//@DisplayModalForm (http://www.clubdelphi.com/foros/) := nil;
end;
// FreeLibrary(LibHand);
// LibHand := 0;
//ShowMessage('Liberado : ' + BoolToStr(blnIsFree));


Lo comentado son cosas q he probado... Lo unico q cambiaba el error era libhand := 0 q hacia q la direccion q daba error fuera la 0x00000

Libhand es una variable global de esa unidad y todo funciona ok... casca al cerrarse la aplicacion.... alguien ve algo feo? me voi a suicidar!!!!

Ñuño Martínez
26-12-2006, 13:45:42
@DisplayModalForm := GetProcAddress(LibHand, 'DisplayModalForm');
En esta línea estás intentando cambiar la posición de memoria de DisplayModalForm. Como lógicamente eso no es posible (no se puede cambiar la posición de memoria de una variable), el compilador hace lo que puede y falla cuando se ejecuta.

Lo que me parece raro es que el compilador no falle al intentar compilar esa lína :confused:. ¿Seguro que no devuelve ningún error?

ALfrediKruger
26-12-2006, 13:56:20
Displaymodalform es una funcion:

TDisplayModalForm = function (AstrFormulario : PChar; var arrIdiomas : array of string; AintIdioma : shortint = 0) :integer

var
DisplayModalForm : TDisplayModalForm;

Mi intencion es asignar a esa variable el proceso que esta en la DLL cargada y q tiene el nombre entrecomillado...

Robert01
26-12-2006, 14:04:15
porque no pruebas así:


libhand := LoadLibrary('mydll.dll');
if libhand = 0 then begin
ShowMessage ('DLL no disponible');
end
else begin
@DisplayModalForm := GetProcAddress(libhand, 'DisplayModalForm');
if @DisplayModalForm = nil then begin
{ function no found. misspelled? }
ShowMessage ('función no encontrada, ¿llamada erronea?');
end
else begin
{ call the function as usually }
result := integer(DisplayModalForm(Pchar(AstrFormulario),VarrIdiomas, AintIdioma));
end;
end;
FreeLibrary(libhand);

Ñuño Martínez
26-12-2006, 14:07:02
Sigo pensando que "@var := value" no es correcto: que yo sepa, el operador @ devuelve la dirección física de la variable o de la función/procedimiento al que se aplica. ¿Estoy equivocado? ¿O es que cambiaron la especificación de Pascal y no me enteré?

seoane
26-12-2006, 14:10:19
Voy a dar un palo de ciego. Supongo que tanto el programa como la dll están creadas en delphi, pero ¿has añadido la unidad ShareMem a las uses?.


On Win32, if a DLL exports routines that pass long strings or dynamic arrays as parameters or function results (whether directly or nested in records or objects), then the DLL and its client applications (or DLLs) must all use the ShareMem unit. The same is true if one application or DLL allocates memory with New or GetMem which is deallocated by a call to Dispose or FreeMem in another module. ShareMem should always be the first unit listed in any program or library uses clause where it occurs.