Can't pass a local variable from a thread - multithreading

I made a thread thread1 which creates another thread thread2. When I try to pass the value of fd (fd declared inside thread2) using pthread_exit from thread2 to thread1 I get a garbage value in retval. But when I declare fd as a global variable I get correct value in retval. I got an answer that this is because the thread is finished so it can't pass the value. But in case of functions, a local variable's scope is also limited inside the function and they do return values. So why can't a thread do that?
Here is the code that I tried:
void *thread2(void *message)
{
int fd;
void *retval;
fd=open(message,O_RDWR);
printf("message is - %s",(char *)message);
pthread_exit(&fd);
}
void *thread1(void *message)
{
void *retval;
pthread_t *tid2;
tido=malloc(sizeof(pthread_t));
pthread_create(tid2,NULL,thread2,message);
pthread_join(*tid2,&retval);
printf("fd in write is-%d\n",*(int *)retval);
pthread_exit(&retval);
}

Um... your int fd is an automatic variable (which we may assume is on the stack), so is out of scope when thread2() returns, so passing a pointer to fd out of the function is probably going to lead to disappointment.
A function can return the value of an automatic (aka local) variable. What it cannot do is return the address of one (not and work, anyway).
What you could do is construct a struct to pass into thread2(), to carry parameters in and results back.

Related

gtk 3.0 use the same callback for several switches

I'm creating a Linux GUI using GTK3.0 and C and I want to use the same callback for several switches. In order to differentiate the switch that was clicked, I am trying to use the gpointer argument in g_signal_connect, but the callback doesn't seem to receive the right value.
I create the signals this way:
g_signal_connect(led1_switch, "state-set", G_CALLBACK(on_gpio_btn_click), (gpointer)"LED1");
g_signal_connect(led2_switch, "state-set", G_CALLBACK(on_gpio_btn_click), (gpointer)"LED2");
And the callback tries to get the gpointer passed:
static void on_gpio_btn_click(GtkWidget *wid, gpointer ptr)
{
int gpio;
int val = 0;
char *gpio_switch = ptr;
...
But when I debug the application, the ptr pointer has the value 0x1, a wrong memory address.
Shouldn't it point to the memory address where the constant string "LED1" is stored?
what am I doing wrong? How can I share the same callback for several widgets? I have 8 switches to control GPIOs and I would prefer to have one callback for all of them instead of creating eight.
Your function signature is wrong: the 2nd argument is the value of the switch's state, as can be found in the documentation of the "state-set" signal. That's also the reason why the value is 1: that's the actual value of TRUE.
In other words, your callback will like this:
static void on_gpio_btn_click(GtkSwitch *swtch, gboolean state, gpointer ptr)
{
int gpio;
int val = 0;
char *gpio_switch = ptr;
// ...
}

starting std::thread with anonymous class call

I am curious as to how to correctly start a std::thread using an anonymous class call.
With the below code, if my class only having 1 member variable and I call std::thread td(someclass(shared_mutex)); I get a compiler warning of warning
C4930: 'std::thread td(someclass)': prototyped function not called (was a variable definition intended?)
However, if I add a second member variable as below and call it with
std::thread td(someclass(shared_mutex,x));
I get an error with error C2064: term does not evaluate to a function taking 0 arguments.
class someclass
{
private:
std::mutex& shared_mutex;
int x;
public:
someclass(std::mutex& init_mutex, int init_x) :
shared_mutex(init_mutex),
x(init_x)
{}
//...
};
int main()
{
std::mutex shared_mutex;
int x = 10;
std::thread td(someclass(shared_mutex,x));
td.join();
return 0;
}
The only way around this is by creating an
void operator()()
{}
within the class, but is that the correct method, just to have some kind of starting function for the thread reference or am I missing some other point here? I thought the constructor would be resolver for that?
Try using { and } syntax to construct your object to avoid veximg parses as a function declaration.
std::thread td(someclass(shared_mutex,x))
becomes
std::thread td{someclass{shared_mutex,x}}
It seems that you want your thread to execute the long-running constructor of someclass and then immediately discard the newly constructed someclass. This can be done by passing the thread constructor a function object that does just that:
int main()
{
std::mutex shared_mutex;
int x = 10;
std::thread td([&]{someclass(shared_mutex,x);});
td.join();
return 0;
}
Be warned: constructing a new thread is a hugely expensive operation, so you should avoid casually spawning new threads if you have the ability to instead reuse existing threads, unless you are only going to create new threads very infrequently.

C++11 When To Use A Memory Fence?

I'm writing some threaded C++11 code, and I'm not totally sure on when I need to use a memory fence or something. So here is basically what I'm doing:
class Worker
{
std::string arg1;
int arg2;
int arg3;
std::thread thread;
public:
Worker( std::string arg1, int arg2, int arg3 )
{
this->arg1 = arg1;
this->arg2 = arg2;
this->arg3 = arg3;
}
void DoWork()
{
this->thread = std::thread( &Worker::Work, this );
}
private:
Work()
{
// Do stuff with args
}
}
int main()
{
Worker worker( "some data", 1, 2 );
worker.DoWork();
// Wait for it to finish
return 0;
}
I was wondering, what steps do I need to take to make sure that the args are safe to access in the Work() function which runs on another thread. Is it enough that it's written in the constructor, and then the thread is created in a separate function? Or do I need a memory fence, and how do I make a memory fence to make sure all 3 args are written by the main thread, and then read by the Worker thread?
Thanks for any help!
The C++11 standard section 30.3.1.2 thread constructors [thread.thread.constr] p5 describes the constructor template <class F, class... Args> explicit thread(F&& f, Args&&... args):
Synchronization: the completion of the invocation of the constructor synchronizes with the beginning of the invocation of the copy of f.
So everything in the current thread happens before the thread function is called. You don't need to do anything special to ensure that the assignments to the Worker members are complete and will be visible to the new thread.
In general, you should never have to use a memory fence when writing multithreaded C++11: synchronization is built into mutexes/atomics and they handle any necessary fences for you. (Caveat: you are on your own if you use relaxed atomics.)

user defined struct can't be passed through tid.send

I have created a mutlithreaded simulator that relies heavily on the native message passing between threads (don't go telling me to go single threaded it's for my thesis on D and I need to get this to work)
after a very durty kludge involving a lot of casts of objects to and from shared. which prolly had some ugly race condition bugs. I decided to create an opaque type that represents an object that can receive messages that should be able to be passed around without all that casting...
no such luck
struct OpaqueFaseSim{
Tid tid;
void send(...){...}
}
void foo(){
Tid tid;
long time;
OpaqueFaseSim ofs;
//...
tid.send(ofs,time);//Error: static assert "Aliases to mutable thread-local data not allowed."
}
why can I pass a Tid around but not a struct containing only a Tid?
and how can I fix this
I think it's because Tid has a MessageBox field which is a class type.
You can type OpaqueFaseSim's tid field as shared or ___gshared and it will work:
struct OpaqueFaseSim{
Bar bar;
shared Tid tid;
// __gshared Tid tid;
}

Visual C++ CreateThread Parameter Problem

I have a class that contains a function that calls create thread, and needs to pass itself (this) as a parameter:
DWORD threadId;
HANDLE h = CreateThread( NULL, 0, runThread, this, 0, &threadId);
My runThread definition is as follows:
DWORD WINAPI runThread(LPVOID args)
{
Obj *t = (Obj*)args;
t->funct();
return 0;
}
Unfortunately, the object t that I get in runThread() gets garbage. My Obj class has a function pointer attribute. Could that be the problem?
class Obj{
void(*funct)();
and in the constructor:
Obj(void(*f)())
{
funct = f;
}
where is my mistake? The function pointer, the createThread itself, or type-casting? I tried whatever I could think of.
Assuming the object has been properly constructed, is there any chance that the object that is creating the thread has gone out of scope after CreateThread is called? This would leave your thread with a garbage object. If not, single step through the code with a debugger, and have a look at the objects 'this' pointer as the thread is being called, with a breakpoint at the thread start to see what it is getting as parameters.
The object was created in my main thread of execution. The error was because the object was going out of scope two lines down in that thread, so when the thread executed there was only garbage at the address.

Resources