blob: 9191c0296a651a2139740bb0ece2a6d31c3a45f4 [file] [log] [blame]
Jim Cownie5e8470a2013-09-27 10:38:44 +00001/*
Jonathan Peytonde4749b2016-12-14 23:01:24 +00002 * z_Windows_NT-586_util.cpp -- platform specific routines.
Jim Cownie5e8470a2013-09-27 10:38:44 +00003 */
4
Jim Cownie5e8470a2013-09-27 10:38:44 +00005//===----------------------------------------------------------------------===//
6//
7// The LLVM Compiler Infrastructure
8//
9// This file is dual licensed under the MIT and the University of Illinois Open
10// Source Licenses. See LICENSE.txt for details.
11//
12//===----------------------------------------------------------------------===//
13
Jim Cownie5e8470a2013-09-27 10:38:44 +000014#include "kmp.h"
15
16#if (KMP_ARCH_X86 || KMP_ARCH_X86_64)
17/* Only 32-bit "add-exchange" instruction on IA-32 architecture causes us to
Jonathan Peyton30419822017-05-12 18:01:32 +000018 use compare_and_store for these routines */
Jim Cownie5e8470a2013-09-27 10:38:44 +000019
Jonathan Peyton30419822017-05-12 18:01:32 +000020kmp_int8 __kmp_test_then_or8(volatile kmp_int8 *p, kmp_int8 d) {
21 kmp_int8 old_value, new_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000022
Jonathan Peyton30419822017-05-12 18:01:32 +000023 old_value = TCR_1(*p);
24 new_value = old_value | d;
25
26 while (!__kmp_compare_and_store8(p, old_value, new_value)) {
27 KMP_CPU_PAUSE();
28 old_value = TCR_1(*p);
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000029 new_value = old_value | d;
Jonathan Peyton30419822017-05-12 18:01:32 +000030 }
31 return old_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000032}
33
Jonathan Peyton30419822017-05-12 18:01:32 +000034kmp_int8 __kmp_test_then_and8(volatile kmp_int8 *p, kmp_int8 d) {
35 kmp_int8 old_value, new_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000036
Jonathan Peyton30419822017-05-12 18:01:32 +000037 old_value = TCR_1(*p);
38 new_value = old_value & d;
39
40 while (!__kmp_compare_and_store8(p, old_value, new_value)) {
41 KMP_CPU_PAUSE();
42 old_value = TCR_1(*p);
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000043 new_value = old_value & d;
Jonathan Peyton30419822017-05-12 18:01:32 +000044 }
45 return old_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000046}
47
Andrey Churbanov5ba90c72017-07-17 09:03:14 +000048kmp_uint32 __kmp_test_then_or32(volatile kmp_uint32 *p, kmp_uint32 d) {
49 kmp_uint32 old_value, new_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +000050
Jonathan Peyton30419822017-05-12 18:01:32 +000051 old_value = TCR_4(*p);
52 new_value = old_value | d;
53
Andrey Churbanov5ba90c72017-07-17 09:03:14 +000054 while (!__kmp_compare_and_store32((volatile kmp_int32 *)p, old_value,
55 new_value)) {
Jonathan Peyton30419822017-05-12 18:01:32 +000056 KMP_CPU_PAUSE();
57 old_value = TCR_4(*p);
Jim Cownie5e8470a2013-09-27 10:38:44 +000058 new_value = old_value | d;
Jonathan Peyton30419822017-05-12 18:01:32 +000059 }
60 return old_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +000061}
62
Andrey Churbanov5ba90c72017-07-17 09:03:14 +000063kmp_uint32 __kmp_test_then_and32(volatile kmp_uint32 *p, kmp_uint32 d) {
64 kmp_uint32 old_value, new_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +000065
Jonathan Peyton30419822017-05-12 18:01:32 +000066 old_value = TCR_4(*p);
67 new_value = old_value & d;
68
Andrey Churbanov5ba90c72017-07-17 09:03:14 +000069 while (!__kmp_compare_and_store32((volatile kmp_int32 *)p, old_value,
70 new_value)) {
Jonathan Peyton30419822017-05-12 18:01:32 +000071 KMP_CPU_PAUSE();
72 old_value = TCR_4(*p);
Jim Cownie5e8470a2013-09-27 10:38:44 +000073 new_value = old_value & d;
Jonathan Peyton30419822017-05-12 18:01:32 +000074 }
75 return old_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +000076}
77
Jonathan Peyton30419822017-05-12 18:01:32 +000078kmp_int8 __kmp_test_then_add8(volatile kmp_int8 *p, kmp_int8 d) {
79 kmp_int64 old_value, new_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000080
Jonathan Peyton30419822017-05-12 18:01:32 +000081 old_value = TCR_1(*p);
82 new_value = old_value + d;
83 while (!__kmp_compare_and_store8(p, old_value, new_value)) {
84 KMP_CPU_PAUSE();
85 old_value = TCR_1(*p);
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000086 new_value = old_value + d;
Jonathan Peyton30419822017-05-12 18:01:32 +000087 }
88 return old_value;
Andrey Churbanov7b2ab712015-03-10 09:03:42 +000089}
90
Jim Cownie5e8470a2013-09-27 10:38:44 +000091#if KMP_ARCH_X86
Jonathan Peyton30419822017-05-12 18:01:32 +000092kmp_int64 __kmp_test_then_add64(volatile kmp_int64 *p, kmp_int64 d) {
93 kmp_int64 old_value, new_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +000094
Jonathan Peyton30419822017-05-12 18:01:32 +000095 old_value = TCR_8(*p);
96 new_value = old_value + d;
97 while (!__kmp_compare_and_store64(p, old_value, new_value)) {
98 KMP_CPU_PAUSE();
99 old_value = TCR_8(*p);
Jim Cownie5e8470a2013-09-27 10:38:44 +0000100 new_value = old_value + d;
Jonathan Peyton30419822017-05-12 18:01:32 +0000101 }
102 return old_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +0000103}
104#endif /* KMP_ARCH_X86 */
105
Andrey Churbanov5ba90c72017-07-17 09:03:14 +0000106kmp_uint64 __kmp_test_then_or64(volatile kmp_uint64 *p, kmp_uint64 d) {
107 kmp_uint64 old_value, new_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +0000108
Jonathan Peyton30419822017-05-12 18:01:32 +0000109 old_value = TCR_8(*p);
110 new_value = old_value | d;
Andrey Churbanov5ba90c72017-07-17 09:03:14 +0000111 while (!__kmp_compare_and_store64((volatile kmp_int64 *)p, old_value,
112 new_value)) {
Jonathan Peyton30419822017-05-12 18:01:32 +0000113 KMP_CPU_PAUSE();
114 old_value = TCR_8(*p);
Jim Cownie5e8470a2013-09-27 10:38:44 +0000115 new_value = old_value | d;
Jonathan Peyton30419822017-05-12 18:01:32 +0000116 }
Jim Cownie5e8470a2013-09-27 10:38:44 +0000117
Jonathan Peyton30419822017-05-12 18:01:32 +0000118 return old_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +0000119}
120
Andrey Churbanov5ba90c72017-07-17 09:03:14 +0000121kmp_uint64 __kmp_test_then_and64(volatile kmp_uint64 *p, kmp_uint64 d) {
122 kmp_uint64 old_value, new_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +0000123
Jonathan Peyton30419822017-05-12 18:01:32 +0000124 old_value = TCR_8(*p);
125 new_value = old_value & d;
Andrey Churbanov5ba90c72017-07-17 09:03:14 +0000126 while (!__kmp_compare_and_store64((volatile kmp_int64 *)p, old_value,
127 new_value)) {
Jonathan Peyton30419822017-05-12 18:01:32 +0000128 KMP_CPU_PAUSE();
129 old_value = TCR_8(*p);
Jim Cownie5e8470a2013-09-27 10:38:44 +0000130 new_value = old_value & d;
Jonathan Peyton30419822017-05-12 18:01:32 +0000131 }
Jim Cownie5e8470a2013-09-27 10:38:44 +0000132
Jonathan Peyton30419822017-05-12 18:01:32 +0000133 return old_value;
Jim Cownie5e8470a2013-09-27 10:38:44 +0000134}
135
136#endif /* KMP_ARCH_X86 || KMP_ARCH_X86_64 */