29 #include "runtime/atomic.hpp"
30 #include "runtime/interfaceSupport.inline.hpp"
31 #include "runtime/orderAccess.hpp"
32 #include "runtime/os.hpp"
33 #include "runtime/semaphore.inline.hpp"
34 #include "runtime/synchronizer.hpp"
35 #include "threadHelper.inline.hpp"
36 #include "unittest.hpp"
37 #include "utilities/globalDefinitions.hpp"
38 #include "utilities/ostream.hpp"
39
40 // The test doesn't work for PRODUCT because it needs WizardMode
41 #ifndef PRODUCT
42
43 static void assert_test_pattern(Handle object, const char* pattern) {
44 stringStream st;
45 object->print_on(&st);
46 ASSERT_THAT(st.base(), testing::HasSubstr(pattern));
47 }
48
49 class LockerThread : public JavaTestThread {
50 oop _obj;
51 public:
52 LockerThread(Semaphore* post, oop obj) : JavaTestThread(post), _obj(obj) {}
53 virtual ~LockerThread() {}
54
55 void main_run() {
56 JavaThread* THREAD = JavaThread::current();
57 HandleMark hm(THREAD);
58 Handle h_obj(THREAD, _obj);
59 ResourceMark rm(THREAD);
60
61 // Wait gets the lock inflated.
62 // The object will stay locked for the context of 'ol' so the lock will
63 // still be inflated after the notify_all() call. Deflation can't happen
64 // while an ObjectMonitor is "busy" and being locked is the most "busy"
65 // state we have...
66 ObjectLocker ol(h_obj, THREAD);
67 ol.notify_all(THREAD);
68 assert_test_pattern(h_obj, "monitor");
69 }
70 };
71
72
73 TEST_VM(markWord, printing) {
74 JavaThread* THREAD = JavaThread::current();
75 ThreadInVMfromNative invm(THREAD);
76 ResourceMark rm(THREAD);
77
78 oop obj = vmClasses::Byte_klass()->allocate_instance(THREAD);
79
80 FlagSetting fs(WizardMode, true);
81
82 HandleMark hm(THREAD);
83 Handle h_obj(THREAD, obj);
84
85 // Thread tries to lock it.
86 {
87 ObjectLocker ol(h_obj, THREAD);
88 assert_test_pattern(h_obj, "locked");
89 }
90 assert_test_pattern(h_obj, "is_unlocked no_hash");
91
92 // Hash the object then print it.
93 intx hash = h_obj->identity_hash();
94 assert_test_pattern(h_obj, "is_unlocked hash=0x");
95
96 // Wait gets the lock inflated.
97 {
98 ObjectLocker ol(h_obj, THREAD);
99
100 Semaphore done(0);
101 LockerThread* st;
102 st = new LockerThread(&done, h_obj());
103 st->doit();
104
105 ol.wait(THREAD);
106 assert_test_pattern(h_obj, "monitor");
107 done.wait_with_safepoint_check(THREAD); // wait till the thread is done.
108 }
109 }
110 #endif // PRODUCT
|
29 #include "runtime/atomic.hpp"
30 #include "runtime/interfaceSupport.inline.hpp"
31 #include "runtime/orderAccess.hpp"
32 #include "runtime/os.hpp"
33 #include "runtime/semaphore.inline.hpp"
34 #include "runtime/synchronizer.hpp"
35 #include "threadHelper.inline.hpp"
36 #include "unittest.hpp"
37 #include "utilities/globalDefinitions.hpp"
38 #include "utilities/ostream.hpp"
39
40 // The test doesn't work for PRODUCT because it needs WizardMode
41 #ifndef PRODUCT
42
43 static void assert_test_pattern(Handle object, const char* pattern) {
44 stringStream st;
45 object->print_on(&st);
46 ASSERT_THAT(st.base(), testing::HasSubstr(pattern));
47 }
48
49 static void assert_mark_word_print_pattern(Handle object, const char* pattern) {
50 if (LockingMode == LM_MONITOR) {
51 // With heavy monitors, we do not use the mark word. Printing the oop only shows "monitor" regardless of the
52 // locking state.
53 assert_test_pattern(object, "monitor");
54 } else {
55 assert_test_pattern(object, pattern);
56 }
57 }
58
59 class LockerThread : public JavaTestThread {
60 oop _obj;
61 public:
62 LockerThread(Semaphore* post, oop obj) : JavaTestThread(post), _obj(obj) {}
63 virtual ~LockerThread() {}
64
65 void main_run() {
66 JavaThread* THREAD = JavaThread::current();
67 HandleMark hm(THREAD);
68 Handle h_obj(THREAD, _obj);
69 ResourceMark rm(THREAD);
70
71 // Wait gets the lock inflated.
72 // The object will stay locked for the context of 'ol' so the lock will
73 // still be inflated after the notify_all() call. Deflation can't happen
74 // while an ObjectMonitor is "busy" and being locked is the most "busy"
75 // state we have...
76 ObjectLocker ol(h_obj, THREAD);
77 ol.notify_all(THREAD);
78 assert_test_pattern(h_obj, "monitor");
79 }
80 };
81
82
83 TEST_VM(markWord, printing) {
84 JavaThread* THREAD = JavaThread::current();
85 ThreadInVMfromNative invm(THREAD);
86 ResourceMark rm(THREAD);
87
88 oop obj = vmClasses::Byte_klass()->allocate_instance(THREAD);
89
90 FlagSetting fs(WizardMode, true);
91
92 HandleMark hm(THREAD);
93 Handle h_obj(THREAD, obj);
94
95 // Thread tries to lock it.
96 {
97 ObjectLocker ol(h_obj, THREAD);
98 assert_mark_word_print_pattern(h_obj, "locked");
99 }
100 assert_mark_word_print_pattern(h_obj, "is_unlocked no_hash");
101
102 // Hash the object then print it.
103 intx hash = h_obj->identity_hash();
104 assert_mark_word_print_pattern(h_obj, "is_unlocked hash=0x");
105
106 // Wait gets the lock inflated.
107 {
108 ObjectLocker ol(h_obj, THREAD);
109
110 Semaphore done(0);
111 LockerThread* st;
112 st = new LockerThread(&done, h_obj());
113 st->doit();
114
115 ol.wait(THREAD);
116 assert_test_pattern(h_obj, "monitor");
117 done.wait_with_safepoint_check(THREAD); // wait till the thread is done.
118 }
119 }
120
121 static void assert_unlocked_state(markWord mark) {
122 EXPECT_FALSE(mark.has_displaced_mark_helper());
123 if (LockingMode == LM_LEGACY) {
124 EXPECT_FALSE(mark.has_locker());
125 } else if (LockingMode == LM_LIGHTWEIGHT) {
126 EXPECT_FALSE(mark.is_fast_locked());
127 }
128 EXPECT_FALSE(mark.has_monitor());
129 EXPECT_FALSE(mark.is_being_inflated());
130 EXPECT_FALSE(mark.is_locked());
131 EXPECT_TRUE(mark.is_unlocked());
132 }
133
134 static void assert_copy_set_hash(markWord mark) {
135 const intptr_t hash = 4711;
136 EXPECT_TRUE(mark.has_no_hash());
137 markWord copy = mark.copy_set_hash(hash);
138 EXPECT_EQ(hash, copy.hash());
139 EXPECT_FALSE(copy.has_no_hash());
140 }
141
142 static void assert_type(markWord mark) {
143 EXPECT_FALSE(mark.is_flat_array());
144 EXPECT_FALSE(mark.is_inline_type());
145 EXPECT_FALSE(mark.is_larval_state());
146 EXPECT_FALSE(mark.is_null_free_array());
147 }
148
149 TEST_VM(markWord, prototype) {
150 markWord mark = markWord::prototype();
151 assert_unlocked_state(mark);
152 EXPECT_TRUE(mark.is_neutral());
153
154 assert_type(mark);
155
156 EXPECT_TRUE(mark.has_no_hash());
157 EXPECT_FALSE(mark.is_marked());
158 EXPECT_TRUE(mark.decode_pointer() == nullptr);
159
160 assert_copy_set_hash(mark);
161 assert_type(mark);
162 }
163
164 static void assert_inline_type(markWord mark) {
165 EXPECT_FALSE(mark.is_flat_array());
166 EXPECT_TRUE(mark.is_inline_type());
167 EXPECT_FALSE(mark.is_null_free_array());
168 }
169
170 TEST_VM(markWord, inline_type_prototype) {
171 markWord mark = markWord::inline_type_prototype();
172 assert_unlocked_state(mark);
173 EXPECT_FALSE(mark.is_neutral());
174
175 assert_inline_type(mark);
176 EXPECT_FALSE(mark.is_larval_state());
177
178 EXPECT_TRUE(mark.has_no_hash());
179 EXPECT_FALSE(mark.is_marked());
180 EXPECT_TRUE(mark.decode_pointer() == nullptr);
181
182 markWord larval = mark.enter_larval_state();
183 EXPECT_TRUE(larval.is_larval_state());
184 assert_inline_type(larval);
185 mark = larval.exit_larval_state();
186 EXPECT_FALSE(mark.is_larval_state());
187 assert_inline_type(mark);
188
189 EXPECT_TRUE(mark.has_no_hash());
190 EXPECT_FALSE(mark.is_marked());
191 EXPECT_TRUE(mark.decode_pointer() == nullptr);
192 }
193
194 #if _LP64
195
196 static void assert_flat_array_type(markWord mark) {
197 EXPECT_TRUE(mark.is_flat_array());
198 EXPECT_FALSE(mark.is_inline_type());
199 EXPECT_FALSE(mark.is_larval_state());
200 }
201
202 TEST_VM(markWord, null_free_flat_array_prototype) {
203 markWord mark = markWord::flat_array_prototype(LayoutKind::NON_ATOMIC_FLAT);
204 assert_unlocked_state(mark);
205 EXPECT_TRUE(mark.is_neutral());
206
207 assert_flat_array_type(mark);
208 EXPECT_TRUE(mark.is_null_free_array());
209
210 EXPECT_TRUE(mark.has_no_hash());
211 EXPECT_FALSE(mark.is_marked());
212 EXPECT_TRUE(mark.decode_pointer() == nullptr);
213
214 assert_copy_set_hash(mark);
215 assert_flat_array_type(mark);
216 EXPECT_TRUE(mark.is_null_free_array());
217 }
218
219 TEST_VM(markWord, nullable_flat_array_prototype) {
220 markWord mark = markWord::flat_array_prototype(LayoutKind::NULLABLE_ATOMIC_FLAT);
221 assert_unlocked_state(mark);
222 EXPECT_TRUE(mark.is_neutral());
223
224 assert_flat_array_type(mark);
225 EXPECT_FALSE(mark.is_null_free_array());
226
227 EXPECT_TRUE(mark.has_no_hash());
228 EXPECT_FALSE(mark.is_marked());
229 EXPECT_TRUE(mark.decode_pointer() == nullptr);
230
231 assert_copy_set_hash(mark);
232 assert_flat_array_type(mark);
233 EXPECT_FALSE(mark.is_null_free_array());
234 }
235
236 static void assert_null_free_array_type(markWord mark) {
237 EXPECT_FALSE(mark.is_flat_array());
238 EXPECT_FALSE(mark.is_inline_type());
239 EXPECT_FALSE(mark.is_larval_state());
240 EXPECT_TRUE(mark.is_null_free_array());
241 }
242
243 TEST_VM(markWord, null_free_array_prototype) {
244 markWord mark = markWord::null_free_array_prototype();
245 assert_unlocked_state(mark);
246 EXPECT_TRUE(mark.is_neutral());
247
248 assert_null_free_array_type(mark);
249
250 EXPECT_TRUE(mark.has_no_hash());
251 EXPECT_FALSE(mark.is_marked());
252 EXPECT_TRUE(mark.decode_pointer() == nullptr);
253
254 assert_copy_set_hash(mark);
255 assert_null_free_array_type(mark);
256 }
257 #endif // _LP64
258
259 #endif // PRODUCT
|