I need to implement solution for readers writer problem in file system i'm developing. I was searching on the internet and found out this Wikipedia solution. Since I'm told no starving may exist I chose third solution. Now, I'm new in multithreaded programming and I have one question. How do I sepparate shared and local variables? I wanted to instantiate one ReadersWriters class in every file object that would manage accessing to that file, so every thread need to have it's own prev and current local variables and all of them need to share nreaders variable. I want to place them in ReadersWriters class.
As far as I know there are only two ways for the parent thread to share data with a child thread.
Global Variables
Passing it via a pointer during creation of the child thread.
Obviously new pointers may be tacked onto any existing objects.
Local variables with remain thread local unless you do something to prevent them from being so. Remember that each thread will have its own stack.
Related
Consider a Foo that holds some resource
struct Foo
{
~Foo();
};
and a global std::vector<Foo>. Perhaps stupid example, but it illustrates the problem well.
std::vector<Foo> bar;
Now, the processes forks.
If bar is then only modified by the child process, then a call to exit should be the proper thing to do within the child process. If calling _exit, any Foo:s in bar would leak. If the parent added some stuff to bar before the fork, these object may be destroyed twice. Or maybe this is not a problem, because they should be considered as different objects.
What is the proper way of dealing with object lifetime together with a fork. Is the only sane way of dealing with this problems to let the child exec and start over?
I should notice that at this point in the program, there is guaranteed to be only one thread.
What is the proper way of dealing with object lifetime together with a fork?
The proper way to handle shared resources when forking depends on what those objects or resources are.
For any object or variable in the process memory, you automatically get a copy of it upon forking. Each process will then be able to modify or destroy any variable without affecting the other process. This also means that each process is responsible for cleaning up its unique copy of the resource.
For other resources that exist outside the process, like a file, web socket, or shared memory; The best way to handle them will depend on what that resource is. Normally those best practices will be outlined by the library / API you are using to create those resources initially.
Once you've forked, your variables exhibit copy-on-write semantics, so any changes by the child process result in unique variables for the child not shared with the parent. Similarly, changes in the parent process will result in the child having new copies and do not propagate, so the parent can go as far as to exit without interrupting the child. I've done this to implement a self-updating program.
Note that as stated in other answers, "global resources" should be treated on a case by case basis, but variables are not global resources.
I have created a class, which has many public functions, some which write data and some that only read data.
It's required that I do this within 3 threads, I have no other option.
I know if I accessed a shared resource just to read, then I don't have to protect, but I don't know if it is any different when I am using a function to read a private variable of the shared resource.
E.g. I am trying to do...
globalObject.readColour();
which is a function that reads the colour of the global object.
Does it mean that I have to secure the thread at this point, or is it okay to just read the value without any risks?
I'm working on mbed, which supports c and c++98.
This question is similar to this one
If all your threads will only read the variable then you don't need mutex (or similar), but if any thread performs a writing operation you should use mutex.
I have a Class File. I created two threads A and B. In A and B, each thread, I create an auto varible File myfile. And then A and B will operate it. Is that secure? Will it lead to the inconsistent of data?
From the pure memory ressource perspective, it will depend on the scope of your File variables :
If they are local function variables, you are good to go. Each thread of execution owns it own stack, totally separate from other threads, where it create local variables.
If they are static, you are referring to the same global address.
From the file access perspective, it will depends if it is the same file, and if you are writing to it or not.
No, that shouldn't be a problem, simply because each instance of your thread has it's own instance of the variable.
Examine the addresses of the variables to be sure, if they differ (which they will if I understand you correctly), you're fine.
Inconsistencies between threads will only occur, if two threads concurrently access the same variable. Not just 'the same name', but really the same variable.
Now, if the variable was global and both threads were to access it, you'd need some sort of mutual exclusion to prevent data corruption, but auto-variables are safe.
The variables will be distint from each other as each thread will have its own stack, and each instance of the variable will live on that stack.
However, it sounds like you're accessing an underlying filesystem file. If it's the same file and one or both of the threads are writing to the file then this may cause data consistency issues. You'll need to consult the documentation for your operating system to see what it says. If both threads are just reading from the same file then you'll be fine.
I have a C++ multi-threaded application which run tasks in separate threads. Each task have an object which handles and stores it's output. Each task create different business logic objects and probably another threads or threadpools.
What I want to do is somehow provide an easy way for any of business logic objects which are run by task to access each task's output without manually passing "output" object to each business logic object.
What i see is to create output singleton factory and store task_id in TLS. But the problem is when business logic create a new thread or thread pool and those thread would not have task_id in TLS. In this way i would need to have an access to parent's thread TLS.
The other way is to simply grab all output since task's start. There would be output from different task in that time, but at least, better than nothing...
I'm looking for any suggestions or ideas of clean and pretty way of solving my problem. Thanks.
upd: yeah, it is not singletone, I agree. I just want to be able to access this object like this:
output << "message";
And that's it. No worry of passing pointers to output object between business logic classes. I need to have a global output object per task.
From an application point of view, they are not singletons, so why treating the objects like singletons?
I would make a new instance of the output storer and pass the (smart?) pointer to the new thread. The main function may put the pointer in the TLS, thus making the instance global per thread (I don't think that this is a wise design deision, but it is asked). When making a new (sub-?)thread, the pointer can again be passed. So according to me, no singletons or factories are needed.
If I understand you correctly, you want to have multiple class instances (each not necessarily the same class) all be able to access a common data pool that needs to be thread safe. I can think of a few ways to do this. The first idea is to have this data pool in a class that each of the other classes contain. This data pool will actually store it's data in a static member, so that way there is only one instance of the data even though there will be more than one instance of the data pool class. The class will then have accessor methods which access this static data pool (so that it is transparent). To make it thread safe you would then require the access to go through a mutex or something like that.
I have several places in my code where a function static object is created once, and then used (copied) any time that function is called. One of these functions can be called from any thread. The function doesn't access any shared state other than this static object.
When thread 1 calls the function for the first time, the object is created and initialized. However, (by a stroke of luck) I have a repeatable case where the program switches to thread 2 and calls the same function before initialization is finished. The object is assigned, and used, with bad data!
I'm not sure how to handle this. I'm using critical sections in the initialization code, but that's not even the problem. This object is being used before being initialized in the first place.
I tried making this thread local using __declspec(thread), but that doesn't work for objects, apparently.
I could just surround the whole thing with a critical section, and maybe that's the best solution, but I'm concerned about problems like this cropping up in other parts of the code- it'd be nice to have a general solution.
If you are on Windows you could use the InitOnceExecuteOnce API. More details can be found in this Raymond Chen post. Also look at the more generic std::call_once
Couldn't you use a semaphore on the object, setting the semaphore to be already set to 1 when the object is created, and then decrementing it to zero when the object is initialized (and ready for use).
Just need to keep an eye out for resource starvation though.