0
Patrocinador del Foro |
Administrador |
@Recato53, lo que puedes hacer es pasar un puntero de una variable en tu DLL que será recuperado por el EXE en la CMD-LINE.
Es decir, en tu DLL defines una variable y llamas al EXE:
COBOL Código:
WORKING-STORAGE SECTION. 01 EXT-INDICADOR PIC X(2). PROCEDURE DIVISION. INVOKE POW-SELF "ExecuteSync" USING EXT-INDICADOR IF EXT-INDICADOR = "SI" INVOKE POW-SELF "DisplayMessage" USING "¡Hay conexión!" 64 ELSE INVOKE POW-SELF "DisplayMessage" USING "¡NO hay conexión!" 48 END-IF
En tu EXE que comprueba la conexión, en la WORKING Global defines:
COBOL Código:
01 GLB-CMD IS GLOBAL PIC X(260). 01 FILLER REDEFINES GLB-CMD 05 PTR-VAR IS GLOBAL POINTER. 05 FILLER PIC X(256).
Y en el evento "Opened" haces lo siguiente:
COBOL Código:
MOVE "CommandLine" OF POW-SELF TO GLB-CMD
En el evento "Click" de tu botón que llama a la rutina de comprobación de la conexión, añades la LINKAGE SECTION y mapeas la variable de retorno. Ejemplo:
COBOL Código:
ENVIRONMENT DIVISION. DATA DIVISION. WORKING-STORAGE SECTION. 01 FUNC PIC X(20). 01 NUM1 PIC S9(9) COMP-5. 01 NUM2 PIC S9(9) COMP-5. 01 NUM3 PIC S9(9) COMP-5. 01 RESP PIC S9(9) COMP-5. LINKAGE SECTION. 01 EXT-VARIABLE PIC X(2). *> <== VARIABLE COMPARTIDA PROCEDURE DIVISION. MOVE "mluser" TO FUNC CALL FUNC WITH STDCALL USING BY VALUE NUM1 BY VALUE NUM2 BY VALUE NUM3 RETURNING RESP SET ADDRESS OF EXT-VARIABLE TO PTR-VAR IF RESP = ZEROS MOVE "NO" TO EXT-VARIABLE ELSE MOVE "SI" TO EXT-VARIABLE END-IF
¿Te han ayudado? NO TE OLVIDES de darle al botón
¿Quieres dirigirte a alguien en tu post? Notifícale con una mención, tienes 2 opciones:
- Haciendo clic en el icono al lado de su nick
- Haciendo clic en el botón en el editor y escribiendo su nick.
Patrocinador del Foro |
Buenas tardes KUK.
Muchisimas gracias por tu interés. He probado la programación que me indicas y no consigo que funcione.
Creo que me he explicado mal. Te cuento otra vez mi problema.
Tengo una DLL que llama a un EXE.
El programa EXE tiene que devolver un valor y desde la DLL recogerlo.
La programación de la DLL
COBOL Código:
WORKING-STORAGE SECTION. 01 EXT-VARIABLE PIC X(2). PROCEDURE DIVISION. PRINCIPAL SECTION. INVOKE POW-SELF "ExecuteSync" USING "CONEXION.EXE" POW-SWNORMAL. IF EXT-VARIABLE = "SI" INVOKE POW-SELF "DisplayMessage" USING "¡Hay conexión!" 64 ELSE INVOKE POW-SELF "DisplayMessage" USING "¡NO hay conexión!" 48 END-IF
La programación del programa EXE
COBOL Código:
WORKING-STORAGE SECTION. ********************************* 01 CONEXION PIC X(20). 01 FUNCION PIC X(24). 01 RESP PIC S9(9) COMP-5. ********************************* 01 GLB-CMD IS GLOBAL PIC X(260). 01 VALOR REDEFINES GLB-CMD GLOBAL. 05 PTR-VAR POINTER. 05 PIC X(256). LINKAGE SECTION. 01 EXT-VARIABLE PIC X(2). PROCEDURE DIVISION. PRINCIPAL SECTION. MOVE "CommandLine" OF POW-SELF TO GLB-CMD MOVE "InternetCheckConnectionA" TO FUNCION MOVE "http://www.google.es" TO CONEXION CALL FUNCION WITH STDCALL USING by reference CONEXION by value 1 by value 0 returning RESP END-CALL SET ADDRESS OF EXT-VARIABLE TO PTR-VAR IF RESP = ZEROS MOVE "NO" TO EXT-VARIABLE ELSE MOVE "SI" TO EXT-VARIABLE END-IF.
Cuando ejecuto el programa da un error.
Administrador |
@Recato53, pruebalo así:COBOL Código:
ENVIRONMENT DIVISION. DATA DIVISION. WORKING-STORAGE SECTION. 01 EXT-VARIABLE PIC X(2). 01 WS-PROGRAMA. 05 WS-NOMBRE PIC X(13) VALUE "CONEXION.EXE ". 05 WS-PTR POINTER. PROCEDURE DIVISION. MOVE FUNCTION ADDR(EXT-VARIABLE) TO WS-PTR INVOKE POW-SELF "ExecuteSync" USING WS-PROGRAMA POW-SWNORMAL. IF EXT-VARIABLE = "SI" INVOKE POW-SELF "DisplayMessage" USING "¡Hay conexión!" 64 ELSE INVOKE POW-SELF "DisplayMessage" USING "¡NO hay conexión!" 48 END-IF
¿Te han ayudado? NO TE OLVIDES de darle al botón
¿Quieres dirigirte a alguien en tu post? Notifícale con una mención, tienes 2 opciones:
- Haciendo clic en el icono al lado de su nick
- Haciendo clic en el botón en el editor y escribiendo su nick.
Patrocinador del Foro |
Buenos días.
Sique sin funcionar estos programas.
Donde se produce el ERROR es en código del programa.EXE, hay algo que no esta correctamente programado y no encuentro lo que es.
Muchas gracias
Un saludo.
Administrador |
@Recato53, ahora que lo pienso es normal... Estamos compartiendo memoria en 2 procesos diferentes, y esto no es posible. Para ello hay que reservar de la memoria compartida (shared memory) que es independiente y se controla por el SO.
Si sigues queriendo hacerlo así puedo mirar cómo se hace, habrá que llamar unas API-s de Windows. Pero en realidad, me sigue pareciendo lo más fácil
- sea crear un fichero CONEXION.COB e importarlo en cada módulo (EXE/DLL) del proyecto donde lo necesites, luego hacer un CALL vulgar y corriente.
- sea dejarlo todo igual salvo que en vez de un EXE que sea una DLL que se abrirá con CallForm o OpenForm.
¿Te han ayudado? NO TE OLVIDES de darle al botón
¿Quieres dirigirte a alguien en tu post? Notifícale con una mención, tienes 2 opciones:
- Haciendo clic en el icono al lado de su nick
- Haciendo clic en el botón en el editor y escribiendo su nick.
Patrocinador del Foro |
Me gustaría que se pudiera hacer como inicialmente me comentaste.
Ahora lo tengo resuelto con un archivo Temp.
En el programa EXE creo un archivo Temp con los valores que me interesan.
En la DLL abro el archivo Temp y leo los valores.
Es una solución un poco rudimentaria, pero funciona.
Un saludo.
Administrador |
@Recato53, aquí tienes lo que necesitas, lo he comprobado y funciona. En realidad es un ejemplo de cómo compartir memoria entre 2 procesos.
En el programa llamante hacemos:COBOL Código:
ENVIRONMENT DIVISION. DATA DIVISION. WORKING-STORAGE SECTION. 01 hMapFile BINARY-LONG. 01 ADR POINTER. 01 nADR REDEFINES ADR PIC S9(9) COMP-5. 01 LastError PIC S9(9) COMP-5. LINKAGE SECTION. 01 InternetRC PIC S9(4) COMP-5. PROCEDURE DIVISION. *> CREAMOS LA MEMORIA CALL "CreateFileMappingA" WITH STDCALL USING BY VALUE -1 *> INVALID_HANDLE_VALUE BY VALUE 0 *> NULL BY VALUE 4 *> PAGE_READWRITE BY VALUE 0 BY VALUE 4 *> TAMAÑO MEMORIA EN BYTES BY CONTENT "VarComp" & X"00" *> NOMBRE DE LA MEMORIA RETURNING hMapFile *> COMPROBAMOS LA REFERENCIA IF hMapFile = ZEROS INVOKE POW-SELF "DisplayMessage" USING "Error creando Memoria Compartida" 16 EXIT PROGRAM END-IF *> OBTENEMOS EL PUNTERO CALL "MapViewOfFile" WITH STDCALL USING BY VALUE hMapFile BY VALUE H"0F001F" *> FILE_MAP_ALL_ACCESS BY VALUE 0 BY VALUE 0 BY VALUE 4 *> TAMAÑO MEMORIA EN BYTES RETURNING ADR *> SI NO HEMOS OBTENIDO EL PUNTERO, MIRAMOS POR QUE IF ADR = NULL CALL "GetLastError" WITH STDCALL RETURNING LastError INVOKE POW-SELF "DisplayMessage" USING "Error creando Memoria Compartida" LastError 16 CALL "CloseHandle" WITH STDCALL USING BY VALUE hMapFile ELSE *> SI TENEMOS EL PUNTERO, MAPEAMOS A LA VARIABLE SET ADDRESS OF InternetRC TO ADR END-IF MOVE POW-FALSE TO "Enabled" OF CmCommand1 INVOKE POW-SELF "ExecuteSync" USING "INTERNET.EXE" MOVE POW-TRUE TO "Enabled" OF CmCommand1 IF InternetRC = 1 INVOKE POW-SELF "DisplayMessage" USING "¡Hay conexión a Internet!" 64 ELSE INVOKE POW-SELF "DisplayMessage" USING "NO hay conexión a Internet..." 48 END-IF *> ELIMINAMOS LA MEMORIA CREADA CALL "CloseHandle" WITH STDCALL USING BY VALUE hMapFile
En el programa llamado hacemos:COBOL Código:
ENVIRONMENT DIVISION. DATA DIVISION. WORKING-STORAGE SECTION. 01 hMapFile BINARY-LONG. 01 ADR POINTER. 01 nADR REDEFINES ADR PIC S9(9) COMP-5. 01 LastError PIC S9(9) COMP-5. 01 CONEXION PIC X(30). 01 ST-INTERNET PIC S9(9) COMP-5. 01 FUNC PIC X(24). LINKAGE SECTION. 01 InternetRC PIC S9(4) COMP-5. PROCEDURE DIVISION. MOVE "http://www.google.es" & X"00" TO CONEXION MOVE "InternetCheckConnectionA" TO FUNC CALL FUNC WITH STDCALL USING by reference CONEXION by value 1 by value 0 returning ST-INTERNET END-CALL *> ACCEDEMOS A LA MEMORIA CREADA CALL "OpenFileMappingA" WITH STDCALL USING BY VALUE H"0F001F" *> FILE_MAP_ALL_ACCESS BY VALUE 0 BY CONTENT "VarComp" & X"00" *> NOMBRE DE LA MEMORIA RETURNING hMapFile IF hMapFile = ZEROS INVOKE POW-SELF "DisplayMessage" USING "Error accediendo a la Memoria Compartida" 16 EXIT PROGRAM END-IF *> OBTENEMOS EL PUNTERO CALL "MapViewOfFile" WITH STDCALL USING BY VALUE hMapFile BY VALUE H"0F001F" *> FILE_MAP_ALL_ACCESS BY VALUE 0 BY VALUE 0 BY VALUE 4 RETURNING ADR IF ADR = NULL CALL "GetLastError" WITH STDCALL RETURNING LastError INVOKE POW-SELF "DisplayMessage" USING "Error obteniendo puntero de Memoria Compartida" LastError 16 ELSE SET ADDRESS OF InternetRC TO ADR MOVE ST-INTERNET TO InternetRC END-IF
Incluyo el proyecto por si a caso
¿Te han ayudado? NO TE OLVIDES de darle al botón
¿Quieres dirigirte a alguien en tu post? Notifícale con una mención, tienes 2 opciones:
- Haciendo clic en el icono al lado de su nick
- Haciendo clic en el botón en el editor y escribiendo su nick.
Patrocinador del Foro |
El archivo .rar, se descarga con una extensión que no se puede descomprimir.
Administrador |
@Recato53, a mi me funciona... De todos modos, simplemente renombralo en INTERNET.rar a mano.
¿Te han ayudado? NO TE OLVIDES de darle al botón
¿Quieres dirigirte a alguien en tu post? Notifícale con una mención, tienes 2 opciones:
- Haciendo clic en el icono al lado de su nick
- Haciendo clic en el botón en el editor y escribiendo su nick.
Actualmente hay 1 usuarios viendo este tema. (0 miembros y 1 visitantes)
Marcadores