#include "comms.h"
#include <pthread.h>
-#ifdef __linux__
+#if defined(__linux__) && !defined(NO_UNLINK)
#include <unistd.h> // for unlink()
#endif
#include "uart.h"
void CloseProxmark(void) {
conn.run = false;
+
+#ifdef __BIONIC__
+ // In Android O and later, if an invalid pthread_t is passed to pthread_join, it calls fatal().
+ // https://github.com/aosp-mirror/platform_bionic/blob/ed16b344e75f422fb36fbfd91fb30de339475880/libc/bionic/pthread_internal.cpp#L116-L128
+ //
+ // In Bionic libc, pthread_t is an integer.
+
+ if (USB_communication_thread != 0) {
+ pthread_join(USB_communication_thread, NULL);
+ }
+#else
+ // pthread_t is a struct on other libc, treat as an opaque memory reference
pthread_join(USB_communication_thread, NULL);
- uart_close(sp);
-#ifdef __linux__
+#endif
+
+ if (sp) {
+ uart_close(sp);
+ }
+
+#if defined(__linux__) && !defined(NO_UNLINK)
// Fix for linux, it seems that it is extremely slow to release the serial port file descriptor /dev/*
+ //
+ // This may be disabled at compile-time with -DNO_UNLINK (used for a JNI-based serial port on Android).
if (serial_port_name) {
unlink(serial_port_name);
}
#endif
+
+ // Clean up our state
+ sp = NULL;
+ serial_port_name = NULL;
+#ifdef __BIONIC__
+ memset(&USB_communication_thread, 0, sizeof(pthread_t));
+#endif
}