summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorElliott Hughes <enh@google.com>2012-03-27 14:08:24 -0700
committerElliott Hughes <enh@google.com>2012-03-27 14:08:24 -0700
commit22869a9026a08b544eca4cefd67386d347e30d2c (patch)
tree814001ed308907e6562516c247658291cc805545
parentab7b9dcbfc4264a0bc4889c3e463ff88a67f6a30 (diff)
downloadart-22869a9026a08b544eca4cefd67386d347e30d2c.zip
art-22869a9026a08b544eca4cefd67386d347e30d2c.tar.gz
art-22869a9026a08b544eca4cefd67386d347e30d2c.tar.bz2
Warn if a thread attaches without a name and blow up if a thread detaches while running.
Also don't crash if a thread attaches without a name. Doing so is allowed, even if it's not a good idea. Change-Id: If5796af689e9221ce21f443023b0d793a8be15b0
-rw-r--r--src/runtime.cc8
-rw-r--r--src/thread.cc6
-rw-r--r--src/utils.cc16
-rw-r--r--src/utils.h2
4 files changed, 19 insertions, 13 deletions
diff --git a/src/runtime.cc b/src/runtime.cc
index f6311bb..7e0eab5 100644
--- a/src/runtime.cc
+++ b/src/runtime.cc
@@ -818,11 +818,15 @@ void Runtime::BlockSignals() {
void Runtime::AttachCurrentThread(const char* thread_name, bool as_daemon, Object* thread_group) {
Thread::Attach(thread_name, as_daemon, thread_group);
+ if (thread_name == NULL) {
+ LOG(WARNING) << *Thread::Current() << " attached without supplying a name";
+ }
}
void Runtime::DetachCurrentThread() {
- // TODO: check we're not calling DetachCurrentThread from a call stack that
- // includes managed frames. (It's only valid if the stack is all-native.)
+ if (Thread::Current()->GetTopOfStack().GetSP() != NULL) {
+ LOG(FATAL) << *Thread::Current() << " attempting to detach while still running code";
+ }
thread_list_->Unregister();
}
diff --git a/src/thread.cc b/src/thread.cc
index dea554f..8bd7bc2 100644
--- a/src/thread.cc
+++ b/src/thread.cc
@@ -415,8 +415,10 @@ Thread* Thread::Attach(const char* thread_name, bool as_daemon, Object* thread_g
self->CreatePeer(thread_name, as_daemon, thread_group);
} else {
// These aren't necessary, but they improve diagnostics for unit tests & command-line tools.
- self->name_->assign(thread_name);
- ::art::SetThreadName(thread_name);
+ if (thread_name != NULL) {
+ self->name_->assign(thread_name);
+ ::art::SetThreadName(thread_name);
+ }
}
self->GetJniEnv()->locals.AssertEmpty();
diff --git a/src/utils.cc b/src/utils.cc
index bdc5925..03b6172 100644
--- a/src/utils.cc
+++ b/src/utils.cc
@@ -740,12 +740,12 @@ bool StartsWith(const std::string& s, const char* prefix) {
return s.compare(0, strlen(prefix), prefix) == 0;
}
-void SetThreadName(const char* threadName) {
- ANNOTATE_THREAD_NAME(threadName); // For tsan.
+void SetThreadName(const char* thread_name) {
+ ANNOTATE_THREAD_NAME(thread_name); // For tsan.
int hasAt = 0;
int hasDot = 0;
- const char* s = threadName;
+ const char* s = thread_name;
while (*s) {
if (*s == '.') {
hasDot = 1;
@@ -754,11 +754,11 @@ void SetThreadName(const char* threadName) {
}
s++;
}
- int len = s - threadName;
+ int len = s - thread_name;
if (len < 15 || hasAt || !hasDot) {
- s = threadName;
+ s = thread_name;
} else {
- s = threadName + len - 15;
+ s = thread_name + len - 15;
}
#if defined(HAVE_ANDROID_PTHREAD_SETNAME_NP)
// pthread_setname_np fails rather than truncating long strings.
@@ -770,11 +770,11 @@ void SetThreadName(const char* threadName) {
PLOG(WARNING) << "Unable to set the name of current thread to '" << buf << "'";
}
#elif defined(__APPLE__) && MAC_OS_X_VERSION_MAX_ALLOWED >= 1060
- pthread_setname_np(threadName);
+ pthread_setname_np(thread_name);
#elif defined(HAVE_PRCTL)
prctl(PR_SET_NAME, (unsigned long) s, 0, 0, 0); // NOLINT (unsigned long)
#else
- UNIMPLEMENTED(WARNING) << threadName;
+ UNIMPLEMENTED(WARNING) << thread_name;
#endif
}
diff --git a/src/utils.h b/src/utils.h
index 9c18093..b49d764 100644
--- a/src/utils.h
+++ b/src/utils.h
@@ -283,7 +283,7 @@ std::string GetSchedulerGroupName(pid_t tid);
// Sets the name of the current thread. The name may be truncated to an
// implementation-defined limit.
-void SetThreadName(const char* name);
+void SetThreadName(const char* thread_name);
// Find $ANDROID_ROOT, /system, or abort
const char* GetAndroidRoot();