Multiple threads accessing different functions member

Hello, I have something like that:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
MyObject::MyObject()
{
    void fun1()
    {
        .....
    }

    bool fun2()
    {
        .....
    }
}

DoWork1()  // thread 1
{
    obj.fun1();
    ....
}

DoWork2()  // thread 2
{
   bool res = obj.fun2();
   .....
}

int main()
{
    MyObject obj;

    // start thread 1
    // start thread 2

    .....

    return 0;
}


Inside each thread I have to call an object's member function, different from each other and that have nothing in common.

Can I do that? Or should I synchronize the access?
Last edited on
If they have nothing in common, why are they in the same class?

If they're really as described, there shouldn't be any issue with threading.
They are in the same class because fun1() in related with the interface of the object, while fun2() is related to the task that the object has to perform.

fun1() only read some values and then draw some elements, but it cannot change anything.
Only data that is modified across the threads needs to be protected. I.e. when you add something to a vector (or any other container) in one thread and read from this vector in the other thread. Then the vector needs to be protected [with a mutex].
In that case I have same counters, but in single variables form. I don't use anykind of container.
If fun1() reads variable(s) that fun2() can change, then these variables should be protected. Perhaps atomic variables are what are needed? http://www.cplusplus.com/reference/atomic/atomic/
1.You can make some static public functions for the class.
2.Just split them away, think this problem in C way.

And please notice that when using multi-thread. Its memory space is seperated from the main and
1.You`ll need to re-allocate space for the known data to pass through call back correctly.
2.be ware of the run condition on the same resource.(You`ll need to lock the access to some variables or functions)
If you write the variable in one thread and you have dependent read/write in the other thread you need to protected that variable. E.g.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
thread_1()
{
  // protection begin
  var++;
  // protection end
}

thread_2()
{
  // protection begin
  if(var > 100)
    var = 0;
  // protection end
}
> fun1() only read some values and then draw some elements, but it cannot change anything.
But presumably it's reading things that fun2() writes to, which makes a complete nonsense of your bold assertion "and that have nothing in common." in your first post.

@c90a78
> And please notice that when using multi-thread. Its memory space is seperated from the main
Not so.

Threads are typically "light-weight" and share the same virtual memory space (code and data). Threads have their own stacks, and perhaps thread local storage.

Processes are typically "heavy-weight" and have different virtual address spaces (even if you run the same program twice). Getting shared data between processes is far from trivial.


Getting shared data between processes is far from trivial.


Depends on what os and what you want to do. Using say a shared data segment for Windows (I don't know about other os's) is quite easy if that is all you want and don't mind the security issues.
Creating a shared segment of memory is trivial in every mainstream OS.
Placing C++ objects in memory shared between processes is far from trivial.

From Boost Interprocess library documentation:
Limitations When Constructing Objects In Mapped Regions
. Offset pointers instead of raw pointers
. References forbidden
. Virtuality forbidden
. Be careful with static class members
https://www.boost.org/doc/libs/1_76_0/doc/html/interprocess/sharedmemorybetweenprocesses.html#interprocess.sharedmemorybetweenprocesses.mapped_region_object_limitations
Placing C++ objects in memory shared between processes is far from trivial.


The OP only uses shared single variables and not containers. With WIN32 API, we use shared memory for objects that don't use dynamic memory together with named mutex/events and it's quite easy.
> The OP only uses shared single variables and not containers.

Placing C++ objects in memory shared between processes is far from trivial.

Containers introduce additional facets of non-triviality.
Boost Interprocess on containers and allocators:
https://www.boost.org/doc/libs/1_76_0/doc/html/interprocess/allocators_containers.html#interprocess.allocators_containers.allocator_introduction
We're thinking of different things, I think.

For Windows using 2 ints in shared memory:

1
2
3
4
5
6
7
#pragma data_seg("Share1")

int ishare1 = 0;
int ishare2 = 0;

#pragma data_seg()
#pragma comment (linker, "/SECTION:Share1,RWS")		// Read, write and shared segment 


Then sync access to them using named mutex/event as appropriate. Each process just uses the variables ishare1, ishare2. Works fine, with the security caveats....
Last edited on
> We're thinking of different things

Yes.

Placing an object in shared memory is much simpler if the shared memory region is guaranteed to be mapped at the same base address in all processes sharing the memory.

Placing an object of a scalar POD type in shared memory is also very straightforward.

Placing a C++ object (which may have member pointers or references, static member objects or virtual functions) in shared memory is a lot more involved.
Last edited on
Registered users can post here. Sign in or register to post.