I tried to emulate aarch64 binary using qemu , I copy all the libraries that this binary depend on. and run it with chroot :
chroot . ./qemu-aarch64-static ./myProcess
The problem is that I see in log that pthread_mutex_init
(implement in so file ) failed
How can I check why pthread_mutex_init
failed? can I see the errno?
I have tried to debug that process ` maybe to see the return value of that function but it doesn't work.
Using chroot . ./qemu-aarch64-static -g 1234 ./myProcess
then connect with gdb-multiarch
file myProcess
set architecture aarch64
target remote 127.0.0.1:1234
b main
c
But the process doesn't stop at main
So I don't know why pthread_mutex_init
failed and why I can't debug that process.
How can I check why
pthread_mutex_init
failed? can I see the errno?
The pthreads functions are among those that return an error number on failure rather than setting the errno
variable.
As with any function call whose failure you cannot reasonably ignore, your program must check calls to pthread_mutex_init
for failure. The natural idiom is
int result;
// ...
result = pthread_mutex_init(&my_mutex, NULL); // assumes default mutex attributes
if (result != 0) {
// ... handle error ...
}
That idiom is already sufficient for easily seeing the error number via a debugger, at least a native debugger. I'm not sure I can explain the behavior you report for gdb-multiarch
, but I suspect that the issue is that you're connecting after the program has started, but trying to break at (entry into) main
.
The question remains, though, how do you actually handle the error. In some cases, you might want to print a diagnostic message. The perror()
function is reasonably good for this, but it uses errno
to determine what message to emit, so maybe ...
errno = result;
perror("pthread_mutex_init");
Messaging alone is rarely sufficient, however. In most cases you will want to follow that up with terminating the program or aborting the function with a failure code.
Note also that for robustness and predictability, a program typically needs to do a lot of error checks along those lines. You may find it makes your code cleaner and clearer to provide one or more macros and / or functions to replace all the boilerplate error handling.