Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitdd50f1a

Browse files
committed
Replace xlc __fetch_and_add() with inline asm.
PostgreSQL has been unusable when built with xlc 13 and newer, which areincompatible with our use of __fetch_and_add(). Back-patch to 9.5,which introduced pg_atomic_fetch_add_u32().Reviewed by Tom Lane.Discussion:https://postgr.es/m/20190831071157.GA3251746@rfd.leadboat.com
1 parentf380c51 commitdd50f1a

File tree

1 file changed

+35
-4
lines changed

1 file changed

+35
-4
lines changed

‎src/include/port/atomics/generic-xlc.h

Lines changed: 35 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -73,11 +73,27 @@ pg_atomic_compare_exchange_u32_impl(volatile pg_atomic_uint32 *ptr,
7373
staticinlineuint32
7474
pg_atomic_fetch_add_u32_impl(volatilepg_atomic_uint32*ptr,int32add_)
7575
{
76+
uint32_t;
77+
uint32res;
78+
7679
/*
77-
* __fetch_and_add() emits a leading "sync" and trailing "isync", thereby
78-
* providing sequential consistency. This is undocumented.
80+
* xlc has a no-longer-documented __fetch_and_add() intrinsic. In xlc
81+
* 12.01.0000.0000, it emits a leading "sync" and trailing "isync". In
82+
* xlc 13.01.0003.0004, it emits neither. Hence, using the intrinsic
83+
* would add redundant syncs on xlc 12.
7984
*/
80-
return__fetch_and_add((volatileint*)&ptr->value,add_);
85+
__asm__ __volatile__(
86+
"sync\n"
87+
"lwarx %1,0,%4\n"
88+
"add %0,%1,%3\n"
89+
"stwcx. %0,0,%4\n"
90+
"bne $-12\n"/* branch to lwarx */
91+
"isync\n"
92+
:"=&r"(_t),"=&r"(res),"+m"(ptr->value)
93+
:"r"(add_),"r"(&ptr->value)
94+
:"memory","cc");
95+
96+
returnres;
8197
}
8298

8399
#ifdefPG_HAVE_ATOMIC_U64_SUPPORT
@@ -103,7 +119,22 @@ pg_atomic_compare_exchange_u64_impl(volatile pg_atomic_uint64 *ptr,
103119
staticinlineuint64
104120
pg_atomic_fetch_add_u64_impl(volatilepg_atomic_uint64*ptr,int64add_)
105121
{
106-
return__fetch_and_addlp((volatilelong*)&ptr->value,add_);
122+
uint64_t;
123+
uint64res;
124+
125+
/* Like u32, but s/lwarx/ldarx/; s/stwcx/stdcx/ */
126+
__asm__ __volatile__(
127+
"sync\n"
128+
"ldarx %1,0,%4\n"
129+
"add %0,%1,%3\n"
130+
"stdcx. %0,0,%4\n"
131+
"bne $-12\n"/* branch to ldarx */
132+
"isync\n"
133+
:"=&r"(_t),"=&r"(res),"+m"(ptr->value)
134+
:"r"(add_),"r"(&ptr->value)
135+
:"memory","cc");
136+
137+
returnres;
107138
}
108139

109140
#endif/* PG_HAVE_ATOMIC_U64_SUPPORT */

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp