Recent

Author Topic: [SOLVED] Form in library  (Read 1642 times)

Zvoni

  • Hero Member
  • *****
  • Posts: 3135
[SOLVED] Form in library
« on: May 05, 2023, 12:49:28 pm »
Hi Folks,
i'm currently making a concept of a Tool for the company i work for.

The concept consists of a "main" Application (EXE), which is more or less something like a "cockpit", offering different "reports" to call from there.
The basic idea is to "blackbox" each "report" into its own library (DLL), since the GUI-Elements will differ for each report, and i don't want to recompile the "main" app everytime.

So, in a way a kind of "plugin"-System

Question: Is there anything i have to consider, if i call such a report from the main app?
It's basically a call to an exported function from that lib to fire up a Form (the GUI for that report), which resides inside that lib.

I think to remember that forms only run in the main thread, and i'm not sure anymore, in what Thread-Context a library runs (i know it runs in the same process-space)

Hope you understand what i mean.
In that context i'm undecided if should call the DLL-Form in modal or modeless state (which would be a try-and-error for me)
« Last Edit: May 08, 2023, 09:54:22 am by Zvoni »
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

440bx

  • Hero Member
  • *****
  • Posts: 5809
Re: Form in library
« Reply #1 on: May 05, 2023, 01:07:19 pm »
An interesting architecture (though not really new.)

If I were you, I'd consider making the "cockpit" app just an interface to choices and nothing else.  Once a choice has been made, the cockpit would "disappear" (no longer be visible) or, if it remained visible, it would reflect no change and just be there to allow the user to make additional choices.

This means that when a choice is made, instead of making a call to some dll function, I'd have a separate exe/process that does whatever that choice is supposed to do.

The only dependency between the cockpit and the separate exe would be the layout and type of data the cockpit supplies to the recipient exe (they must fully agree - easy to ensure.)  Memory mapped files can easily take care of that.

If the cockpit provides feedback as to which reports are currently running then it needs to be "overlooking" which processes are still active and possibly have a mechanism between the processes and the cockpit to have them inform the cockpit when they are terminating successfully (this way the cockpit can keep  track of what has happened and any failures.)

One possibility would be to have the "report" process have a separate thread that increments a counter every second in a shared area of memory.  That would make it very easy for the cockpit to figure out if any one of its processes has crashed.

HTH.
FPC v3.2.2 and Lazarus v4.0rc3 on Windows 7 SP1 64bit.

ojz0r

  • Jr. Member
  • **
  • Posts: 71
Re: Form in library
« Reply #2 on: May 05, 2023, 01:29:25 pm »
I recently made something similar to what you are asking for, but not for reports.
I use the dynlib function to load a library in a loop an launch it in its own thread, then i have a second thread that monitors the status/commands inside the library. Depending on the exit code of the monitor thread the main application decides if the loop should infact loop around and reload the library (if changes are made) or to simply close the application all together.
I like big endians and i can not lie.

zeljko

  • Hero Member
  • *****
  • Posts: 1792
    • http://wiki.lazarus.freepascal.org/User:Zeljan
Re: Form in library
« Reply #3 on: May 05, 2023, 02:01:43 pm »
Hi Folks,
i'm currently making a concept of a Tool for the company i work for.

The concept consists of a "main" Application (EXE), which is more or less something like a "cockpit", offering different "reports" to call from there.
The basic idea is to "blackbox" each "report" into its own library (DLL), since the GUI-Elements will differ for each report, and i don't want to recompile the "main" app everytime.

So, in a way a kind of "plugin"-System

Question: Is there anything i have to consider, if i call such a report from the main app?
It's basically a call to an exported function from that lib to fire up a Form (the GUI for that report), which resides inside that lib.

I think to remember that forms only run in the main thread, and i'm not sure anymore, in what Thread-Context a library runs (i know it runs in the same process-space)

Hope you understand what i mean.
In that context i'm undecided if should call the DLL-Form in modal or modeless state (which would be a try-and-error for me)

In Fast Reports you have ability to run standalone reports with it's own form implementation which you can edit per report (for input parameters). It works ok (I'm using it) on all platforms.

Zvoni

  • Hero Member
  • *****
  • Posts: 3135
Re: Form in library
« Reply #4 on: May 05, 2023, 02:35:44 pm »
OK, i think i confused everybody with those "reports"
with "reports" i don't mean something like FastReport or LazReport.

More like, each dll will have its own individual TForm-GUI, providing "report"-specific Data and asking for Input to THEN generate, say an Excel-File, or a PDF, or a print-out.
Might even be not a "report" in the classic sense, but, say, just a Form to pull some data from a database and display it there.

@440bx
interesting.
But i was under the impression that two EXE's from FPC cannot "communicate" with each other, since an EXE can't export functions like a dll?!?!

Anyway, interesting approach.
No, the "DLL" doesn't have to report back to the Exe.
maybe i should have called "main" more like "launcher".
Imagine a single app, which has a listbox with, say 10 games you have on your Computer.
in the ListBox you select a game, say Diablo2, either doubleclick or hit "Run"-Button, and "Diablo2" starts.
More like that

So, if i understood you correctly, i could actually use:
one "main" EXE ("Launcher")
two (or more) other EXE's, which get "launched" with a TProcess-call? commandline-parameters being optional, if i would have to pass anything to the "second" exe?

EDIT: to maybe paint a clearer picture:
We have a File-Server (Surprise  :P)
on that File-Server there is Folder-Tree (think Purchase Department, Sales, Warehouse, Assembly etc.), each Folder with its own subfolder.
Now over the years, i had to create a plethora of "reports". Mainly Excel-Files which contain VBA-Code. And pretty much any two "reports" are not even slightly "comparable"

Everytime there is a Change-Request, i always have to search for that specific "report", because the Users can actually pull that report in whatever folder they want.
Yes, i do have my own "copy" of that report, but keeping track of Versions is PITA, and No, don't start with svn, git or whatever else.
It's a trading company, and i'm locked down on what i can use.

And my main idea was to "centralize" this VBA-Code (ported to FPC) in a fixed location.
The user starts the Launcher, chooses the report he/she wants, the report creates the Excel-Data, and saves it somewhere else wherever the user wants it
« Last Edit: May 05, 2023, 02:48:09 pm by Zvoni »
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

440bx

  • Hero Member
  • *****
  • Posts: 5809
Re: Form in library
« Reply #5 on: May 05, 2023, 03:36:10 pm »
@440bx
interesting.
But i was under the impression that two EXE's from FPC cannot "communicate" with each other, since an EXE can't export functions like a dll?!?!
Actually, an exe _can_ export functions (debuggers take advantage of that.)  That said, it is not exactly "easy" for the child process to call functions that reside in the parent process (more often than not, it goes in the opposite direction anyway, debugger calling into debuggee.)  That said, from what you said, it doesn't look like the child process would need to call functions in the parent (or the "dll" into the main program if dlls were to be used.)

maybe i should have called "main" more like "launcher".
Imagine a single app, which has a listbox with, say 10 games you have on your Computer.
in the ListBox you select a game, say Diablo2, either doubleclick or hit "Run"-Button, and "Diablo2" starts.
More like that
That's exactly what I was suggesting.

So, if i understood you correctly, i could actually use:
one "main" EXE ("Launcher")
two (or more) other EXE's, which get "launched" with a TProcess-call? commandline-parameters being optional, if i would have to pass anything to the "second" exe?
Yes, I think you got it.  if the information to be passed to the child process is "small" then command line parameters may be a good mechanism.  If there is a significant amount of data to be passed to the child process then a named memory mapping containing the data would likely be a better mechanism.

What you described sounds like a good candidate for what I suggested.
FPC v3.2.2 and Lazarus v4.0rc3 on Windows 7 SP1 64bit.

balazsszekely

  • Guest
Re: Form in library
« Reply #6 on: May 05, 2023, 04:58:31 pm »
@Zvoni
Please try attached project from the following post: https://forum.lazarus.freepascal.org/index.php/topic,53621.msg396954.html#msg396954

MarkMLl

  • Hero Member
  • *****
  • Posts: 8504
Re: Form in library
« Reply #7 on: May 05, 2023, 07:17:27 pm »
Actually, an exe _can_ export functions (debuggers take advantage of that.)

Leaving aside debuggers, I'm aware of two facets to this. The first is that a .exe- but possibly not a unix executable (ELF etc.) can be built to export additional named entry points (going back to early Windows, executables often had extra entry points for "print" etc.)

The second is that when an executable loads and calls a named entry point in a library dynamically, the library can then ask for named entry points in the executable. I've had this working to good effect with 32-bit x86 Linux programs, but hit problems I never resolved with x86_64.

I'd add that my understanding is that the FSF considers the distinction between an executable with a single entry point vs a library with multiple entry points to be significant to licence applications.

MarkMLl
MT+86 & Turbo Pascal v1 on CCP/M-86, multitasking with LAN & graphics in 128Kb.
Logitech, TopSpeed & FTL Modula-2 on bare metal (Z80, '286 protected mode).
Pet hate: people who boast about the size and sophistication of their computer.
GitHub repositories: https://github.com/MarkMLl?tab=repositories

PascalDragon

  • Hero Member
  • *****
  • Posts: 6189
  • Compiler Developer
Re: Form in library
« Reply #8 on: May 05, 2023, 09:06:20 pm »
Question: Is there anything i have to consider, if i call such a report from the main app?
It's basically a call to an exported function from that lib to fire up a Form (the GUI for that report), which resides inside that lib.

I think to remember that forms only run in the main thread, and i'm not sure anymore, in what Thread-Context a library runs (i know it runs in the same process-space)

Your library must use a C-based API and you must ensure that you don't use operations that rely on the VMT (e.g. as or is operators), the RTTI or have exceptions cross the module boundary. For anything more to be used reliably the dynamic package system in FPC needs to be finished first.

Zvoni

  • Hero Member
  • *****
  • Posts: 3135
Re: Form in library
« Reply #9 on: May 08, 2023, 09:11:35 am »
@Zvoni
Please try attached project from the following post: https://forum.lazarus.freepascal.org/index.php/topic,53621.msg396954.html#msg396954
Thx.
Somehow i missed that thread when searching.

Quote
Your library must use a C-based API and you must ensure that you don't use operations that rely on the VMT (e.g. as or is operators), the RTTI or have exceptions cross the module boundary.
Understood.
As i said: The "Child" (DLL) doesn't have to report back to the launcher, nor is it going to use anything from the launcher

@everyone else: Thx for your input.
Appreciated
« Last Edit: May 08, 2023, 09:16:22 am by Zvoni »
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

 

TinyPortal © 2005-2018