Welcome, Guest. Please login or register.

Author Topic: Stupid question about if it's possible to link and create two separate executables  (Read 7028 times)

Description:

0 Members and 1 Guest are viewing this topic.

Offline Piru

  • \' union select name,pwd--
  • Hero Member
  • *****
  • Join Date: Aug 2002
  • Posts: 6946
    • Show all replies
    • http://www.iki.fi/sintonen/
Quote
Is it possible to have two different programs recognize each others variables with linking but still be compiled to two different executables?
I know it sounds stupid but the reason is that I want a created process to be created after the main task and I want it to recognize some global variables between the two.

No, you need to somehow pass ptr to some structure you use to share data. Convinient and flexible way is to use messages, it allows great dynamic control of the subprocess: My IPC example

Some uglier hacks use tc_UserData or pr_ExitData of the just created struct Process. If you do this, remember to enclose CreateNewProc + field poking in Forbid/Permit or else the code gets to run before you have chance to poke the ptr in.

Quote
Now if you know another way of creating a process in

The answer would be fake seglist passed to CreateProc.

Something like:
Code: [Select]

#include <exec/execbase.h>
#include <dos/dos.h>

#include <proto/exec.h>
#include <proto/dos.h>

#ifdef __GNUC__
# pragma pack(2)
#endif
struct fakeseg
{
  ULONG size;
  BPTR  next;
  UWORD jmp;
  APTR  myfunc;
};
#ifdef __GNUC__
# pragma pack()
#endif

extern struct ExecBase *SysBase;

BPTR allocfakeseg(void (*func)(void))
{
  struct fakeseg *seg = AllocMem(sizeof(*seg),
                                 MEMF_PUBLIC);
  if (seg)
  {
    seg->size   = 16;
    seg->next   = 0;
    seg->jmp    = 0x4EF9;
    seg->myfunc = (APTR) func;

    if (SysBase->LibNode.lib_Version >= 37)
    {
      CacheClearE(seg, sizeof(*seg), CACRF_ClearI);
    }
    else
    {
      /* Call some asm cacheclear function that handles possible
         020/030 caches. 040+ is only supported on 2.0+. */

      /* flushcaches(); */
    }    

    return MKBADDR(&seg->next);
  }

  return 0;
}

void freefakeseg(BPTR segptr)
{
  if (segptr)
  {
    struct fakeseg *seg = (APTR) (((ULONG *) BADDR(segptr)) - 1);

    FreeMem(seg, sizeof(*seg));
  }
}

void code(void)
{
  /* ... */
}

int main(void)
{
  BPTR seg;

  seg = allocfakeseg(code);
  if (seg)
  {
    /* use seg */

    freefakeseg(seg);
  }

  return 0;
}

Obviously you still need to provide proper syncronization so that you don't call freefakeseg prematurely.
 

Offline Piru

  • \' union select name,pwd--
  • Hero Member
  • *****
  • Join Date: Aug 2002
  • Posts: 6946
    • Show all replies
    • http://www.iki.fi/sintonen/
Quote
Code: [Select]
struct OurStructure *OurMessage

OurMessage = (struct OurStructure*)AllocMem (sizeof(OurStructure), MEMF_PUBLIC|MEMF_CLEAR))
/* Initialize the structure after*/

That would be either:
Code: [Select]

struct OurStructure *OurMessage;

OurMessage = (struct OurStructure *) AllocMem(sizeof(struct OurStructure), MEMF_PUBLIC|MEMF_CLEAR);

or:
Code: [Select]

struct OurStructure *OurMessage;

OurMessage = (struct OurStructure *) AllocMem(sizeof(*OurMessage), MEMF_PUBLIC|MEMF_CLEAR);
 

Offline Piru

  • \' union select name,pwd--
  • Hero Member
  • *****
  • Join Date: Aug 2002
  • Posts: 6946
    • Show all replies
    • http://www.iki.fi/sintonen/
@PiR

Try to put 6 bytes of data (yes 'size' and 'next' are not really part of it) to a segment. Then load the segment with LoadSeg. Segment 'size' will be 16.

Basically the size of the data is padded to multiple of longwords (4), and thus to stay consistent the fake segment size is also 16 and not 14.

So in a sense using _filler like that is not a bad idea, it makes the sizeof() correct, too. It is not strictly speaking needed, though.

Quote
On the other hand if it's not used for anything, why to bother and initiate it at all?

Some applications scan the seglists, and if the fields would not be set properly these apps could crash.