The image below depicts the dependency relationship between different modules.
The executable depends on two dynamic libraries, dynamic_lib1 and dynamic_lib2. And both dynamic_lib1 and dynamic_lib2 depends on static_lib. There is a singleton class in static_lib. dynamic_lib1 and dynamic_lib2 use get_instance method to retrieve the instance of the singleton class.
The basic skeleton of the singleton class is shown below:
1 // singleton.h
2 #pragma once
3
4 class __declspec(dllexport) singleton
5 {
6 public:
7 singleton(void);
8 ~singleton(void);
9
10 static singleton* instance;
11 static singleton* get_instance();
12 };
13
14
15 // singleton.cpp
16 #include "singleton.h"
17 #include <iostream>
18
19 singleton* singleton::instance;
20
21 singleton::singleton(void)
22 {
23 }
24
25 singleton::~singleton(void)
26 {
27 }
28
29
30 singleton* singleton::get_instance()
31 {
32 // lock here
33 if(!instance)
34 {
35 instance = new singleton();
36 }
37 // unlock here
38 return instance;
39 }
2 #pragma once
3
4 class __declspec(dllexport) singleton
5 {
6 public:
7 singleton(void);
8 ~singleton(void);
9
10 static singleton* instance;
11 static singleton* get_instance();
12 };
13
14
15 // singleton.cpp
16 #include "singleton.h"
17 #include <iostream>
18
19 singleton* singleton::instance;
20
21 singleton::singleton(void)
22 {
23 }
24
25 singleton::~singleton(void)
26 {
27 }
28
29
30 singleton* singleton::get_instance()
31 {
32 // lock here
33 if(!instance)
34 {
35 instance = new singleton();
36 }
37 // unlock here
38 return instance;
39 }
But when we run the executable, we're surprised to find that the the use of get_instance method in dynamic_lib1 and dynamic_lib2 doesn't share the same instance.
After thinking about it carefully, it's clear that the bug is caused by we use static_lib3 as a static library. When we compile dynamic_lib1 and dynamic_lib2, they both link with static_lib, and each get a separate copy of the singleton::instance in data section.
But be aware that the behavior is compiler specific. The singleton is still singleton when I tested with gcc. And the singleton got created multiple instances when I tested microsoft's C++ compiler and apple's developer tools.