This source file includes following definitions.
- lock_simh
- unlock_simh
- lock_libuv
- unlock_libuv
- test_libuv_lock
- get_rmw_lock
- lock_rmw
- lock_mem_rd
- lock_mem_wr
- unlock_rmw
- unlock_mem
- unlock_mem_force
- lock_ptr
- unlock_ptr
- lock_scu
- unlock_scu
- lock_iom
- unlock_iom
- lock_tst
- unlock_tst
- test_tst_lock
- pthread_create_with_cpu_policy
- createCPUThread
- stopCPUThread
- cpuRunningWait
- sleepCPU
- wakeCPU
- createIOMThread
- iomInterruptWait
- iomInterruptDone
- iomDoneWait
- setIOMInterrupt
- iomRdyWait
- createChnThread
- chnConnectWait
- chnConnectDone
- setChnConnect
- chnRdyWait
- initThreadz
- setSignals
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 #include <unistd.h>
22 #include <stdlib.h>
23 #include <signal.h>
24
25 #include "dps8.h"
26 #include "dps8_sys.h"
27 #include "dps8_cpu.h"
28 #include "dps8_faults.h"
29 #include "dps8_iom.h"
30 #include "dps8_utils.h"
31
32 #include "threadz.h"
33 #if defined(__FreeBSD__) || defined(__OpenBSD__)
34 # include <pthread_np.h>
35 #endif
36
37
38
39
40
41
42
43 #if defined(IO_ASYNC_PAYLOAD_CHAN_THREAD)
44 pthread_cond_t iomCond;
45 pthread_mutex_t iom_start_lock;
46 #endif
47
48 #if !defined(QUIET_UNUSED)
49 void lock_simh (void)
50 {
51 pthread_mutex_lock (& simh_lock);
52 }
53
54 void unlock_simh (void)
55 {
56 pthread_mutex_unlock (& simh_lock);
57 }
58 #endif
59
60
61
62 static pthread_mutex_t libuv_lock;
63
64 void lock_libuv (void)
65 {
66 pthread_mutex_lock (& libuv_lock);
67 }
68
69 void unlock_libuv (void)
70 {
71 pthread_mutex_unlock (& libuv_lock);
72 }
73
74 #if defined(TESTING)
75 bool test_libuv_lock (void)
76 {
77
78 int rc;
79 rc = pthread_mutex_trylock (& libuv_lock);
80 if (rc)
81 {
82
83 return true;
84 }
85
86 rc = pthread_mutex_unlock (& libuv_lock);
87 if (rc)
88 sim_printf ("test_libuv_lock pthread_mutex_lock libuv_lock %d\n", rc);
89 return false;
90 }
91 #endif
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112 #if !defined(LOCKLESS)
113 pthread_rwlock_t mem_lock = PTHREAD_RWLOCK_INITIALIZER;
114 static __thread bool have_mem_lock = false;
115 static __thread bool have_rmw_lock = false;
116
117 bool get_rmw_lock (void)
118 {
119 return have_rmw_lock;
120 }
121
122 void lock_rmw (void)
123 {
124 if (have_rmw_lock)
125 {
126 sim_warn ("%s: Already have RMW lock\n", __func__);
127 return;
128 }
129 if (have_mem_lock)
130 {
131 sim_warn ("%s: Already have memory lock\n", __func__);
132 return;
133 }
134 int rc= pthread_rwlock_wrlock (& mem_lock);
135 if (rc)
136 sim_printf ("%s pthread_rwlock_rdlock mem_lock %d\n", __func__, rc);
137 have_mem_lock = true;
138 have_rmw_lock = true;
139 }
140
141 void lock_mem_rd (void)
142 {
143
144 if (have_rmw_lock)
145 return;
146
147 if (have_mem_lock)
148 {
149 sim_warn ("%s: Already have memory lock\n", __func__);
150 return;
151 }
152 int rc= pthread_rwlock_rdlock (& mem_lock);
153 if (rc)
154 sim_printf ("%s pthread_rwlock_rdlock mem_lock %d\n", __func__, rc);
155 have_mem_lock = true;
156 }
157
158 void lock_mem_wr (void)
159 {
160
161 if (have_rmw_lock)
162 return;
163
164 if (have_mem_lock)
165 {
166 sim_warn ("%s: Already have memory lock\n", __func__);
167 return;
168 }
169 int rc= pthread_rwlock_wrlock (& mem_lock);
170 if (rc)
171 sim_printf ("%s pthread_rwlock_wrlock mem_lock %d\n", __func__, rc);
172 have_mem_lock = true;
173 }
174
175 void unlock_rmw (void)
176 {
177 if (! have_mem_lock)
178 {
179 sim_warn ("%s: Don't have memory lock\n", __func__);
180 return;
181 }
182 if (! have_rmw_lock)
183 {
184 sim_warn ("%s: Don't have RMW lock\n", __func__);
185 return;
186 }
187
188 int rc = pthread_rwlock_unlock (& mem_lock);
189 if (rc)
190 sim_printf ("%s pthread_rwlock_ublock mem_lock %d\n", __func__, rc);
191 have_mem_lock = false;
192 have_rmw_lock = false;
193 }
194
195 void unlock_mem (void)
196 {
197 if (have_rmw_lock)
198 return;
199 if (! have_mem_lock)
200 {
201 sim_warn ("%s: Don't have memory lock\n", __func__);
202 return;
203 }
204
205 int rc = pthread_rwlock_unlock (& mem_lock);
206 if (rc)
207 sim_printf ("%s pthread_rwlock_ublock mem_lock %d\n", __func__, rc);
208 have_mem_lock = false;
209 }
210
211 void unlock_mem_force (void)
212 {
213 if (have_mem_lock)
214 {
215 int rc = pthread_rwlock_unlock (& mem_lock);
216 if (rc)
217 sim_printf ("%s pthread_rwlock_unlock mem_lock %d\n", __func__, rc);
218 }
219 have_mem_lock = false;
220 have_rmw_lock = false;
221 }
222 #endif
223
224
225
226 void lock_ptr (pthread_mutex_t * lock)
227 {
228 int rc;
229 rc = pthread_mutex_lock (lock);
230 if (rc)
231 sim_printf ("lock_ptr %d\n", rc);
232 }
233
234 void unlock_ptr (pthread_mutex_t * lock)
235 {
236
237 int rc;
238 rc = pthread_mutex_unlock (lock);
239 if (rc)
240 sim_printf ("unlock_ptr %d\n", rc);
241 }
242
243
244
245 static pthread_mutex_t scu_lock;
246
247 void lock_scu (void)
248 {
249
250 int rc;
251 rc = pthread_mutex_lock (& scu_lock);
252 if (rc)
253 sim_printf ("lock_scu pthread_spin_lock scu %d\n", rc);
254 }
255
256 void unlock_scu (void)
257 {
258
259 int rc;
260 rc = pthread_mutex_unlock (& scu_lock);
261 if (rc)
262 sim_printf ("unlock_scu pthread_spin_lock scu %d\n", rc);
263 }
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286 static pthread_mutex_t iom_lock;
287
288 void lock_iom (void)
289 {
290 int rc;
291 rc = pthread_mutex_lock (& iom_lock);
292 if (rc)
293 sim_printf ("%s pthread_spin_lock iom %d\n", __func__, rc);
294 }
295
296 void unlock_iom (void)
297 {
298 int rc;
299 rc = pthread_mutex_unlock (& iom_lock);
300 if (rc)
301 sim_printf ("%s pthread_spin_lock iom %d\n", __func__, rc);
302 }
303
304
305
306 #if defined(TESTING)
307 static pthread_mutex_t tst_lock = PTHREAD_MUTEX_INITIALIZER;
308
309 void lock_tst (void)
310 {
311
312 int rc;
313 rc = pthread_mutex_lock (& tst_lock);
314 if (rc)
315 sim_printf ("lock_tst pthread_mutex_lock tst_lock %d\n", rc);
316 }
317
318 void unlock_tst (void)
319 {
320
321 int rc;
322 rc = pthread_mutex_unlock (& tst_lock);
323 if (rc)
324 sim_printf ("unlock_tst pthread_mutex_lock tst_lock %d\n", rc);
325 }
326
327
328
329 bool test_tst_lock (void)
330 {
331
332 int rc;
333 rc = pthread_mutex_trylock (& tst_lock);
334 if (rc)
335 {
336
337 return true;
338 }
339
340 rc = pthread_mutex_unlock (& tst_lock);
341 if (rc)
342 sim_printf ("test_tst_lock pthread_mutex_lock tst_lock %d\n", rc);
343 return false;
344 }
345 #endif
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373 struct cpuThreadz_t cpuThreadz [N_CPU_UNITS_MAX];
374
375
376
377 #if defined(__APPLE__)
378 int pthread_create_with_cpu_policy(
379 pthread_t *restrict thread,
380 int policy_group,
381 const pthread_attr_t *restrict attr,
382 void *(*start_routine)(void *), void *restrict arg)
383 {
384 # if defined(TESTING)
385 sim_msg ("\rAffinity policy group %d requested for thread.\r\n", policy_group);
386 # endif
387 thread_affinity_policy_data_t policy_data = { policy_group };
388 int rv = pthread_create_suspended_np(thread, attr, start_routine, arg);
389 mach_port_t mach_thread = pthread_mach_thread_np(*thread);
390 if (rv != 0)
391 {
392 return rv;
393 }
394 thread_policy_set(
395 mach_thread,
396 THREAD_AFFINITY_POLICY,
397 (thread_policy_t)&policy_data,
398 THREAD_AFFINITY_POLICY_COUNT);
399 thread_resume(mach_thread);
400 return 0;
401 }
402 #endif
403
404
405
406 void createCPUThread (uint cpuNum)
407 {
408 int rc;
409 struct cpuThreadz_t * p = & cpuThreadz[cpuNum];
410 if (p->run)
411 return;
412 cpu_reset_unit_idx (cpuNum, false);
413 p->cpuThreadArg = (int) cpuNum;
414
415 rc = pthread_mutex_init (& p->runLock, NULL);
416 if (rc)
417 sim_printf ("createCPUThread pthread_mutex_init runLock %d\n", rc);
418 rc = pthread_cond_init (& p->runCond, NULL);
419 if (rc)
420 sim_printf ("createCPUThread pthread_cond_init runCond %d\n", rc);
421
422 p->run = true;
423
424
425 #if defined(USE_MONOTONIC)
426 # if defined(__APPLE__) || !defined(CLOCK_MONOTONIC)
427 p->sleepClock = CLOCK_REALTIME;
428 rc = pthread_cond_init (& p->sleepCond, NULL);
429 # else
430 rc = pthread_condattr_init (& p->sleepCondAttr);
431 if (rc)
432 sim_printf ("createCPUThread pthread_condattr_init sleepCond %d\n", rc);
433
434 rc = pthread_condattr_setclock (& p->sleepCondAttr, CLOCK_MONOTONIC);
435 if (rc) {
436
437 p->sleepClock = CLOCK_REALTIME;
438 } else {
439 p->sleepClock = CLOCK_MONOTONIC;
440 }
441 # endif
442 rc = pthread_cond_init (& p->sleepCond, & p->sleepCondAttr);
443 #else
444 rc = pthread_cond_init (& p->sleepCond, NULL);
445 #endif
446 if (rc)
447 sim_printf ("createCPUThread pthread_cond_init sleepCond %d\n", rc);
448
449 #if defined(__APPLE__)
450 rc = pthread_create_with_cpu_policy(
451 & p->cpuThread,
452 cpuNum,
453 NULL,
454 cpu_thread_main,
455 & p->cpuThreadArg);
456 #else
457 rc = pthread_create(
458 & p->cpuThread,
459 NULL,
460 cpu_thread_main,
461 & p->cpuThreadArg);
462 #endif
463 if (rc)
464 sim_printf ("createCPUThread pthread_create %d\n", rc);
465
466 #if defined(AFFINITY)
467 if (cpus[cpuNum].set_affinity)
468 {
469 cpu_set_t cpuset;
470 CPU_ZERO (& cpuset);
471 CPU_SET (cpus[cpuNum].affinity, & cpuset);
472 int s = pthread_setaffinity_np (p->cpuThread, sizeof (cpu_set_t), & cpuset);
473 if (s)
474 sim_printf ("pthread_setaffinity_np %u on CPU %u returned %d\n",
475 cpus[cpuNum].affinity, cpuNum, s);
476 }
477 #endif
478
479 while (! cpus[cpuNum].up) {
480 sim_usleep (1);
481 }
482 }
483
484 void stopCPUThread(void)
485 {
486 struct cpuThreadz_t * p = & cpuThreadz[current_running_cpu_idx];
487 p->run = false;
488 pthread_exit(NULL);
489 }
490
491
492
493 #if defined(THREADZ)
494 void cpuRunningWait (void)
495 {
496 int rc;
497 struct cpuThreadz_t * p = & cpuThreadz[current_running_cpu_idx];
498 if (p->run)
499 return;
500 rc = pthread_mutex_lock (& p->runLock);
501 if (rc)
502 sim_printf ("cpuRunningWait pthread_mutex_lock %d\n", rc);
503 while (! p->run)
504 {
505 rc = pthread_cond_wait (& p->runCond, & p->runLock);
506 if (rc)
507 sim_printf ("cpuRunningWait pthread_cond_wait %d\n", rc);
508 }
509 rc = pthread_mutex_unlock (& p->runLock);
510 if (rc)
511 sim_printf ("cpuRunningWait pthread_mutex_unlock %d\n", rc);
512 }
513 #endif
514
515
516
517 unsigned long sleepCPU (unsigned long usec) {
518 int rc;
519 struct cpuThreadz_t * p = & cpuThreadz[current_running_cpu_idx];
520 struct timespec startTime, absTime;
521
522 #if defined(USE_MONOTONIC)
523 clock_gettime (p->sleepClock, & startTime);
524 #else
525 clock_gettime (CLOCK_REALTIME, & startTime);
526 #endif
527 absTime = startTime;
528 int64_t nsec = ((int64_t) usec) * 1000L + (int64_t)startTime.tv_nsec;
529 absTime.tv_nsec = nsec % 1000000000L;
530 absTime.tv_sec += nsec / 1000000000L;
531
532 rc = pthread_cond_timedwait (& p->sleepCond, & scu_lock, & absTime);
533
534 if (rc == ETIMEDOUT) {
535 return 0;
536 }
537
538 if (rc) {
539 cpu_state_t * cpup = _cpup;
540 sim_printf ("sleepCPU pthread_cond_timedwait rc %ld usec %ld TR %lu CPU %lu\n",
541 (long) rc, (long) usec, (unsigned long) cpu.rTR,
542 (unsigned long) current_running_cpu_idx);
543 }
544
545 struct timespec newTime;
546 struct timespec delta;
547 #if defined(USE_MONOTONIC)
548 clock_gettime (p->sleepClock, & newTime);
549 #else
550 clock_gettime (CLOCK_REALTIME, & newTime);
551 #endif
552 timespec_diff (& absTime, & newTime, & delta);
553
554 if (delta.tv_nsec < 0)
555 return 0;
556 return (unsigned long) delta.tv_nsec / 1000L;
557 }
558
559
560
561 void wakeCPU (uint cpuNum)
562 {
563 int rc;
564 struct cpuThreadz_t * p = & cpuThreadz[cpuNum];
565
566 rc = pthread_cond_signal (& p->sleepCond);
567 if (rc)
568 sim_printf ("wakeCPU pthread_cond_signal %d\n", rc);
569 }
570
571 #if defined(IO_THREADZ)
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595 struct iomThreadz_t iomThreadz [N_IOM_UNITS_MAX];
596
597
598
599 void createIOMThread (uint iomNum)
600 {
601 int rc;
602 struct iomThreadz_t * p = & iomThreadz[iomNum];
603 # if defined(tdbg)
604 p->inCnt = 0;
605 p->outCnt = 0;
606 # endif
607 p->iomThreadArg = (int) iomNum;
608
609 p->ready = false;
610
611 p->intr = false;
612 rc = pthread_mutex_init (& p->intrLock, NULL);
613 if (rc)
614 sim_printf ("createIOMThread pthread_mutex_init intrLock %d\n", rc);
615 rc = pthread_cond_init (& p->intrCond, NULL);
616 if (rc)
617 sim_printf ("createIOMThread pthread_cond_init intrCond %d\n", rc);
618
619 # if defined(__APPLE__)
620 rc = pthread_create_with_cpu_policy(
621 & p->iomThread,
622 iomNum,
623 NULL,
624 iom_thread_main,
625 & p->iomThreadArg);
626 # else
627 rc = pthread_create(
628 & p->iomThread,
629 NULL,
630 iom_thread_main,
631 & p->iomThreadArg);
632 # endif
633 if (rc)
634 sim_printf ("createIOMThread pthread_create %d\n", rc);
635
636 char nm [17];
637 (void)sprintf (nm, "IOM %c", 'a' + iomNum);
638 # if defined(__FreeBSD__) || defined(__OpenBSD__)
639 pthread_setname_np (p->iomThread, nm);
640 # else
641 pthread_set_name_np (p->iomThread, nm);
642 # endif
643 }
644
645
646
647 void iomInterruptWait (void)
648 {
649 int rc;
650 struct iomThreadz_t * p = & iomThreadz[this_iom_idx];
651 rc = pthread_mutex_lock (& p->intrLock);
652 if (rc)
653 sim_printf ("iomInterruptWait pthread_mutex_lock %d\n", rc);
654 p -> ready = true;
655 while (! p->intr)
656 {
657 rc = pthread_cond_wait (& p->intrCond, & p->intrLock);
658 if (rc)
659 sim_printf ("iomInterruptWait pthread_cond_wait %d\n", rc);
660 }
661 # if defined(tdbg)
662 p->outCnt++;
663 if (p->inCnt != p->outCnt)
664 sim_printf ("iom thread %d in %d out %d\n", this_iom_idx,
665 p->inCnt, p->outCnt);
666 # endif
667 }
668
669
670
671 void iomInterruptDone (void)
672 {
673 int rc;
674 struct iomThreadz_t * p = & iomThreadz[this_iom_idx];
675 p->intr = false;
676 rc = pthread_cond_signal (& p->intrCond);
677 if (rc)
678 sim_printf ("iomInterruptDone pthread_cond_signal %d\n", rc);
679 rc = pthread_mutex_unlock (& p->intrLock);
680 if (rc)
681 sim_printf ("iomInterruptDone pthread_mutex_unlock %d\n", rc);
682 }
683
684
685
686 void iomDoneWait (uint iomNum)
687 {
688 int rc;
689 struct iomThreadz_t * p = & iomThreadz[iomNum];
690 rc = pthread_mutex_lock (& p->intrLock);
691 if (rc)
692 sim_printf ("iomDoneWait pthread_mutex_lock %d\n", rc);
693 while (p->intr)
694 {
695 rc = pthread_cond_wait (& p->intrCond, & p->intrLock);
696 if (rc)
697 sim_printf ("iomDoneWait pthread_cond_wait %d\n", rc);
698 }
699 rc = pthread_mutex_unlock (& p->intrLock);
700 if (rc)
701 sim_printf ("iomDoneWait pthread_mutex_unlock %d\n", rc);
702 }
703
704
705
706 void setIOMInterrupt (uint iomNum)
707 {
708 int rc;
709 struct iomThreadz_t * p = & iomThreadz[iomNum];
710 rc = pthread_mutex_lock (& p->intrLock);
711 if (rc)
712 sim_printf ("setIOMInterrupt pthread_mutex_lock %d\n", rc);
713 while (p->intr)
714 {
715 rc = pthread_cond_wait(&p->intrCond, &p->intrLock);
716 if (rc)
717 sim_printf ("setIOMInterrupt pthread_cond_wait intrLock %d\n", rc);
718 }
719 # if defined(tdbg)
720 p->inCnt++;
721 # endif
722 p->intr = true;
723 rc = pthread_cond_signal (& p->intrCond);
724 if (rc)
725 sim_printf ("setIOMInterrupt pthread_cond_signal %d\n", rc);
726 rc = pthread_mutex_unlock (& p->intrLock);
727 if (rc)
728 sim_printf ("setIOMInterrupt pthread_mutex_unlock %d\n", rc);
729 }
730
731
732
733 void iomRdyWait (uint iomNum)
734 {
735 struct iomThreadz_t * p = & iomThreadz[iomNum];
736 while (! p -> ready)
737 sim_usleep (10000);
738 }
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762 struct chnThreadz_t chnThreadz [N_IOM_UNITS_MAX] [MAX_CHANNELS];
763
764
765
766 void createChnThread (uint iomNum, uint chnNum, const char * devTypeStr)
767 {
768 int rc;
769 struct chnThreadz_t * p = & chnThreadz[iomNum][chnNum];
770 p->chnThreadArg = (int) (chnNum + iomNum * MAX_CHANNELS);
771
772 # if defined(tdbg)
773 p->inCnt = 0;
774 p->outCnt = 0;
775 # endif
776 p->ready = false;
777
778 p->connect = false;
779 rc = pthread_mutex_init (& p->connectLock, NULL);
780 if (rc)
781 sim_printf ("createChnThread pthread_mutex_init connectLock %d\n", rc);
782 rc = pthread_cond_init (& p->connectCond, NULL);
783 if (rc)
784 sim_printf ("createChnThread pthread_cond_init connectCond %d\n", rc);
785
786 # if defined(__APPLE__)
787 rc = pthread_create_with_cpu_policy(
788 & p->chnThread,
789 iomNum
790 NULL,
791 chan_thread_main,
792 & p->chnThreadArg);
793 # else
794 rc = pthread_create(
795 & p->chnThread,
796 NULL,
797 chan_thread_main,
798 & p->chnThreadArg);
799 # endif
800 if (rc)
801 sim_printf ("createChnThread pthread_create %d\n", rc);
802
803 char nm [17];
804 (void)sprintf (nm, "chn %c/%u %s", 'a' + iomNum, chnNum, devTypeStr);
805 # if defined(__FreeBSD__) || defined(__OpenBSD__)
806 pthread_setname_np (p->chnThread, nm);
807 # else
808 pthread_set_name_np (p->chnThread, nm);
809 # endif
810 }
811
812
813
814 void chnConnectWait (void)
815 {
816 int rc;
817 struct chnThreadz_t * p = & chnThreadz[this_iom_idx][this_chan_num];
818
819 rc = pthread_mutex_lock (& p->connectLock);
820 if (rc)
821 sim_printf ("chnConnectWait pthread_mutex_lock %d\n", rc);
822 p -> ready = true;
823 while (! p->connect)
824 {
825 rc = pthread_cond_wait (& p->connectCond, & p->connectLock);
826 if (rc)
827 sim_printf ("chnConnectWait pthread_cond_wait %d\n", rc);
828 }
829 # if defined(tdbg)
830 p->outCnt++;
831 if (p->inCnt != p->outCnt)
832 sim_printf ("chn thread %d in %d out %d\n", this_chan_num,
833 p->inCnt, p->outCnt);
834 # endif
835 }
836
837
838
839 void chnConnectDone (void)
840 {
841 int rc;
842 struct chnThreadz_t * p = & chnThreadz[this_iom_idx][this_chan_num];
843 p->connect = false;
844 rc = pthread_cond_signal (& p->connectCond);
845 if (rc)
846 sim_printf ("chnInterruptDone pthread_cond_signal %d\n", rc);
847 rc = pthread_mutex_unlock (& p->connectLock);
848 if (rc)
849 sim_printf ("chnConnectDone pthread_mutex_unlock %d\n", rc);
850 }
851
852
853
854 void setChnConnect (uint iomNum, uint chnNum)
855 {
856 int rc;
857 struct chnThreadz_t * p = & chnThreadz[iomNum][chnNum];
858 rc = pthread_mutex_lock (& p->connectLock);
859 if (rc)
860 sim_printf ("setChnConnect pthread_mutex_lock %d\n", rc);
861 while (p->connect)
862 {
863 rc = pthread_cond_wait(&p->connectCond, &p->connectLock);
864 if (rc)
865 sim_printf ("setChnInterrupt pthread_cond_wait connectLock %d\n", rc);
866 }
867 # if defined(tdbg)
868 p->inCnt++;
869 # endif
870 p->connect = true;
871 rc = pthread_cond_signal (& p->connectCond);
872 if (rc)
873 sim_printf ("setChnConnect pthread_cond_signal %d\n", rc);
874 rc = pthread_mutex_unlock (& p->connectLock);
875 if (rc)
876 sim_printf ("setChnConnect pthread_mutex_unlock %d\n", rc);
877 }
878
879
880
881 void chnRdyWait (uint iomNum, uint chnNum)
882 {
883 struct chnThreadz_t * p = & chnThreadz[iomNum][chnNum];
884 while (! p -> ready)
885 sim_usleep (10000);
886 }
887 #endif
888
889 void initThreadz (void)
890 {
891 #if defined(IO_THREADZ)
892
893 (void)memset (chnThreadz, 0, sizeof (chnThreadz));
894 #endif
895
896 #if !defined(LOCKLESS)
897
898 have_mem_lock = false;
899 have_rmw_lock = false;
900 #endif
901 #if defined(__FreeBSD__) || defined(__OpenBSD__)
902 pthread_mutexattr_t scu_attr;
903 pthread_mutexattr_init(&scu_attr);
904 # if !defined(__OpenBSD__)
905 pthread_mutexattr_settype(&scu_attr, PTHREAD_MUTEX_ADAPTIVE_NP);
906 # endif
907 pthread_mutex_init (& scu_lock, &scu_attr);
908 #else
909 pthread_mutex_init (& scu_lock, NULL);
910 #endif
911 pthread_mutexattr_t iom_attr;
912 pthread_mutexattr_init(& iom_attr);
913 pthread_mutexattr_settype(& iom_attr, PTHREAD_MUTEX_RECURSIVE);
914
915 pthread_mutex_init (& iom_lock, & iom_attr);
916
917 pthread_mutexattr_t libuv_attr;
918 pthread_mutexattr_init(& libuv_attr);
919 pthread_mutexattr_settype(& libuv_attr, PTHREAD_MUTEX_RECURSIVE);
920
921 pthread_mutex_init (& libuv_lock, & libuv_attr);
922
923 #if defined(IO_ASYNC_PAYLOAD_CHAN_THREAD)
924 pthread_cond_init (& iomCond, NULL);
925 pthread_mutex_init (& iom_start_lock, NULL);
926 #endif
927 }
928
929
930
931 void int_handler (int signal);
932
933 void setSignals (void)
934 {
935 #if !defined(__MINGW64__) && !defined(__MINGW32__)
936 struct sigaction act;
937 (void)memset (& act, 0, sizeof (act));
938 act.sa_handler = int_handler;
939 act.sa_flags = 0;
940 sigaction (SIGINT, & act, NULL);
941 sigaction (SIGTERM, & act, NULL);
942 #endif
943 }
944
945
946
947
948
949
950
951
952
953
954