How to call a C ++ function after completion of main ()

I am developing a C ++ tool that should work transparently for the main program. That is: if the user simply attaches the tool to his program, the tool will be activated. To do this, I need to call two functions, a function a(), before it main()gets control and a function b()after completion main().

I can easily do the first by declaring a global variable in my program and initializing it with a return code a(). iee

int v = a() ;

but I can not find a way to call b()after completion main()?

Can anyone think of how to do this?

The tool runs on Windows, but I would prefer not to use any specific OS calls.

Thanks George

+4
source share
5 answers

Use RAII, with a and b called constructor / destructor.

class MyObj {
MyObj()
  {
   a();
  };
~MyObj()
  {
    b();
  };
};

Then just enter an instance of MyObj outside the main () scope

MyObj obj;

main()
{
  ...
}

Some notes.

  • This is standard C ++ and works on any platform.
  • You can use this without changing any source code, simply using your instance of MyObj in a separate compiler.
  • While it will work before and after main (), other objects built outside the main one will also be executed at this time. And you have little control over the order of your construction / destruction facility, among others.
+9
source

SOLUTION IN C:

look atexit:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
void bye(void)
{
    printf("That was all, folks\n");
}
int main(void)
{
    long a;
    int i;
    a = sysconf(_SC_ATEXIT_MAX);
    printf("ATEXIT_MAX = %ld\n", a);
    i = atexit(bye);
    if (i != 0) {
        fprintf(stderr, "cannot set exit function\n");
        exit(EXIT_FAILURE);
    }
    exit(EXIT_SUCCESS);
}

http://linux.die.net/man/3/atexit

, , atexit. , , , - .

EDIT:

++:

sudgested ++- std. , , :

#include <iostream>
#include <cstdlib>

void atexit_handler_1() 
{
    std::cout << "at exit #1\n";
}

void atexit_handler_2() 
{
    std::cout << "at exit #2\n";
}

int main() 
{
    const int result_1 = std::atexit(atexit_handler_1);
    const int result_2 = std::atexit(atexit_handler_2);

    if ((result_1 != 0) or (result_2 != 0)) {
        std::cerr << "Registration failed\n";
        return EXIT_FAILURE;
    }

    std::cout << "returning from main\n";
    return EXIT_SUCCESS;
}

http://en.cppreference.com/w/cpp/utility/program/atexit

+4

C/++, GCC __attribute__((constructor)) __attribute__((destructor)):

#include <stdio.h>

void __attribute__((constructor)) ctor()
{
    printf("Before main()\n");
}

void __attribute__((destructor)) dtor()
{
    printf("After main()\n");
}

int main()
{
    printf("main()\n");

    return 0;
}

:

Before main()
main()
After main()
+1

main ? struct, main .

#include <iostream>

struct Test
{
    Test()  { std::cout << "Before main..." << std::endl; }
    ~Test() { std::cout << "After main..."  << std::endl; }
};

Test test;

int main()
{
    std::cout << "Returning now..." << std::endl;
    return 0;
}
+1

As an alternative to the destructor, you can use it in a atexit()similar way - in C ++, you do not need to have access to main()register atexitthere. You can do this in your own a()- for example:

void b(void) {
    std::cout << "Exiting.\n";
}

int a(void) {
    std::cout << "Starting.\n";
    atexit(b);
    return 0;
}

// global in your module
int i = a();

At the same time, I would also prefer a global object of the C ++ class, which will call the material b()in its destructor.

0
source

All Articles