aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--share/man/man9/fetch.918
-rw-r--r--share/man/man9/store.914
-rw-r--r--sys/kern/kern_umtx.c72
-rw-r--r--sys/kern/subr_uio.c12
-rw-r--r--sys/powerpc/powerpc/copyinout.c28
-rw-r--r--sys/sys/systm.h26
6 files changed, 77 insertions, 93 deletions
diff --git a/share/man/man9/fetch.9 b/share/man/man9/fetch.9
index 7e13cbc51c45..1d46784ed310 100644
--- a/share/man/man9/fetch.9
+++ b/share/man/man9/fetch.9
@@ -34,7 +34,7 @@
.\"
.\" $FreeBSD$
.\"
-.Dd October 21, 2014
+.Dd October 29, 2014
.Dt FETCH 9
.Os
.Sh NAME
@@ -53,21 +53,21 @@
.In sys/types.h
.In sys/systm.h
.Ft int
-.Fn fubyte "const void *base"
+.Fn fubyte "volatile const void *base"
.Ft long
-.Fn fuword "const void *base"
+.Fn fuword "volatile const void *base"
.Ft int
-.Fn fuword16 "void *base"
+.Fn fuword16 "volatile const void *base"
.Ft int32_t
-.Fn fuword32 "const void *base"
+.Fn fuword32 "volatile const void *base"
.Ft int64_t
-.Fn fuword64 "const void *base"
+.Fn fuword64 "volatile const void *base"
.Ft long
-.Fn fueword "const void *base" "long *val"
+.Fn fueword "volatile const void *base" "long *val"
.Ft int32_t
-.Fn fueword32 "const void *base" "int32_t *val"
+.Fn fueword32 "volatile const void *base" "int32_t *val"
.Ft int64_t
-.Fn fueword64 "const void *base" "int64_t *val"
+.Fn fueword64 "volatile const void *base" "int64_t *val"
.In sys/resourcevar.h
.Ft int
.Fn fuswintr "void *base"
diff --git a/share/man/man9/store.9 b/share/man/man9/store.9
index d333eff03315..cc442f25f47c 100644
--- a/share/man/man9/store.9
+++ b/share/man/man9/store.9
@@ -34,7 +34,7 @@
.\"
.\" $FreeBSD$
.\"
-.Dd October 5, 2009
+.Dd October 29, 2014
.Dt STORE 9
.Os
.Sh NAME
@@ -48,15 +48,15 @@
.In sys/time.h
.In sys/systm.h
.Ft int
-.Fn subyte "void *base" "int byte"
+.Fn subyte "volatile void *base" "int byte"
.Ft int
-.Fn suword "void *base" "long word"
+.Fn suword "volatile void *base" "long word"
.Ft int
-.Fn suword16 "void *base" "int word"
+.Fn suword16 "volatile void *base" "int word"
.Ft int
-.Fn suword32 "void *base" "int32_t word"
+.Fn suword32 "volatile void *base" "int32_t word"
.Ft int
-.Fn suword64 "void *base" "int64_t word"
+.Fn suword64 "volatile void *base" "int64_t word"
.In sys/resourcevar.h
.Ft int
.Fn suswintr "void *base" "int word"
@@ -64,6 +64,8 @@
The
.Nm
functions are designed to copy small amounts of data to user-space.
+If write is successful, it is performed atomically.
+The data written must be naturally aligned.
.Pp
The
.Nm
diff --git a/sys/kern/kern_umtx.c b/sys/kern/kern_umtx.c
index 58e76bc90b64..33fdf71e5ebe 100644
--- a/sys/kern/kern_umtx.c
+++ b/sys/kern/kern_umtx.c
@@ -942,7 +942,7 @@ do_lock_normal(struct thread *td, struct umutex *m, uint32_t flags,
* can fault on any access.
*/
for (;;) {
- rv = fueword32(__DEVOLATILE(void *, &m->m_owner), &owner);
+ rv = fueword32(&m->m_owner, &owner);
if (rv == -1)
return (EFAULT);
if (mode == _UMUTEX_WAIT) {
@@ -1057,7 +1057,7 @@ do_unlock_normal(struct thread *td, struct umutex *m, uint32_t flags)
/*
* Make sure we own this mtx.
*/
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner), &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
return (EFAULT);
@@ -1115,7 +1115,7 @@ do_wake_umutex(struct thread *td, struct umutex *m)
int error;
int count;
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner), &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
return (EFAULT);
@@ -1192,8 +1192,7 @@ do_wake2_umutex(struct thread *td, struct umutex *m, uint32_t flags)
* any memory.
*/
if (count > 1) {
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner),
- &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
error = EFAULT;
while (error == 0 && (owner & UMUTEX_CONTESTED) == 0) {
@@ -1211,8 +1210,7 @@ do_wake2_umutex(struct thread *td, struct umutex *m, uint32_t flags)
break;
}
} else if (count == 1) {
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner),
- &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
error = EFAULT;
while (error == 0 && (owner & ~UMUTEX_CONTESTED) != 0 &&
@@ -1776,7 +1774,7 @@ do_unlock_pi(struct thread *td, struct umutex *m, uint32_t flags)
/*
* Make sure we own this mtx.
*/
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner), &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
return (EFAULT);
@@ -2008,7 +2006,7 @@ do_unlock_pp(struct thread *td, struct umutex *m, uint32_t flags)
/*
* Make sure we own this mtx.
*/
- error = fueword32(__DEVOLATILE(uint32_t *, &m->m_owner), &owner);
+ error = fueword32(&m->m_owner, &owner);
if (error == -1)
return (EFAULT);
@@ -2040,8 +2038,7 @@ do_unlock_pp(struct thread *td, struct umutex *m, uint32_t flags)
* to lock the mutex, it is necessary because thread priority
* has to be adjusted for such mutex.
*/
- error = suword32(__DEVOLATILE(uint32_t *, &m->m_owner),
- UMUTEX_CONTESTED);
+ error = suword32(&m->m_owner, UMUTEX_CONTESTED);
umtxq_lock(&key);
if (error == 0)
@@ -2116,8 +2113,7 @@ do_set_ceiling(struct thread *td, struct umutex *m, uint32_t ceiling,
if (owner == UMUTEX_CONTESTED) {
suword32(&m->m_ceilings[0], ceiling);
- suword32(__DEVOLATILE(uint32_t *, &m->m_owner),
- UMUTEX_CONTESTED);
+ suword32(&m->m_owner, UMUTEX_CONTESTED);
error = 0;
break;
}
@@ -2263,10 +2259,9 @@ do_cv_wait(struct thread *td, struct ucond *cv, struct umutex *m,
* Set c_has_waiters to 1 before releasing user mutex, also
* don't modify cache line when unnecessary.
*/
- error = fueword32(__DEVOLATILE(uint32_t *, &cv->c_has_waiters),
- &hasw);
+ error = fueword32(&cv->c_has_waiters, &hasw);
if (error == 0 && hasw == 0)
- suword32(__DEVOLATILE(uint32_t *, &cv->c_has_waiters), 1);
+ suword32(&cv->c_has_waiters, 1);
umtxq_unbusy_unlocked(&uq->uq_key);
@@ -2296,9 +2291,7 @@ do_cv_wait(struct thread *td, struct ucond *cv, struct umutex *m,
umtxq_remove(uq);
if (oldlen == 1) {
umtxq_unlock(&uq->uq_key);
- suword32(
- __DEVOLATILE(uint32_t *,
- &cv->c_has_waiters), 0);
+ suword32(&cv->c_has_waiters, 0);
umtxq_lock(&uq->uq_key);
}
}
@@ -2333,8 +2326,7 @@ do_cv_signal(struct thread *td, struct ucond *cv)
nwake = umtxq_signal(&key, 1);
if (cnt <= nwake) {
umtxq_unlock(&key);
- error = suword32(
- __DEVOLATILE(uint32_t *, &cv->c_has_waiters), 0);
+ error = suword32(&cv->c_has_waiters, 0);
if (error == -1)
error = EFAULT;
umtxq_lock(&key);
@@ -2363,7 +2355,7 @@ do_cv_broadcast(struct thread *td, struct ucond *cv)
umtxq_signal(&key, INT_MAX);
umtxq_unlock(&key);
- error = suword32(__DEVOLATILE(uint32_t *, &cv->c_has_waiters), 0);
+ error = suword32(&cv->c_has_waiters, 0);
if (error == -1)
error = EFAULT;
@@ -2399,8 +2391,7 @@ do_rw_rdlock(struct thread *td, struct urwlock *rwlock, long fflag, struct _umtx
wrflags |= URWLOCK_WRITE_WAITERS;
for (;;) {
- rv = fueword32(__DEVOLATILE(int32_t *, &rwlock->rw_state),
- &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1) {
umtx_key_release(&uq->uq_key);
return (EFAULT);
@@ -2440,8 +2431,7 @@ do_rw_rdlock(struct thread *td, struct urwlock *rwlock, long fflag, struct _umtx
* re-read the state, in case it changed between the try-lock above
* and the check below
*/
- rv = fueword32(__DEVOLATILE(int32_t *, &rwlock->rw_state),
- &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1)
error = EFAULT;
@@ -2499,8 +2489,7 @@ sleep:
umtxq_unlock(&uq->uq_key);
if (error)
break;
- rv = fueword32(__DEVOLATILE(int32_t *,
- &rwlock->rw_state), &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1) {
error = EFAULT;
break;
@@ -2517,8 +2506,7 @@ sleep:
}
suword32(&rwlock->rw_blocked_readers, blocked_readers-1);
if (blocked_readers == 1) {
- rv = fueword32(__DEVOLATILE(int32_t *,
- &rwlock->rw_state), &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1)
error = EFAULT;
while (error == 0) {
@@ -2569,8 +2557,7 @@ do_rw_wrlock(struct thread *td, struct urwlock *rwlock, struct _umtx_time *timeo
blocked_readers = 0;
for (;;) {
- rv = fueword32(__DEVOLATILE(int32_t *, &rwlock->rw_state),
- &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1) {
umtx_key_release(&uq->uq_key);
return (EFAULT);
@@ -2614,8 +2601,7 @@ do_rw_wrlock(struct thread *td, struct urwlock *rwlock, struct _umtx_time *timeo
* re-read the state, in case it changed between the try-lock above
* and the check below
*/
- rv = fueword32(__DEVOLATILE(int32_t *, &rwlock->rw_state),
- &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1)
error = EFAULT;
@@ -2670,8 +2656,7 @@ sleep:
umtxq_unlock(&uq->uq_key);
if (error)
break;
- rv = fueword32(__DEVOLATILE(int32_t *,
- &rwlock->rw_state), &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1) {
error = EFAULT;
break;
@@ -2687,8 +2672,7 @@ sleep:
}
suword32(&rwlock->rw_blocked_writers, blocked_writers-1);
if (blocked_writers == 1) {
- rv = fueword32(__DEVOLATILE(int32_t *,
- &rwlock->rw_state), &state);
+ rv = fueword32(&rwlock->rw_state, &state);
if (rv == -1) {
umtxq_unbusy_unlocked(&uq->uq_key);
error = EFAULT;
@@ -2748,7 +2732,7 @@ do_rw_unlock(struct thread *td, struct urwlock *rwlock)
if (error != 0)
return (error);
- error = fueword32(__DEVOLATILE(int32_t *, &rwlock->rw_state), &state);
+ error = fueword32(&rwlock->rw_state, &state);
if (error == -1) {
error = EFAULT;
goto out;
@@ -2856,7 +2840,7 @@ do_sem_wait(struct thread *td, struct _usem *sem, struct _umtx_time *timeout)
umtxq_unlock(&uq->uq_key);
rv = casueword32(&sem->_has_waiters, 0, &count1, 1);
if (rv == 0)
- rv = fueword32(__DEVOLATILE(uint32_t *, &sem->_count), &count);
+ rv = fueword32(&sem->_count, &count);
if (rv == -1 || count != 0) {
umtxq_lock(&uq->uq_key);
umtxq_unbusy(&uq->uq_key);
@@ -2911,8 +2895,7 @@ do_sem_wake(struct thread *td, struct _usem *sem)
*/
if (cnt == 1) {
umtxq_unlock(&key);
- error = suword32(
- __DEVOLATILE(uint32_t *, &sem->_has_waiters), 0);
+ error = suword32(&sem->_has_waiters, 0);
umtxq_lock(&key);
if (error == -1)
error = EFAULT;
@@ -2946,7 +2929,7 @@ do_sem2_wait(struct thread *td, struct _usem2 *sem, struct _umtx_time *timeout)
umtxq_busy(&uq->uq_key);
umtxq_insert(uq);
umtxq_unlock(&uq->uq_key);
- rv = fueword32(__DEVOLATILE(uint32_t *, &sem->_count), &count);
+ rv = fueword32(&sem->_count, &count);
if (rv == -1) {
umtxq_lock(&uq->uq_key);
umtxq_unbusy(&uq->uq_key);
@@ -3024,8 +3007,7 @@ do_sem2_wake(struct thread *td, struct _usem2 *sem)
*/
if (cnt == 1) {
umtxq_unlock(&key);
- rv = fueword32(__DEVOLATILE(uint32_t *, &sem->_count),
- &count);
+ rv = fueword32(&sem->_count, &count);
while (rv != -1 && count & USEM_HAS_WAITERS)
rv = casueword32(&sem->_count, count, &count,
count & ~USEM_HAS_WAITERS);
diff --git a/sys/kern/subr_uio.c b/sys/kern/subr_uio.c
index f2bbb0cdff12..87892fd82798 100644
--- a/sys/kern/subr_uio.c
+++ b/sys/kern/subr_uio.c
@@ -453,7 +453,7 @@ copyout_unmap(struct thread *td, vm_offset_t addr, size_t sz)
*/
int
-fueword(const void *base, long *val)
+fueword(volatile const void *base, long *val)
{
long res;
@@ -465,7 +465,7 @@ fueword(const void *base, long *val)
}
int
-fueword32(const void *base, int32_t *val)
+fueword32(volatile const void *base, int32_t *val)
{
int32_t res;
@@ -478,7 +478,7 @@ fueword32(const void *base, int32_t *val)
#ifdef _LP64
int
-fueword64(const void *base, int64_t *val)
+fueword64(volatile const void *base, int64_t *val)
{
int32_t res;
@@ -516,7 +516,7 @@ casueword(volatile u_long *p, u_long oldval, u_long *oldvalp, u_long newval)
}
#else /* NO_FUEWORD */
int32_t
-fuword32(const void *addr)
+fuword32(volatile const void *addr)
{
int rv;
int32_t val;
@@ -527,7 +527,7 @@ fuword32(const void *addr)
#ifdef _LP64
int64_t
-fuword64(const void *addr)
+fuword64(volatile const void *addr)
{
int rv;
int64_t val;
@@ -538,7 +538,7 @@ fuword64(const void *addr)
#endif /* _LP64 */
long
-fuword(const void *addr)
+fuword(volatile const void *addr)
{
long val;
int rv;
diff --git a/sys/powerpc/powerpc/copyinout.c b/sys/powerpc/powerpc/copyinout.c
index a337c8b73495..fdee51da056e 100644
--- a/sys/powerpc/powerpc/copyinout.c
+++ b/sys/powerpc/powerpc/copyinout.c
@@ -80,7 +80,7 @@ int setfault(faultbuf); /* defined in locore.S */
#ifdef __powerpc64__
static __inline void
-set_user_sr(pmap_t pm, const void *addr)
+set_user_sr(pmap_t pm, volatile const void *addr)
{
struct slb *slb;
register_t slbv;
@@ -113,7 +113,7 @@ set_user_sr(pmap_t pm, const void *addr)
}
#else
static __inline void
-set_user_sr(pmap_t pm, const void *addr)
+set_user_sr(pmap_t pm, volatile const void *addr)
{
register_t vsid;
@@ -135,7 +135,7 @@ set_user_sr(pmap_t pm, const void *addr)
#endif
static __inline int
-map_user_ptr(pmap_t pm, const void *uaddr, void **kaddr, size_t ulen,
+map_user_ptr(pmap_t pm, volatile const void *uaddr, void **kaddr, size_t ulen,
size_t *klen)
{
size_t l;
@@ -156,7 +156,7 @@ map_user_ptr(pmap_t pm, const void *uaddr, void **kaddr, size_t ulen,
}
#else /* Book-E uses a combined kernel/user mapping */
static __inline int
-map_user_ptr(pmap_t pm, const void *uaddr, void **kaddr, size_t ulen,
+map_user_ptr(pmap_t pm, volatile const void *uaddr, void **kaddr, size_t ulen,
size_t *klen)
{
@@ -281,7 +281,7 @@ copyinstr(const void *udaddr, void *kaddr, size_t len, size_t *done)
}
int
-subyte(void *addr, int byte)
+subyte(volatile void *addr, int byte)
{
struct thread *td;
pmap_t pm;
@@ -309,7 +309,7 @@ subyte(void *addr, int byte)
#ifdef __powerpc64__
int
-suword32(void *addr, int word)
+suword32(volatile void *addr, int word)
{
struct thread *td;
pmap_t pm;
@@ -337,7 +337,7 @@ suword32(void *addr, int word)
#endif
int
-suword(void *addr, long word)
+suword(volatile void *addr, long word)
{
struct thread *td;
pmap_t pm;
@@ -365,20 +365,20 @@ suword(void *addr, long word)
#ifdef __powerpc64__
int
-suword64(void *addr, int64_t word)
+suword64(volatile void *addr, int64_t word)
{
return (suword(addr, (long)word));
}
#else
int
-suword32(void *addr, int32_t word)
+suword32(volatile void *addr, int32_t word)
{
return (suword(addr, (long)word));
}
#endif
int
-fubyte(const void *addr)
+fubyte(volatile const void *addr)
{
struct thread *td;
pmap_t pm;
@@ -406,7 +406,7 @@ fubyte(const void *addr)
}
int
-fuword16(const void *addr)
+fuword16(volatile const void *addr)
{
struct thread *td;
pmap_t pm;
@@ -433,7 +433,7 @@ fuword16(const void *addr)
}
int
-fueword32(const void *addr, int32_t *val)
+fueword32(volatile const void *addr, int32_t *val)
{
struct thread *td;
pmap_t pm;
@@ -461,7 +461,7 @@ fueword32(const void *addr, int32_t *val)
#ifdef __powerpc64__
int
-fueword64(const void *addr, int64_t *val)
+fueword64(volatile const void *addr, int64_t *val)
{
struct thread *td;
pmap_t pm;
@@ -489,7 +489,7 @@ fueword64(const void *addr, int64_t *val)
#endif
int
-fueword(const void *addr, long *val)
+fueword(volatile const void *addr, long *val)
{
struct thread *td;
pmap_t pm;
diff --git a/sys/sys/systm.h b/sys/sys/systm.h
index 6f2e86d4225a..d3833d0f7df6 100644
--- a/sys/sys/systm.h
+++ b/sys/sys/systm.h
@@ -252,19 +252,19 @@ int copyout(const void * __restrict kaddr, void * __restrict udaddr,
int copyout_nofault(const void * __restrict kaddr, void * __restrict udaddr,
size_t len) __nonnull(1) __nonnull(2);
-int fubyte(const void *base);
-long fuword(const void *base);
-int fuword16(const void *base);
-int32_t fuword32(const void *base);
-int64_t fuword64(const void *base);
-int fueword(const void *base, long *val);
-int fueword32(const void *base, int32_t *val);
-int fueword64(const void *base, int64_t *val);
-int subyte(void *base, int byte);
-int suword(void *base, long word);
-int suword16(void *base, int word);
-int suword32(void *base, int32_t word);
-int suword64(void *base, int64_t word);
+int fubyte(volatile const void *base);
+long fuword(volatile const void *base);
+int fuword16(volatile const void *base);
+int32_t fuword32(volatile const void *base);
+int64_t fuword64(volatile const void *base);
+int fueword(volatile const void *base, long *val);
+int fueword32(volatile const void *base, int32_t *val);
+int fueword64(volatile const void *base, int64_t *val);
+int subyte(volatile void *base, int byte);
+int suword(volatile void *base, long word);
+int suword16(volatile void *base, int word);
+int suword32(volatile void *base, int32_t word);
+int suword64(volatile void *base, int64_t word);
uint32_t casuword32(volatile uint32_t *base, uint32_t oldval, uint32_t newval);
u_long casuword(volatile u_long *p, u_long oldval, u_long newval);
int casueword32(volatile uint32_t *base, uint32_t oldval, uint32_t *oldvalp,