Commit 9b6c4ea9 authored by Linus Torvalds's avatar Linus Torvalds

Merge branch 'core-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull locking fixes from Ingo Molnar:
 "Two fixes from lockdep coverage of seqlocks, which fix deadlocks on
  lockdep-enabled ARM systems"

* 'core-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  sched_clock: Disable seqlock lockdep usage in sched_clock()
  seqlock: Use raw_ prefix instead of _no_lockdep
parents 93a11c8f 7a06c41c
...@@ -178,7 +178,7 @@ notrace static int __always_inline do_realtime(struct timespec *ts) ...@@ -178,7 +178,7 @@ notrace static int __always_inline do_realtime(struct timespec *ts)
ts->tv_nsec = 0; ts->tv_nsec = 0;
do { do {
seq = read_seqcount_begin_no_lockdep(&gtod->seq); seq = raw_read_seqcount_begin(&gtod->seq);
mode = gtod->clock.vclock_mode; mode = gtod->clock.vclock_mode;
ts->tv_sec = gtod->wall_time_sec; ts->tv_sec = gtod->wall_time_sec;
ns = gtod->wall_time_snsec; ns = gtod->wall_time_snsec;
...@@ -198,7 +198,7 @@ notrace static int do_monotonic(struct timespec *ts) ...@@ -198,7 +198,7 @@ notrace static int do_monotonic(struct timespec *ts)
ts->tv_nsec = 0; ts->tv_nsec = 0;
do { do {
seq = read_seqcount_begin_no_lockdep(&gtod->seq); seq = raw_read_seqcount_begin(&gtod->seq);
mode = gtod->clock.vclock_mode; mode = gtod->clock.vclock_mode;
ts->tv_sec = gtod->monotonic_time_sec; ts->tv_sec = gtod->monotonic_time_sec;
ns = gtod->monotonic_time_snsec; ns = gtod->monotonic_time_snsec;
...@@ -214,7 +214,7 @@ notrace static int do_realtime_coarse(struct timespec *ts) ...@@ -214,7 +214,7 @@ notrace static int do_realtime_coarse(struct timespec *ts)
{ {
unsigned long seq; unsigned long seq;
do { do {
seq = read_seqcount_begin_no_lockdep(&gtod->seq); seq = raw_read_seqcount_begin(&gtod->seq);
ts->tv_sec = gtod->wall_time_coarse.tv_sec; ts->tv_sec = gtod->wall_time_coarse.tv_sec;
ts->tv_nsec = gtod->wall_time_coarse.tv_nsec; ts->tv_nsec = gtod->wall_time_coarse.tv_nsec;
} while (unlikely(read_seqcount_retry(&gtod->seq, seq))); } while (unlikely(read_seqcount_retry(&gtod->seq, seq)));
...@@ -225,7 +225,7 @@ notrace static int do_monotonic_coarse(struct timespec *ts) ...@@ -225,7 +225,7 @@ notrace static int do_monotonic_coarse(struct timespec *ts)
{ {
unsigned long seq; unsigned long seq;
do { do {
seq = read_seqcount_begin_no_lockdep(&gtod->seq); seq = raw_read_seqcount_begin(&gtod->seq);
ts->tv_sec = gtod->monotonic_time_coarse.tv_sec; ts->tv_sec = gtod->monotonic_time_coarse.tv_sec;
ts->tv_nsec = gtod->monotonic_time_coarse.tv_nsec; ts->tv_nsec = gtod->monotonic_time_coarse.tv_nsec;
} while (unlikely(read_seqcount_retry(&gtod->seq, seq))); } while (unlikely(read_seqcount_retry(&gtod->seq, seq)));
......
...@@ -117,15 +117,15 @@ static inline unsigned __read_seqcount_begin(const seqcount_t *s) ...@@ -117,15 +117,15 @@ static inline unsigned __read_seqcount_begin(const seqcount_t *s)
} }
/** /**
* read_seqcount_begin_no_lockdep - start seq-read critical section w/o lockdep * raw_read_seqcount_begin - start seq-read critical section w/o lockdep
* @s: pointer to seqcount_t * @s: pointer to seqcount_t
* Returns: count to be passed to read_seqcount_retry * Returns: count to be passed to read_seqcount_retry
* *
* read_seqcount_begin_no_lockdep opens a read critical section of the given * raw_read_seqcount_begin opens a read critical section of the given
* seqcount, but without any lockdep checking. Validity of the critical * seqcount, but without any lockdep checking. Validity of the critical
* section is tested by checking read_seqcount_retry function. * section is tested by checking read_seqcount_retry function.
*/ */
static inline unsigned read_seqcount_begin_no_lockdep(const seqcount_t *s) static inline unsigned raw_read_seqcount_begin(const seqcount_t *s)
{ {
unsigned ret = __read_seqcount_begin(s); unsigned ret = __read_seqcount_begin(s);
smp_rmb(); smp_rmb();
...@@ -144,7 +144,7 @@ static inline unsigned read_seqcount_begin_no_lockdep(const seqcount_t *s) ...@@ -144,7 +144,7 @@ static inline unsigned read_seqcount_begin_no_lockdep(const seqcount_t *s)
static inline unsigned read_seqcount_begin(const seqcount_t *s) static inline unsigned read_seqcount_begin(const seqcount_t *s)
{ {
seqcount_lockdep_reader_access(s); seqcount_lockdep_reader_access(s);
return read_seqcount_begin_no_lockdep(s); return raw_read_seqcount_begin(s);
} }
/** /**
...@@ -206,14 +206,26 @@ static inline int read_seqcount_retry(const seqcount_t *s, unsigned start) ...@@ -206,14 +206,26 @@ static inline int read_seqcount_retry(const seqcount_t *s, unsigned start)
} }
static inline void raw_write_seqcount_begin(seqcount_t *s)
{
s->sequence++;
smp_wmb();
}
static inline void raw_write_seqcount_end(seqcount_t *s)
{
smp_wmb();
s->sequence++;
}
/* /*
* Sequence counter only version assumes that callers are using their * Sequence counter only version assumes that callers are using their
* own mutexing. * own mutexing.
*/ */
static inline void write_seqcount_begin_nested(seqcount_t *s, int subclass) static inline void write_seqcount_begin_nested(seqcount_t *s, int subclass)
{ {
s->sequence++; raw_write_seqcount_begin(s);
smp_wmb();
seqcount_acquire(&s->dep_map, subclass, 0, _RET_IP_); seqcount_acquire(&s->dep_map, subclass, 0, _RET_IP_);
} }
...@@ -225,8 +237,7 @@ static inline void write_seqcount_begin(seqcount_t *s) ...@@ -225,8 +237,7 @@ static inline void write_seqcount_begin(seqcount_t *s)
static inline void write_seqcount_end(seqcount_t *s) static inline void write_seqcount_end(seqcount_t *s)
{ {
seqcount_release(&s->dep_map, 1, _RET_IP_); seqcount_release(&s->dep_map, 1, _RET_IP_);
smp_wmb(); raw_write_seqcount_end(s);
s->sequence++;
} }
/** /**
......
...@@ -74,7 +74,7 @@ unsigned long long notrace sched_clock(void) ...@@ -74,7 +74,7 @@ unsigned long long notrace sched_clock(void)
return cd.epoch_ns; return cd.epoch_ns;
do { do {
seq = read_seqcount_begin(&cd.seq); seq = raw_read_seqcount_begin(&cd.seq);
epoch_cyc = cd.epoch_cyc; epoch_cyc = cd.epoch_cyc;
epoch_ns = cd.epoch_ns; epoch_ns = cd.epoch_ns;
} while (read_seqcount_retry(&cd.seq, seq)); } while (read_seqcount_retry(&cd.seq, seq));
...@@ -99,10 +99,10 @@ static void notrace update_sched_clock(void) ...@@ -99,10 +99,10 @@ static void notrace update_sched_clock(void)
cd.mult, cd.shift); cd.mult, cd.shift);
raw_local_irq_save(flags); raw_local_irq_save(flags);
write_seqcount_begin(&cd.seq); raw_write_seqcount_begin(&cd.seq);
cd.epoch_ns = ns; cd.epoch_ns = ns;
cd.epoch_cyc = cyc; cd.epoch_cyc = cyc;
write_seqcount_end(&cd.seq); raw_write_seqcount_end(&cd.seq);
raw_local_irq_restore(flags); raw_local_irq_restore(flags);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment