concurrent-ruby 0.6.1 → 0.7.0.rc0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (94) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +1 -1
  3. data/lib/concurrent.rb +3 -4
  4. data/lib/concurrent/atomic.rb +46 -0
  5. data/lib/concurrent/atomic_reference/concurrent_update_error.rb +7 -0
  6. data/lib/concurrent/atomic_reference/delegated_update.rb +28 -0
  7. data/lib/concurrent/atomic_reference/direct_update.rb +28 -0
  8. data/lib/concurrent/atomic_reference/jruby.rb +8 -0
  9. data/lib/concurrent/atomic_reference/mutex_atomic.rb +47 -0
  10. data/lib/concurrent/atomic_reference/numeric_cas_wrapper.rb +24 -0
  11. data/lib/concurrent/atomic_reference/rbx.rb +16 -0
  12. data/lib/concurrent/atomic_reference/ruby.rb +16 -0
  13. data/lib/concurrent/atomics.rb +1 -1
  14. data/lib/concurrent/configuration.rb +1 -1
  15. data/lib/concurrent/supervisor.rb +1 -1
  16. data/lib/concurrent/timer_task.rb +0 -36
  17. data/lib/concurrent/version.rb +1 -1
  18. data/lib/concurrent_ruby_ext.so +0 -0
  19. data/lib/extension_helper.rb +9 -0
  20. metadata +16 -148
  21. data/lib/concurrent/actor/actor.rb +0 -270
  22. data/lib/concurrent/actor/postable.rb +0 -102
  23. data/lib/concurrent/actors.rb +0 -2
  24. data/lib/concurrent/atomic/atomic.rb +0 -48
  25. data/lib/concurrent/runnable.rb +0 -90
  26. data/lib/concurrent/stoppable.rb +0 -20
  27. data/spec/concurrent/actor/actor_spec.rb +0 -376
  28. data/spec/concurrent/actor/postable_shared.rb +0 -218
  29. data/spec/concurrent/actress_spec.rb +0 -211
  30. data/spec/concurrent/agent_spec.rb +0 -500
  31. data/spec/concurrent/async_spec.rb +0 -352
  32. data/spec/concurrent/atomic/atomic_boolean_spec.rb +0 -172
  33. data/spec/concurrent/atomic/atomic_fixnum_spec.rb +0 -186
  34. data/spec/concurrent/atomic/atomic_spec.rb +0 -133
  35. data/spec/concurrent/atomic/condition_spec.rb +0 -171
  36. data/spec/concurrent/atomic/copy_on_notify_observer_set_spec.rb +0 -10
  37. data/spec/concurrent/atomic/copy_on_write_observer_set_spec.rb +0 -10
  38. data/spec/concurrent/atomic/count_down_latch_spec.rb +0 -151
  39. data/spec/concurrent/atomic/cyclic_barrier_spec.rb +0 -248
  40. data/spec/concurrent/atomic/event_spec.rb +0 -200
  41. data/spec/concurrent/atomic/observer_set_shared.rb +0 -242
  42. data/spec/concurrent/atomic/thread_local_var_spec.rb +0 -113
  43. data/spec/concurrent/channel/buffered_channel_spec.rb +0 -151
  44. data/spec/concurrent/channel/channel_spec.rb +0 -39
  45. data/spec/concurrent/channel/probe_spec.rb +0 -77
  46. data/spec/concurrent/channel/unbuffered_channel_spec.rb +0 -132
  47. data/spec/concurrent/collection/blocking_ring_buffer_spec.rb +0 -149
  48. data/spec/concurrent/collection/priority_queue_spec.rb +0 -317
  49. data/spec/concurrent/collection/ring_buffer_spec.rb +0 -126
  50. data/spec/concurrent/configuration_spec.rb +0 -69
  51. data/spec/concurrent/dataflow_spec.rb +0 -242
  52. data/spec/concurrent/delay_spec.rb +0 -91
  53. data/spec/concurrent/dereferenceable_shared.rb +0 -146
  54. data/spec/concurrent/exchanger_spec.rb +0 -66
  55. data/spec/concurrent/executor/cached_thread_pool_shared.rb +0 -115
  56. data/spec/concurrent/executor/fixed_thread_pool_shared.rb +0 -136
  57. data/spec/concurrent/executor/global_thread_pool_shared.rb +0 -35
  58. data/spec/concurrent/executor/immediate_executor_spec.rb +0 -12
  59. data/spec/concurrent/executor/java_cached_thread_pool_spec.rb +0 -44
  60. data/spec/concurrent/executor/java_fixed_thread_pool_spec.rb +0 -64
  61. data/spec/concurrent/executor/java_single_thread_executor_spec.rb +0 -21
  62. data/spec/concurrent/executor/java_thread_pool_executor_spec.rb +0 -71
  63. data/spec/concurrent/executor/per_thread_executor_spec.rb +0 -57
  64. data/spec/concurrent/executor/ruby_cached_thread_pool_spec.rb +0 -69
  65. data/spec/concurrent/executor/ruby_fixed_thread_pool_spec.rb +0 -39
  66. data/spec/concurrent/executor/ruby_single_thread_executor_spec.rb +0 -18
  67. data/spec/concurrent/executor/ruby_thread_pool_executor_spec.rb +0 -171
  68. data/spec/concurrent/executor/safe_task_executor_spec.rb +0 -103
  69. data/spec/concurrent/executor/thread_pool_class_cast_spec.rb +0 -52
  70. data/spec/concurrent/executor/thread_pool_executor_shared.rb +0 -155
  71. data/spec/concurrent/executor/thread_pool_shared.rb +0 -269
  72. data/spec/concurrent/executor/timer_set_spec.rb +0 -183
  73. data/spec/concurrent/future_spec.rb +0 -329
  74. data/spec/concurrent/ivar_spec.rb +0 -215
  75. data/spec/concurrent/mvar_spec.rb +0 -380
  76. data/spec/concurrent/obligation_shared.rb +0 -102
  77. data/spec/concurrent/obligation_spec.rb +0 -282
  78. data/spec/concurrent/observable_shared.rb +0 -177
  79. data/spec/concurrent/observable_spec.rb +0 -56
  80. data/spec/concurrent/options_parser_spec.rb +0 -71
  81. data/spec/concurrent/promise_spec.rb +0 -367
  82. data/spec/concurrent/runnable_shared.rb +0 -68
  83. data/spec/concurrent/runnable_spec.rb +0 -235
  84. data/spec/concurrent/scheduled_task_spec.rb +0 -340
  85. data/spec/concurrent/stoppable_shared.rb +0 -37
  86. data/spec/concurrent/supervisor_spec.rb +0 -1149
  87. data/spec/concurrent/timer_task_spec.rb +0 -256
  88. data/spec/concurrent/tvar_spec.rb +0 -137
  89. data/spec/concurrent/utility/processor_count_spec.rb +0 -20
  90. data/spec/concurrent/utility/timeout_spec.rb +0 -50
  91. data/spec/concurrent/utility/timer_spec.rb +0 -52
  92. data/spec/spec_helper.rb +0 -41
  93. data/spec/support/example_group_extensions.rb +0 -52
  94. data/spec/support/less_than_or_equal_to_matcher.rb +0 -5
@@ -1,146 +0,0 @@
1
- require 'spec_helper'
2
-
3
- share_examples_for :dereferenceable do
4
-
5
- it 'defaults :dup_on_deref to false' do
6
- value = 'value'
7
- value.should_not_receive(:dup).with(any_args)
8
-
9
- subject = dereferenceable_subject(value)
10
- subject.value.should eq 'value'
11
-
12
- subject = dereferenceable_subject(value, dup_on_deref: false)
13
- subject.value.should eq 'value'
14
-
15
- subject = dereferenceable_subject(value, dup: false)
16
- subject.value.should eq 'value'
17
- end
18
-
19
- it 'calls #dup when the :dup_on_deref option is true' do
20
- value = 'value'
21
-
22
- subject = dereferenceable_subject(value, dup_on_deref: true)
23
- subject.value.object_id.should_not eq value.object_id
24
- subject.value.should eq 'value'
25
-
26
- subject = dereferenceable_subject(value, dup: true)
27
- subject.value.object_id.should_not eq value.object_id
28
- subject.value.should eq 'value'
29
- end
30
-
31
- it 'defaults :freeze_on_deref to false' do
32
- value = 'value'
33
- value.should_not_receive(:freeze).with(any_args)
34
-
35
- subject = dereferenceable_subject(value)
36
- subject.value.should eq 'value'
37
-
38
- subject = dereferenceable_subject(value, freeze_on_deref: false)
39
- subject.value.should eq 'value'
40
-
41
- subject = dereferenceable_subject(value, freeze: false)
42
- subject.value.should eq 'value'
43
- end
44
-
45
- it 'calls #freeze when the :freeze_on_deref option is true' do
46
- value = 'value'
47
-
48
- subject = dereferenceable_subject(value, freeze_on_deref: true)
49
- subject.value.should be_frozen
50
- subject.value.should eq 'value'
51
-
52
- subject = dereferenceable_subject(value, freeze: true)
53
- subject.value.should be_frozen
54
- subject.value.should eq 'value'
55
- end
56
-
57
- it 'defaults :copy_on_deref to nil' do
58
- value = 'value'
59
-
60
- subject = dereferenceable_subject(value)
61
- subject.value.object_id.should == value.object_id
62
- subject.value.should eq 'value'
63
-
64
- subject = dereferenceable_subject(value, copy_on_deref: nil)
65
- subject.value.object_id.should == value.object_id
66
- subject.value.should eq 'value'
67
-
68
- subject = dereferenceable_subject(value, copy: nil)
69
- subject.value.object_id.should == value.object_id
70
- subject.value.should eq 'value'
71
- end
72
-
73
- it 'calls the block when the :copy_on_deref option is passed a proc' do
74
- value = 'value'
75
- copy = proc{|val| 'copy' }
76
-
77
- subject = dereferenceable_subject(value, copy_on_deref: copy)
78
- subject.value.object_id.should_not == value.object_id
79
-
80
- subject = dereferenceable_subject(value, copy: copy)
81
- subject.value.object_id.should_not == value.object_id
82
- end
83
-
84
- it 'calls the :copy block first followed by #dup followed by #freeze' do
85
- value = 'value'
86
- copied = 'copied'
87
- dup = 'dup'
88
- frozen = 'frozen'
89
- copy = proc{|val| copied }
90
-
91
- copied.should_receive(:dup).at_least(:once).with(no_args).and_return(dup)
92
- dup.should_receive(:freeze).at_least(:once).with(no_args).and_return(frozen)
93
-
94
- subject = dereferenceable_subject(value, dup_on_deref: true, freeze_on_deref: true, copy_on_deref: copy)
95
- subject.value.should eq frozen
96
- end
97
-
98
- it 'does not call #dup when #dup_on_deref is set and the value is nil' do
99
- allow_message_expectations_on_nil
100
- result = nil
101
- result.should_not_receive(:dup).with(any_args)
102
- subject = dereferenceable_subject(result, dup_on_deref: true)
103
- subject.value
104
- end
105
-
106
- it 'does not call #freeze when #freeze_on_deref is set and the value is nil' do
107
- allow_message_expectations_on_nil
108
- result = nil
109
- result.should_not_receive(:freeze).with(any_args)
110
- subject = dereferenceable_subject(result, freeze_on_deref: true)
111
- subject.value
112
- end
113
-
114
- it 'does not call the #copy_on_deref block when the value is nil' do
115
- copier = proc { 42 }
116
- subject = dereferenceable_subject(nil, copy_on_deref: copier)
117
- subject.value.should be_nil
118
- end
119
-
120
- it 'locks when all options are false' do
121
- subject = dereferenceable_subject(0)
122
- mutex = double('mutex')
123
- subject.stub(:mutex).and_return(mutex)
124
- mutex.should_receive(:lock).at_least(:once)
125
- mutex.should_receive(:unlock).at_least(:once)
126
- subject.value
127
- end
128
-
129
- it 'supports dereference flags with observers' do
130
- if dereferenceable_subject(0).respond_to?(:add_observer)
131
-
132
- result = 'result'
133
- result.should_receive(:dup).at_least(:once).and_return(result)
134
- result.should_receive(:freeze).at_least(:once).and_return(result)
135
- copier = proc { result }
136
-
137
- observer = double('observer')
138
- observer.should_receive(:update).at_least(:once).with(any_args)
139
-
140
- subject = dereferenceable_observable(dup_on_deref: true, freeze_on_deref: true, copy_on_deref: copier)
141
-
142
- subject.add_observer(observer)
143
- execute_dereferenceable(subject)
144
- end
145
- end
146
- end
@@ -1,66 +0,0 @@
1
- require 'spec_helper'
2
-
3
- module Concurrent
4
-
5
- describe Exchanger do
6
-
7
- subject { Exchanger.new }
8
- let!(:exchanger) { subject } # let is not thread safe, let! creates the object before ensuring uniqueness
9
-
10
- describe 'exchange' do
11
- context 'without timeout' do
12
- it 'should block' do
13
- t = Thread.new { exchanger.exchange(1) }
14
- sleep(0.1)
15
- t.status.should eq 'sleep'
16
- end
17
-
18
- it 'should receive the other value' do
19
- first_value = nil
20
- second_value = nil
21
-
22
- Thread.new { first_value = exchanger.exchange(2) }
23
- Thread.new { second_value = exchanger.exchange(4) }
24
-
25
- sleep(0.1)
26
-
27
- first_value.should eq 4
28
- second_value.should eq 2
29
- end
30
-
31
- it 'can be reused' do
32
- first_value = nil
33
- second_value = nil
34
-
35
- Thread.new { first_value = exchanger.exchange(1) }
36
- Thread.new { second_value = exchanger.exchange(0) }
37
-
38
- sleep(0.1)
39
-
40
- Thread.new { first_value = exchanger.exchange(10) }
41
- Thread.new { second_value = exchanger.exchange(12) }
42
-
43
- sleep(0.1)
44
-
45
- first_value.should eq 12
46
- second_value.should eq 10
47
- end
48
- end
49
-
50
- context 'with timeout' do
51
- it 'should block until timeout' do
52
-
53
- value = 0
54
- start = Time.now.to_f
55
-
56
- future = Concurrent::Future.execute do
57
- exchanger.exchange(2, 0.2)
58
- end
59
-
60
- future.value.should be_nil
61
- (Time.now.to_f - start).should >= 0.2
62
- end
63
- end
64
- end
65
- end
66
- end
@@ -1,115 +0,0 @@
1
- require 'spec_helper'
2
- require_relative 'thread_pool_shared'
3
-
4
- share_examples_for :cached_thread_pool do
5
-
6
- subject do
7
- described_class.new(overflow_policy: :discard)
8
- end
9
-
10
- after(:each) do
11
- subject.kill
12
- sleep(0.1)
13
- end
14
-
15
- it_should_behave_like :thread_pool
16
-
17
- context '#initialize' do
18
-
19
- it 'sets :max_length to DEFAULT_MAX_POOL_SIZE' do
20
- described_class.new.max_length.should eq described_class::DEFAULT_MAX_POOL_SIZE
21
- end
22
-
23
- it 'sets :min_length to DEFAULT_MIN_POOL_SIZE' do
24
- subject = described_class.new.min_length.should eq described_class::DEFAULT_MIN_POOL_SIZE
25
- end
26
-
27
- it 'sets :idletime to DEFAULT_THREAD_IDLETIMEOUT' do
28
- subject = described_class.new.idletime.should eq described_class::DEFAULT_THREAD_IDLETIMEOUT
29
- end
30
-
31
- it 'sets :max_queue to DEFAULT_MAX_QUEUE_SIZE' do
32
- subject = described_class.new.max_queue.should eq described_class::DEFAULT_MAX_QUEUE_SIZE
33
- end
34
- end
35
-
36
- context '#min_length' do
37
-
38
- it 'returns zero on creation' do
39
- subject.min_length.should eq 0
40
- end
41
-
42
- it 'returns zero while running' do
43
- 10.times{ subject.post{ nil } }
44
- sleep(0.1)
45
- subject.min_length.should eq 0
46
- end
47
-
48
- it 'returns zero once shutdown' do
49
- 10.times{ subject.post{ nil } }
50
- sleep(0.1)
51
- subject.shutdown
52
- subject.wait_for_termination(1)
53
- subject.min_length.should eq 0
54
- end
55
- end
56
-
57
- context '#max_length' do
58
-
59
- it 'returns :max_length on creation' do
60
- subject.max_length.should eq described_class::DEFAULT_MAX_POOL_SIZE
61
- end
62
-
63
- it 'returns :max_length while running' do
64
- 10.times{ subject.post{ nil } }
65
- sleep(0.1)
66
- subject.max_length.should eq described_class::DEFAULT_MAX_POOL_SIZE
67
- end
68
-
69
- it 'returns :max_length once shutdown' do
70
- 10.times{ subject.post{ nil } }
71
- sleep(0.1)
72
- subject.shutdown
73
- subject.wait_for_termination(1)
74
- subject.max_length.should eq described_class::DEFAULT_MAX_POOL_SIZE
75
- end
76
- end
77
-
78
- context '#largest_length' do
79
-
80
- it 'returns zero on creation' do
81
- subject.largest_length.should eq 0
82
- end
83
-
84
- it 'returns a non-zero number once tasks have been received' do
85
- 10.times{ subject.post{ sleep(0.1) } }
86
- sleep(0.1)
87
- subject.largest_length.should > 0
88
- end
89
-
90
- it 'returns a non-zero number after shutdown if tasks have been received' do
91
- 10.times{ subject.post{ sleep(0.1) } }
92
- sleep(0.1)
93
- subject.shutdown
94
- subject.wait_for_termination(1)
95
- subject.largest_length.should > 0
96
- end
97
- end
98
-
99
- context '#status' do
100
-
101
- it 'returns an array' do
102
- subject.stub(:warn)
103
- subject.status.should be_kind_of(Array)
104
- end
105
- end
106
-
107
- context '#idletime' do
108
-
109
- subject{ described_class.new(idletime: 42) }
110
-
111
- it 'returns the thread idletime' do
112
- subject.idletime.should eq described_class::DEFAULT_THREAD_IDLETIMEOUT
113
- end
114
- end
115
- end
@@ -1,136 +0,0 @@
1
- require 'spec_helper'
2
- require_relative 'thread_pool_shared'
3
-
4
- share_examples_for :fixed_thread_pool do
5
-
6
- let!(:num_threads){ 5 }
7
- subject { described_class.new(num_threads) }
8
-
9
- after(:each) do
10
- subject.kill
11
- sleep(0.1)
12
- end
13
-
14
- it_should_behave_like :thread_pool
15
-
16
- context '#initialize' do
17
-
18
- it 'raises an exception when the pool length is less than one' do
19
- lambda {
20
- described_class.new(0)
21
- }.should raise_error(ArgumentError)
22
- end
23
- end
24
-
25
- context '#min_length' do
26
-
27
- it 'returns :num_threads on creation' do
28
- subject.min_length.should eq num_threads
29
- end
30
-
31
- it 'returns :num_threads while running' do
32
- 10.times{ subject.post{ nil } }
33
- sleep(0.1)
34
- subject.min_length.should eq num_threads
35
- end
36
-
37
- it 'returns :num_threads once shutdown' do
38
- 10.times{ subject.post{ nil } }
39
- sleep(0.1)
40
- subject.shutdown
41
- subject.wait_for_termination(1)
42
- subject.min_length.should eq num_threads
43
- end
44
- end
45
-
46
- context '#max_length' do
47
-
48
- it 'returns :num_threads on creation' do
49
- subject.max_length.should eq num_threads
50
- end
51
-
52
- it 'returns :num_threads while running' do
53
- 10.times{ subject.post{ nil } }
54
- sleep(0.1)
55
- subject.max_length.should eq num_threads
56
- end
57
-
58
- it 'returns :num_threads once shutdown' do
59
- 10.times{ subject.post{ nil } }
60
- sleep(0.1)
61
- subject.shutdown
62
- subject.wait_for_termination(1)
63
- subject.max_length.should eq num_threads
64
- end
65
- end
66
-
67
- context '#length' do
68
-
69
- it 'returns :num_threads while running' do
70
- 10.times{ subject.post{ nil } }
71
- sleep(0.1)
72
- subject.length.should eq num_threads
73
- end
74
- end
75
-
76
- context '#largest_length' do
77
-
78
- it 'returns zero on creation' do
79
- subject.largest_length.should eq 0
80
- end
81
-
82
- it 'returns :num_threads while running' do
83
- 10.times{ subject.post{ nil } }
84
- sleep(0.1)
85
- subject.largest_length.should eq num_threads
86
- end
87
-
88
- it 'returns :num_threads once shutdown' do
89
- 10.times{ subject.post{ nil } }
90
- sleep(0.1)
91
- subject.shutdown
92
- subject.wait_for_termination(1)
93
- subject.largest_length.should eq num_threads
94
- end
95
- end
96
-
97
- context '#status' do
98
-
99
- it 'returns an array' do
100
- subject.stub(:warn)
101
- subject.status.should be_kind_of(Array)
102
- end
103
- end
104
-
105
- context '#idletime' do
106
-
107
- it 'returns zero' do
108
- subject.idletime.should eq 0
109
- end
110
- end
111
-
112
- context '#kill' do
113
-
114
- it 'attempts to kill all in-progress tasks' do
115
- thread_count = [subject.length, 5].max
116
- @expected = false
117
- thread_count.times{ subject.post{ sleep(1) } }
118
- subject.post{ @expected = true }
119
- sleep(0.1)
120
- subject.kill
121
- sleep(0.1)
122
- @expected.should be_false
123
- end
124
- end
125
-
126
- context 'worker creation and caching' do
127
-
128
- it 'never creates more than :num_threads threads' do
129
- pool = described_class.new(5)
130
- 100.times{ pool << proc{ sleep(1) } }
131
- sleep(0.1)
132
- pool.current_length.should eq 5
133
- pool.kill
134
- end
135
- end
136
- end