I am starting a new thread from the
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification
method, using
MyThread *thread1 = [[MyThread alloc] init] ;
[thread1 start] ;
where MyThread is a subclass of NSThread.
If I run an empty for loop in the thread's main method and quit, it works fine. But as soon as I try to use a Cocoa API such as NSString or even NSAutoReleasePool, my program just hangs by entering the debugger.
What could be the source of the problem ?
[Hint]: I tried stepping thru the debugger and it once gave me a SIGBUS error. What memory access issues could there be ?
The problem was tricky. I was declaring a large char array of 1 MB in the middle of my main() method. The compiler was pushing this declaration to the top of the compiled method. Somehow this space was too large to ask for and hence the program would crash immediately upon entering the main method. Unfortunately, even when I inserted a return statement much before this declaration, the program would crash because the compiler would push this declaration to the very beginning. I changed that array declaration to a malloc() and the program ran.
Related
I have an application with Vulkan for rendering and glfw for windowing. If I start several threads, each with a different window, I get errors on threading and queue submission even though ALL vulkan calls are protected by a common mutex. The vulkan layer says:
THREADING ERROR : object of type VkQueue is simultaneously used in thread 0x0 and thread 0x7fc365b99700
Here is the skeleton of the loop under which this happens in each thread:
while (!finished) {
window.draw(...);
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}
The draw function skeleton looks like:
draw(Arg arg) {
static std::mutex mtx;
std::lock_guard lock{mtx};
// .... drawing calls. Including
device.acquireNextImageKHR(...);
// Fill command bufers
graphicsQueue.submit(...);
presentQueue.presentKHR(presentInfo);
}
This is C++17 which slightly simplifies the syntax but is otherwise irrelevant.
Clearly everything is under a mutex. I also intercept the call to the debug message. When I do so, I see that one thread is waiting for glfw events, one is printing the vulkan layer message and the other two threads are trying to acquire the mutex for the lock_guard.
I am at a loss as to what is going on or how to even figure out what is causing this.
I am running on linux, and it does not crash. However on Mac OS X, after a random amount of time, the code will crash in a queue submit call of MoltenVK and when the crash happens, I see a similar situation of the threads. That is to say no other thread is inside a Vulkan call.
I'd appreciate any ideas. My next move would be to move all queue submissions to a single thread, though that is not my favorite solution.
PS: I created a complete MCVE under the Vookoo framework. It is at https://github.com/FunMiles/Vookoo/tree/lock_guard_queues and is the example 00-parallelTriangles
To try it, do the following:
git clone https://github.com/FunMiles/Vookoo.git
cd Vookoo
git checkout lock_guard_queues
mkdir build
cd build
cmake ..
make
examples/00-parallelTriangles
The way you call the draw is:
window.draw(device, fw.graphicsQueue(), [&](){//some lambda});
The insides of draw is protected by mutex, but the fw.graphicsQueue() isn't.
fw.graphicsQueue() million abstraction layers below just calls vkGetDeviceQueue. I found executing vkGetDeviceQueue in parallel with vkQueueSubmit causes the validation error.
So there are few issues here:
There is a bug in layers that causes multiple initialization of VkQueue state on vkGetDeviceQueue, which is the cause of the validation error
KhronosGroup/Vulkan-ValidationLayers#1751
Thread id 0 is not a separate issue. As there are not any actual previous accesses, thread id is not recorded. The problem is the layers issue the error because the access count goes into negative because it is previously wrongly reset to 0.
Arguably there is some spec issue here. It is not immediatelly obvious from the text that VkQueue is not actually accessed in vkGetDeviceQueue, except the silent assumption that it is the sane thing to do.
KhronosGroup/Vulkan-Docs#1254
I'm using gdb to debug a multithreaded program.
The program produces a lot of threads that repeatedly process a string (identical thread function).
In that loop, I wish to break if the string in any of these threads equals a predefined constant string. For this I'm using break myfile:1234 if $_streq(managedStr->value(), "testString").
But this breakpoint never gets hit, eventhough I know for sure that managestStr takes the value "testString" for sure.
When leaving the condition, it breaks, but when trying to evaluate the condition manually then, I get an error
The program stopped in another thread while making a function call from GDB.
From this link i learned to set the scheduler-locking option while the program is paused, but setting this option from the very beginning didn't help with the breakpoint not being hit. Instead it will then get get
Error in testing breakpoint condition:
The program stopped in another thread while making a function call from GDB.
Evaluation of the expression containing the function
(ManageString::value()) will be abandoned.
When the function is done executing, GDB will silently stop.
[Switching to Thread 0x7ffd35fb3700 (LWP 24354)]
What can I do to achieve the desired behaviour?
break myfile:1234 if $_streq(managedStr->value(), "testString")
That should work, and the fact that it doesn't work implies a bug in GDB.
That said, this method of debugging is exceedingly slow, because GDB has to stop every thread at line 1234 and then examine the memory values (i.e. evaluate the condition).
Usually it is much faster to insert a little bit of helper code into the program:
if (strcmp(namagedStr->value(), "testString") == 0) {
printf("DEBUG: match\n"); // set breakpoint here!
}
and rebuild it.
Now instead of stopping every thread all the time and evaluating the condition, GDB will set a breakpoint on code that is only reached when the condition is true. This will be 100 to 1000 times faster (depending on number of threads).
This technique could be trivially extended if you need to vary the actual value you are looking for from run to run, or even within a single run, by adding a global variable:
const char *str_to_match = "testString"; // variable can be overwritten in GDB
if (strcmp(managedStr->value(), str_to_match) == 0) {
...
}
The following functions and fields are part of the same class in a Visual Studio DLL. Data is continuously being read and processed using the run function on a thread. However, getPoints is being accessed in a Qt app on a QTimer. I don't wan't to miss a single processed vector, because it seems it could be skipping leading to jumpy data. What's the safest way to get the points to the updated version?
If possible I'd like an answer that uses the C++ standard library as I've been exploring mutex-es, but it still seems to lead to jumpy data.
vector<float> points;
// std::mutex ioMutex;
// function running on a thread
void run(){
while(running){
//ioMutex.lock()
vector<byte> data = ReadData()
points = processData(data);
//ioMutex.unlock()
}
}
vector<float> getPoints(){
return points;
}
I believe there is a mistake in your code. The while loop will consume all the process activity and will not allow proper functionality of other functions. In Qt, in such continuous loops, usually it is a good habit to use the following because it actually gives other process time to access the event buffer properly. If this dll is written in Qt, please add the following within the while loop
QCoreApplication::processEvents();
The safest (and probably easiest) way to deliver your points-data to the main thread is by calling qApp->postEvent() with an object of a custom QEvent-subclass that contains your vector<float> as a member-variable.
That will cause the event(QEvent *) method of (whatever Qt object you specified as the first argument to postEvent()) to be called from inside the main/GUI thread, and so you can override that method to read the vector<float> out of the QEvent-subclassed object and update the GUI with that data.
I have an issue with Microsoft Active Accessibility and threads in Qt. Code for example below:
CComPtr<IAccessible> _pAccMain;
HWND _hWnd = ...; // Handle of some window
HRESULT hr0 = ::AccessibleObjectFromWindow(_hWnd,
OBJID_CLIENT,
IID_IAccessible,
(void**)(&_pAccMain));
long childCount = 0;
HRESULT hr1 = _pAccMain->get_accChildCount(&childCount);
It works fine and in the main-thread these functions returns success for hr0 and hr1 and I got a proper success data for _pAccMain and childCount. But when I create a new thread and try to use the code in that new thread I got again success for hr0 and hr1, but I got different data in _pAccMain and childCount. I.e. the same code have more than one behavior in different threads.
Why another thread have another behavior in that example?
How can I fix it behavior?
Can I fix it?
There is no promise that AccessibleObjectFromWindow calls return the same interface pointer, so _pAccMain values don't have to be pointer-equal
Additionally, calling from different threads (apartments) might have marshaling involved, in which case you might get a proxy interface, not real object interface; it is behavior by design that those are different pointers
By mentioning different childCount you should have mentioned if worker thread get you zero, or otherwise what exactly is different in child enumeration
There is no free COM pointer passing between threads in COM, what your question suggests you are doing; you can only do this with MTA threads, and otherwise you have to marshal/unmarshal pointers to get a valid pointer in another thread
It seems like Qt quietly initialized COM in each new thread and after that CoInitializeEx with any COINIT can't do anything with it. But if you call in new QThread CoUnitialize before CoInitializeEx all will be ok, it is works for me.
I'm working on a project where I need to make a program run on multiple threads. However, I'm running into a bit of an issue.
In my program, I have an accessory function called 'func_call'.
If I use this in my code:
func_call((void*) &my_pixels);
The program runs fine.
However, if I try to create a thread, and then run the function on that, the program runs into a segmentation fault.
pthread_t thread;
pthread_create (&thread, NULL, (void*)&func_call, (void*) &my_pixels);
I've included pthread.h in my program. Any ideas what might be wrong?
You are not handling data in a thread safe manner:
the thread copies data from the thread argument, which is a pointer to the main thread's my_pixels variable; the main thread may exit, making my_pixles invalid.
the thread uses scene, main thread calls free_scene() on it, which I imagine makes it invalid
the thread calls printf(), the main thread closes stdout (kind of unusual itself)
the thread updates the picture array, the main thread accesses picture to output data from it
It looks like you should just wait for the thread to finish its work after creating it - call pthread_join() to do that.
For a single thread, that would seem to be pointless (you've just turned a multi-threaded program into a single threaded program). But on the basis of code that's commented out, it looks like you're planning to start up several threads that work on chunks of the data. So, when you get to the point of trying that again, make sure you join all the threads you start. As long as the threads don't modify the same data, it'll work. Note that you'll need to use separate my_pixels instances for each thread (make an array of them, just like you did with pthreads), or some threads will likely get parameters that are intended for a different thread.
Without knowing what func_call does, it is difficult to give you an answer. Nevertheless, here are few possibilities
Does func_call use some sort of a global state - check if that is initialized properly from within the thread. The order of execution of threads is not always the same for every execution
Not knowing your operating system (AIX /Linux/Solaris etc) it is difficult to answer this, but please check your compilation options
Please provide the signal trapped and atleast a few lines of the stack-trace - for all the threads. One thing you can check for yourself is to print the threads' stack-track (using threads/thread or pthread and thread current <x> based on the debugger) and and if there is a common data that is being accessed. It is most likely that the segfault occurred when two threads were trying to read off the other's (uncommitted) change
Hope that helps.
Edit:
After checking your code, I think the problem is the global picture array. You seem to be modifying that in the thread function without any guards. You loop using px and py and all the threads will have the same px and py and will try to write into the picture array at the same time. Please try to modify your code to prevent multiple threads from stepping on each other's data modifications.
Is func_call a function, or a function pointer? If it's a function pointer, there is your problem: you took the address of a function pointer and then cast it.
People are guessing because you've provided only a fraction of the program, which mentions names like func_call with no declaration in scope.
Your compiler must be giving you diagnostics about this program, because you're passing a (void *) expression to a function pointer parameter.
Define your thread function in a way that is compatible with pthread_create, and then just call it without any casts.