Skip to content

Commit

Permalink
Added Thread#name, #name=.
Browse files Browse the repository at this point in the history
  • Loading branch information
brixen committed Jul 20, 2016
1 parent b39b6dd commit 7cd67e4
Show file tree
Hide file tree
Showing 6 changed files with 85 additions and 0 deletions.
18 changes: 18 additions & 0 deletions core/thread.rb
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,24 @@ def self.stop
nil
end

def name
Rubinius.primitive :thread_name
Kernel.raise PrimitiveFailure, "Thread#name primitive failed"
end

def name=(name)
return unless name

thread_name = StringValue(name)
unless thread_name.ascii_only?
Kernel.raise ArgumentError, "name must be ASCII only"
end

Rubinius.invoke_primitive :thread_set_name, self, thread_name

name
end

def fiber_list
Rubinius.primitive :thread_fiber_list
Kernel.raise PrimitiveFailure, "Thread.fiber_list primitive failed"
Expand Down
10 changes: 10 additions & 0 deletions machine/builtin/thread.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -411,6 +411,16 @@ namespace rubinius {
return 0;
}

Object* Thread::name(STATE) {
return String::create(state, vm()->name().c_str());
}

Object* Thread::set_name(STATE, String* name) {
vm()->set_name(state, name->c_str(state));

return name;
}

void Thread::fork(STATE) {
if(int error = start_thread(state, Thread::run)) {
char buf[RBX_STRERROR_BUFSIZE];
Expand Down
6 changes: 6 additions & 0 deletions machine/builtin/thread.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,12 @@ namespace rubinius {

void fork(STATE);

// Rubinius.primitive :thread_name
Object* name(STATE);

// Rubinius.primitive :thread_set_name
Object* set_name(STATE, String* name);

/**
* Retrieve the priority set for this Thread.
*
Expand Down
8 changes: 8 additions & 0 deletions machine/memory/managed.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include "shared_state.hpp"
#include "metrics.hpp"

#include <thread>
#include <sstream>

namespace rubinius {
Expand Down Expand Up @@ -35,6 +36,13 @@ namespace memory {
}
}

void ManagedThread::set_name(STATE, const char* name) {
if(pthread_self() == os_thread_) {
utilities::thread::Thread::set_os_name(name);
}
name_.assign(name);
}

ManagedThread* ManagedThread::current() {
return _current_thread.get();
}
Expand Down
3 changes: 3 additions & 0 deletions machine/memory/managed.hpp
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#ifndef RBX_GC_MANAGED_THREAD
#define RBX_GC_MANAGED_THREAD

#include "defines.hpp"
#include "memory/slab.hpp"
#include "memory/variable_buffer.hpp"
#include "memory/root_buffer.hpp"
Expand Down Expand Up @@ -120,6 +121,8 @@ namespace memory {
return name_;
}

void set_name(STATE, const char* name);

uint32_t thread_id() const {
return id_;
}
Expand Down
40 changes: 40 additions & 0 deletions spec/ruby/core/thread/name_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
# encoding: utf-8
require File.expand_path('../../../spec_helper', __FILE__)

describe "Thread#name=" do
before :each do
@thread = Thread.new { }
end

after :each do
@thread.join
end

it "sets the Thread name" do
@thread.name = "a new name"
@thread.name.should == "a new name"
end

it "ignores setting the Thread's name to nil" do
@thread.name = nil
@thread.name.should be_an_instance_of(String)
end

it "calls #to_str to convert name to String" do
name = mock("Thread#name")
name.should_receive(:to_str).and_return("a thread name")

@thread.name = name
@thread.name.should == "a thread name"
end

it "raises an ArgumentError if the name is not ASCII" do
lambda { @thread.name = "あ" }.should raise_error(ArgumentError)
end
end

describe "Thread#name" do
it "returns a String" do
@thread.name.should be_an_instance_of(String)
end
end

0 comments on commit 7cd67e4

Please sign in to comment.