Skip to content

Commit

Permalink
[S390] use inline assembly contraints available with gcc 3.3.3
Browse files Browse the repository at this point in the history
Drop support to compile the kernel with gcc versions older than 3.3.3.
This allows us to use the "Q" inline assembly contraint on some more
inline assemblies without duplicating a lot of complex code (e.g. __xchg
and __cmpxchg). The distinction for older gcc versions can be removed
which saves a few lines and simplifies the code.

Reviewed-by: Heiko Carstens <heiko.carstens@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
  • Loading branch information
Martin Schwidefsky authored and Martin Schwidefsky committed Feb 26, 2010
1 parent d1bf859 commit 987bcda
Show file tree
Hide file tree
Showing 11 changed files with 226 additions and 388 deletions.
86 changes: 11 additions & 75 deletions arch/s390/include/asm/atomic.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,6 @@

#define ATOMIC_INIT(i) { (i) }

#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)

#define __CS_LOOP(ptr, op_val, op_string) ({ \
int old_val, new_val; \
asm volatile( \
Expand All @@ -35,26 +33,6 @@
new_val; \
})

#else /* __GNUC__ */

#define __CS_LOOP(ptr, op_val, op_string) ({ \
int old_val, new_val; \
asm volatile( \
" l %0,0(%3)\n" \
"0: lr %1,%0\n" \
op_string " %1,%4\n" \
" cs %0,%1,0(%3)\n" \
" jl 0b" \
: "=&d" (old_val), "=&d" (new_val), \
"=m" (((atomic_t *)(ptr))->counter) \
: "a" (ptr), "d" (op_val), \
"m" (((atomic_t *)(ptr))->counter) \
: "cc", "memory"); \
new_val; \
})

#endif /* __GNUC__ */

static inline int atomic_read(const atomic_t *v)
{
barrier();
Expand Down Expand Up @@ -101,19 +79,11 @@ static inline void atomic_set_mask(unsigned long mask, atomic_t *v)

static inline int atomic_cmpxchg(atomic_t *v, int old, int new)
{
#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)
asm volatile(
" cs %0,%2,%1"
: "+d" (old), "=Q" (v->counter)
: "d" (new), "Q" (v->counter)
: "cc", "memory");
#else /* __GNUC__ */
asm volatile(
" cs %0,%3,0(%2)"
: "+d" (old), "=m" (v->counter)
: "a" (v), "d" (new), "m" (v->counter)
: "cc", "memory");
#endif /* __GNUC__ */
return old;
}

Expand All @@ -140,8 +110,6 @@ static inline int atomic_add_unless(atomic_t *v, int a, int u)

#ifdef CONFIG_64BIT

#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)

#define __CSG_LOOP(ptr, op_val, op_string) ({ \
long long old_val, new_val; \
asm volatile( \
Expand All @@ -157,26 +125,6 @@ static inline int atomic_add_unless(atomic_t *v, int a, int u)
new_val; \
})

#else /* __GNUC__ */

#define __CSG_LOOP(ptr, op_val, op_string) ({ \
long long old_val, new_val; \
asm volatile( \
" lg %0,0(%3)\n" \
"0: lgr %1,%0\n" \
op_string " %1,%4\n" \
" csg %0,%1,0(%3)\n" \
" jl 0b" \
: "=&d" (old_val), "=&d" (new_val), \
"=m" (((atomic_t *)(ptr))->counter) \
: "a" (ptr), "d" (op_val), \
"m" (((atomic_t *)(ptr))->counter) \
: "cc", "memory"); \
new_val; \
})

#endif /* __GNUC__ */

static inline long long atomic64_read(const atomic64_t *v)
{
barrier();
Expand Down Expand Up @@ -214,19 +162,11 @@ static inline void atomic64_set_mask(unsigned long mask, atomic64_t *v)
static inline long long atomic64_cmpxchg(atomic64_t *v,
long long old, long long new)
{
#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)
asm volatile(
" csg %0,%2,%1"
: "+d" (old), "=Q" (v->counter)
: "d" (new), "Q" (v->counter)
: "cc", "memory");
#else /* __GNUC__ */
asm volatile(
" csg %0,%3,0(%2)"
: "+d" (old), "=m" (v->counter)
: "a" (v), "d" (new), "m" (v->counter)
: "cc", "memory");
#endif /* __GNUC__ */
return old;
}

Expand All @@ -243,10 +183,8 @@ static inline long long atomic64_read(const atomic64_t *v)
register_pair rp;

asm volatile(
" lm %0,%N0,0(%1)"
: "=&d" (rp)
: "a" (&v->counter), "m" (v->counter)
);
" lm %0,%N0,%1"
: "=&d" (rp) : "Q" (v->counter) );
return rp.pair;
}

Expand All @@ -255,10 +193,8 @@ static inline void atomic64_set(atomic64_t *v, long long i)
register_pair rp = {.pair = i};

asm volatile(
" stm %1,%N1,0(%2)"
: "=m" (v->counter)
: "d" (rp), "a" (&v->counter)
);
" stm %1,%N1,%0"
: "=Q" (v->counter) : "d" (rp) );
}

static inline long long atomic64_xchg(atomic64_t *v, long long new)
Expand All @@ -267,11 +203,11 @@ static inline long long atomic64_xchg(atomic64_t *v, long long new)
register_pair rp_old;

asm volatile(
" lm %0,%N0,0(%2)\n"
"0: cds %0,%3,0(%2)\n"
" lm %0,%N0,%1\n"
"0: cds %0,%2,%1\n"
" jl 0b\n"
: "=&d" (rp_old), "+m" (v->counter)
: "a" (&v->counter), "d" (rp_new)
: "=&d" (rp_old), "=Q" (v->counter)
: "d" (rp_new), "Q" (v->counter)
: "cc");
return rp_old.pair;
}
Expand All @@ -283,9 +219,9 @@ static inline long long atomic64_cmpxchg(atomic64_t *v,
register_pair rp_new = {.pair = new};

asm volatile(
" cds %0,%3,0(%2)"
: "+&d" (rp_old), "+m" (v->counter)
: "a" (&v->counter), "d" (rp_new)
" cds %0,%2,%1"
: "+&d" (rp_old), "=Q" (v->counter)
: "d" (rp_new), "Q" (v->counter)
: "cc");
return rp_old.pair;
}
Expand Down
83 changes: 20 additions & 63 deletions arch/s390/include/asm/bitops.h
Original file line number Diff line number Diff line change
Expand Up @@ -71,8 +71,6 @@ extern const char _sb_findmap[];
#define __BITOPS_AND "nr"
#define __BITOPS_XOR "xr"

#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)

#define __BITOPS_LOOP(__old, __new, __addr, __val, __op_string) \
asm volatile( \
" l %0,%2\n" \
Expand All @@ -85,22 +83,6 @@ extern const char _sb_findmap[];
: "d" (__val), "Q" (*(unsigned long *) __addr) \
: "cc");

#else /* __GNUC__ */

#define __BITOPS_LOOP(__old, __new, __addr, __val, __op_string) \
asm volatile( \
" l %0,0(%4)\n" \
"0: lr %1,%0\n" \
__op_string " %1,%3\n" \
" cs %0,%1,0(%4)\n" \
" jl 0b" \
: "=&d" (__old), "=&d" (__new), \
"=m" (*(unsigned long *) __addr) \
: "d" (__val), "a" (__addr), \
"m" (*(unsigned long *) __addr) : "cc");

#endif /* __GNUC__ */

#else /* __s390x__ */

#define __BITOPS_ALIGN 7
Expand All @@ -109,8 +91,6 @@ extern const char _sb_findmap[];
#define __BITOPS_AND "ngr"
#define __BITOPS_XOR "xgr"

#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 2)

#define __BITOPS_LOOP(__old, __new, __addr, __val, __op_string) \
asm volatile( \
" lg %0,%2\n" \
Expand All @@ -123,23 +103,6 @@ extern const char _sb_findmap[];
: "d" (__val), "Q" (*(unsigned long *) __addr) \
: "cc");

#else /* __GNUC__ */

#define __BITOPS_LOOP(__old, __new, __addr, __val, __op_string) \
asm volatile( \
" lg %0,0(%4)\n" \
"0: lgr %1,%0\n" \
__op_string " %1,%3\n" \
" csg %0,%1,0(%4)\n" \
" jl 0b" \
: "=&d" (__old), "=&d" (__new), \
"=m" (*(unsigned long *) __addr) \
: "d" (__val), "a" (__addr), \
"m" (*(unsigned long *) __addr) : "cc");


#endif /* __GNUC__ */

#endif /* __s390x__ */

#define __BITOPS_WORDS(bits) (((bits)+__BITOPS_WORDSIZE-1)/__BITOPS_WORDSIZE)
Expand Down Expand Up @@ -261,9 +224,8 @@ static inline void __set_bit(unsigned long nr, volatile unsigned long *ptr)

addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
asm volatile(
" oc 0(1,%1),0(%2)"
: "=m" (*(char *) addr) : "a" (addr),
"a" (_oi_bitmap + (nr & 7)), "m" (*(char *) addr) : "cc" );
" oc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_oi_bitmap[nr & 7]) : "cc" );
}

static inline void
Expand All @@ -290,9 +252,8 @@ __clear_bit(unsigned long nr, volatile unsigned long *ptr)

addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
asm volatile(
" nc 0(1,%1),0(%2)"
: "=m" (*(char *) addr) : "a" (addr),
"a" (_ni_bitmap + (nr & 7)), "m" (*(char *) addr) : "cc");
" nc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_ni_bitmap[nr & 7]) : "cc" );
}

static inline void
Expand All @@ -318,9 +279,8 @@ static inline void __change_bit(unsigned long nr, volatile unsigned long *ptr)

addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
asm volatile(
" xc 0(1,%1),0(%2)"
: "=m" (*(char *) addr) : "a" (addr),
"a" (_oi_bitmap + (nr & 7)), "m" (*(char *) addr) : "cc" );
" xc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_oi_bitmap[nr & 7]) : "cc" );
}

static inline void
Expand Down Expand Up @@ -349,10 +309,9 @@ test_and_set_bit_simple(unsigned long nr, volatile unsigned long *ptr)
addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
ch = *(unsigned char *) addr;
asm volatile(
" oc 0(1,%1),0(%2)"
: "=m" (*(char *) addr)
: "a" (addr), "a" (_oi_bitmap + (nr & 7)),
"m" (*(char *) addr) : "cc", "memory");
" oc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_oi_bitmap[nr & 7])
: "cc", "memory");
return (ch >> (nr & 7)) & 1;
}
#define __test_and_set_bit(X,Y) test_and_set_bit_simple(X,Y)
Expand All @@ -369,10 +328,9 @@ test_and_clear_bit_simple(unsigned long nr, volatile unsigned long *ptr)
addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
ch = *(unsigned char *) addr;
asm volatile(
" nc 0(1,%1),0(%2)"
: "=m" (*(char *) addr)
: "a" (addr), "a" (_ni_bitmap + (nr & 7)),
"m" (*(char *) addr) : "cc", "memory");
" nc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_ni_bitmap[nr & 7])
: "cc", "memory");
return (ch >> (nr & 7)) & 1;
}
#define __test_and_clear_bit(X,Y) test_and_clear_bit_simple(X,Y)
Expand All @@ -389,10 +347,9 @@ test_and_change_bit_simple(unsigned long nr, volatile unsigned long *ptr)
addr = (unsigned long) ptr + ((nr ^ (__BITOPS_WORDSIZE - 8)) >> 3);
ch = *(unsigned char *) addr;
asm volatile(
" xc 0(1,%1),0(%2)"
: "=m" (*(char *) addr)
: "a" (addr), "a" (_oi_bitmap + (nr & 7)),
"m" (*(char *) addr) : "cc", "memory");
" xc %O0(1,%R0),%1"
: "=Q" (*(char *) addr) : "Q" (_oi_bitmap[nr & 7])
: "cc", "memory");
return (ch >> (nr & 7)) & 1;
}
#define __test_and_change_bit(X,Y) test_and_change_bit_simple(X,Y)
Expand Down Expand Up @@ -591,11 +548,11 @@ static inline unsigned long __load_ulong_le(const unsigned long *p,
p = (unsigned long *)((unsigned long) p + offset);
#ifndef __s390x__
asm volatile(
" ic %0,0(%1)\n"
" icm %0,2,1(%1)\n"
" icm %0,4,2(%1)\n"
" icm %0,8,3(%1)"
: "=&d" (word) : "a" (p), "m" (*p) : "cc");
" ic %0,%O1(%R1)\n"
" icm %0,2,%O1+1(%R1)\n"
" icm %0,4,%O1+2(%R1)\n"
" icm %0,8,%O1+3(%R1)"
: "=&d" (word) : "Q" (*p) : "cc");
#else
asm volatile(
" lrvg %0,%1"
Expand Down
12 changes: 6 additions & 6 deletions arch/s390/include/asm/etr.h
Original file line number Diff line number Diff line change
Expand Up @@ -145,11 +145,11 @@ static inline int etr_setr(struct etr_eacr *ctrl)
int rc = -ENOSYS;

asm volatile(
" .insn s,0xb2160000,0(%2)\n"
" .insn s,0xb2160000,%1\n"
"0: la %0,0\n"
"1:\n"
EX_TABLE(0b,1b)
: "+d" (rc) : "m" (*ctrl), "a" (ctrl));
: "+d" (rc) : "Q" (*ctrl));
return rc;
}

Expand All @@ -159,11 +159,11 @@ static inline int etr_stetr(struct etr_aib *aib)
int rc = -ENOSYS;

asm volatile(
" .insn s,0xb2170000,0(%2)\n"
" .insn s,0xb2170000,%1\n"
"0: la %0,0\n"
"1:\n"
EX_TABLE(0b,1b)
: "+d" (rc) : "m" (*aib), "a" (aib));
: "+d" (rc) : "Q" (*aib));
return rc;
}

Expand All @@ -174,11 +174,11 @@ static inline int etr_steai(struct etr_aib *aib, unsigned int func)
int rc = -ENOSYS;

asm volatile(
" .insn s,0xb2b30000,0(%2)\n"
" .insn s,0xb2b30000,%1\n"
"0: la %0,0\n"
"1:\n"
EX_TABLE(0b,1b)
: "+d" (rc) : "m" (*aib), "a" (aib), "d" (reg0));
: "+d" (rc) : "Q" (*aib), "d" (reg0));
return rc;
}

Expand Down
Loading

0 comments on commit 987bcda

Please sign in to comment.