~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to storage/innobase/include/sync0rw.h

  • Committer: Monty Taylor
  • Date: 2009-01-09 07:02:24 UTC
  • mto: (779.1.2 devel)
  • mto: This revision was merged to the branch mainline in revision 784.
  • Revision ID: mordred@inaugust.com-20090109070224-prwl5p52mfql3zfw
Split out readline.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*****************************************************************************
2
 
 
3
 
Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved.
4
 
Copyright (c) 2008, Google Inc.
5
 
 
6
 
Portions of this file contain modifications contributed and copyrighted by
7
 
Google, Inc. Those modifications are gratefully acknowledged and are described
8
 
briefly in the InnoDB documentation. The contributions by Google are
9
 
incorporated with their permission, and subject to the conditions contained in
10
 
the file COPYING.Google.
11
 
 
12
 
This program is free software; you can redistribute it and/or modify it under
13
 
the terms of the GNU General Public License as published by the Free Software
14
 
Foundation; version 2 of the License.
15
 
 
16
 
This program is distributed in the hope that it will be useful, but WITHOUT
17
 
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
18
 
FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
19
 
 
20
 
You should have received a copy of the GNU General Public License along with
21
 
this program; if not, write to the Free Software Foundation, Inc., 59 Temple
22
 
Place, Suite 330, Boston, MA 02111-1307 USA
23
 
 
24
 
*****************************************************************************/
25
 
 
26
1
/******************************************************
27
2
The read-write lock (for threads, not for database transactions)
28
3
 
 
4
(c) 1995 Innobase Oy
 
5
 
29
6
Created 9/11/1995 Heikki Tuuri
30
7
*******************************************************/
31
8
 
47
24
#define RW_X_LATCH      2
48
25
#define RW_NO_LATCH     3
49
26
 
50
 
/* We decrement lock_word by this amount for each x_lock. It is also the
51
 
start value for the lock_word, meaning that it limits the maximum number
52
 
of concurrent read locks before the rw_lock breaks. The current value of
53
 
0x00100000 allows 1,048,575 concurrent readers and 2047 recursive writers.*/
54
 
#define X_LOCK_DECR             0x00100000
55
 
 
56
27
typedef struct rw_lock_struct           rw_lock_t;
57
28
#ifdef UNIV_SYNC_DEBUG
58
29
typedef struct rw_lock_debug_struct     rw_lock_debug_t;
76
47
                                        there may be waiters for the event */
77
48
#endif /* UNIV_SYNC_DEBUG */
78
49
 
79
 
extern  ib_int64_t      rw_s_spin_wait_count;
80
 
extern  ib_int64_t      rw_s_spin_round_count;
81
 
extern  ib_int64_t      rw_s_exit_count;
82
 
extern  ib_int64_t      rw_s_os_wait_count;
83
 
extern  ib_int64_t      rw_x_spin_wait_count;
84
 
extern  ib_int64_t      rw_x_spin_round_count;
85
 
extern  ib_int64_t      rw_x_os_wait_count;
86
 
extern  ib_int64_t      rw_x_exit_count;
 
50
extern  ulint   rw_s_system_call_count;
 
51
extern  ulint   rw_s_spin_wait_count;
 
52
extern  ulint   rw_s_exit_count;
 
53
extern  ulint   rw_s_os_wait_count;
 
54
extern  ulint   rw_x_system_call_count;
 
55
extern  ulint   rw_x_spin_wait_count;
 
56
extern  ulint   rw_x_os_wait_count;
 
57
extern  ulint   rw_x_exit_count;
87
58
 
88
59
/**********************************************************************
89
60
Creates, or rather, initializes an rw-lock object in a specified memory
156
127
NOTE! The following macros should be used in rw s-locking, not the
157
128
corresponding function. */
158
129
 
159
 
#define rw_lock_s_lock_nowait(M, F, L)    rw_lock_s_lock_low(\
160
 
                                          (M), 0, (F), (L))
161
 
/**********************************************************************
162
 
Low-level function which tries to lock an rw-lock in s-mode. Performs no
163
 
spinning. */
164
 
UNIV_INLINE
165
 
ibool
166
 
rw_lock_s_lock_low(
167
 
/*===============*/
168
 
                                /* out: TRUE if success */
169
 
        rw_lock_t*      lock,   /* in: pointer to rw-lock */
170
 
        ulint           pass __attribute__((unused)),
171
 
                                /* in: pass value; != 0, if the lock will be
172
 
                                passed to another thread to unlock */
173
 
        const char*     file_name, /* in: file name where lock requested */
174
 
        ulint           line);  /* in: line where requested */
 
130
#define rw_lock_s_lock_nowait(M)        rw_lock_s_lock_func_nowait(\
 
131
                (M), __FILE__, __LINE__)
175
132
/**********************************************************************
176
133
NOTE! Use the corresponding macro, not directly this function, except if
177
134
you supply the file name and line number. Lock an rw-lock in shared mode
189
146
        const char*     file_name,/* in: file name where lock requested */
190
147
        ulint           line);  /* in: line where requested */
191
148
/**********************************************************************
 
149
NOTE! Use the corresponding macro, not directly this function, except if
 
150
you supply the file name and line number. Lock an rw-lock in shared mode
 
151
for the current thread if the lock can be acquired immediately. */
 
152
UNIV_INLINE
 
153
ibool
 
154
rw_lock_s_lock_func_nowait(
 
155
/*=======================*/
 
156
                                /* out: TRUE if success */
 
157
        rw_lock_t*      lock,   /* in: pointer to rw-lock */
 
158
        const char*     file_name,/* in: file name where lock requested */
 
159
        ulint           line);  /* in: line where requested */
 
160
/**********************************************************************
192
161
NOTE! Use the corresponding macro, not directly this function! Lock an
193
162
rw-lock in exclusive mode for the current thread if the lock can be
194
163
obtained immediately. */
372
341
rw_lock_get_reader_count(
373
342
/*=====================*/
374
343
        rw_lock_t*      lock);
375
 
/**********************************************************************
376
 
Decrements lock_word the specified amount if it is greater than 0.
377
 
This is used by both s_lock and x_lock operations. */
378
 
UNIV_INLINE
379
 
ibool
380
 
rw_lock_lock_word_decr(
381
 
/*===================*/
382
 
                                        /* out: TRUE if decr occurs */
383
 
        rw_lock_t*      lock,           /* in: rw-lock */
384
 
        ulint           amount);        /* in: amount to decrement */
385
 
/**********************************************************************
386
 
Increments lock_word the specified amount and returns new value. */
387
 
UNIV_INLINE
388
 
lint
389
 
rw_lock_lock_word_incr(
390
 
/*===================*/
391
 
                                        /* out: TRUE if decr occurs */
392
 
        rw_lock_t*      lock,
393
 
        ulint           amount);        /* in: rw-lock */
394
 
/**********************************************************************
395
 
This function sets the lock->writer_thread and lock->recursive fields.
396
 
For platforms where we are using atomic builtins instead of lock->mutex
397
 
it sets the lock->writer_thread field using atomics to ensure memory
398
 
ordering. Note that it is assumed that the caller of this function
399
 
effectively owns the lock i.e.: nobody else is allowed to modify
400
 
lock->writer_thread at this point in time.
401
 
The protocol is that lock->writer_thread MUST be updated BEFORE the
402
 
lock->recursive flag is set. */
403
 
UNIV_INLINE
404
 
void
405
 
rw_lock_set_writer_id_and_recursion_flag(
406
 
/*=====================================*/
407
 
        rw_lock_t*      lock,           /* in/out: lock to work on */
408
 
        ibool           recursive);     /* in: TRUE if recursion
409
 
                                        allowed */
410
344
#ifdef UNIV_SYNC_DEBUG
411
345
/**********************************************************************
412
346
Checks if the thread has locked the rw-lock in the specified mode, with
483
417
implementation of a read-write lock. Several threads may have a shared lock
484
418
simultaneously in this lock, but only one writer may have an exclusive lock,
485
419
in which case no shared locks are allowed. To prevent starving of a writer
486
 
blocked by readers, a writer may queue for x-lock by decrementing lock_word:
487
 
no new readers will be let in while the thread waits for readers to exit. */
 
420
blocked by readers, a writer may queue for the lock by setting the writer
 
421
field. Then no new readers are allowed in. */
488
422
 
489
423
struct rw_lock_struct {
490
 
        volatile lint   lock_word;
491
 
                                /* Holds the state of the lock. */
492
 
        volatile ulint  waiters;/* 1: there are waiters */
493
 
        volatile ibool  recursive;/* Default value FALSE which means the lock
494
 
                                is non-recursive. The value is typically set
495
 
                                to TRUE making normal rw_locks recursive. In
496
 
                                case of asynchronous IO, when a non-zero
497
 
                                value of 'pass' is passed then we keep the
498
 
                                lock non-recursive.
499
 
                                This flag also tells us about the state of
500
 
                                writer_thread field. If this flag is set
501
 
                                then writer_thread MUST contain the thread
502
 
                                id of the current x-holder or wait-x thread.
503
 
                                This flag must be reset in x_unlock
504
 
                                functions before incrementing the lock_word */
505
 
        volatile os_thread_id_t writer_thread;
506
 
                                /* Thread id of writer thread. Is only
507
 
                                guaranteed to have sane and non-stale
508
 
                                value iff recursive flag is set. */
509
424
        os_event_t      event;  /* Used by sync0arr.c for thread queueing */
510
 
        os_event_t      wait_ex_event;
511
 
                                /* Event for next-writer to wait on. A thread
512
 
                                must decrement lock_word before waiting. */
513
 
#ifndef INNODB_RW_LOCKS_USE_ATOMICS
 
425
 
 
426
#ifdef __WIN__
 
427
        os_event_t      wait_ex_event;  /* This windows specific event is
 
428
                                used by the thread which has set the
 
429
                                lock state to RW_LOCK_WAIT_EX. The
 
430
                                rw_lock design guarantees that this
 
431
                                thread will be the next one to proceed
 
432
                                once the current the event gets
 
433
                                signalled. See LEMMA 2 in sync0sync.c */
 
434
#endif
 
435
 
 
436
        ulint   reader_count;   /* Number of readers who have locked this
 
437
                                lock in the shared mode */
 
438
        ulint   writer;         /* This field is set to RW_LOCK_EX if there
 
439
                                is a writer owning the lock (in exclusive
 
440
                                mode), RW_LOCK_WAIT_EX if a writer is
 
441
                                queueing for the lock, and
 
442
                                RW_LOCK_NOT_LOCKED, otherwise. */
 
443
        os_thread_id_t  writer_thread;
 
444
                                /* Thread id of a possible writer thread */
 
445
        ulint   writer_count;   /* Number of times the same thread has
 
446
                                recursively locked the lock in the exclusive
 
447
                                mode */
514
448
        mutex_t mutex;          /* The mutex protecting rw_lock_struct */
515
 
#endif /* INNODB_RW_LOCKS_USE_ATOMICS */
516
 
 
 
449
        ulint   pass;           /* Default value 0. This is set to some
 
450
                                value != 0 given by the caller of an x-lock
 
451
                                operation, if the x-lock is to be passed to
 
452
                                another thread to unlock (which happens in
 
453
                                asynchronous i/o). */
 
454
        ulint   waiters;        /* This ulint is set to 1 if there are
 
455
                                waiters (readers or writers) in the global
 
456
                                wait array, waiting for this rw_lock.
 
457
                                Otherwise, == 0. */
517
458
        UT_LIST_NODE_T(rw_lock_t) list;
518
459
                                /* All allocated rw locks are put into a
519
460
                                list */
523
464
                                info list of the lock */
524
465
        ulint   level;          /* Level in the global latching order. */
525
466
#endif /* UNIV_SYNC_DEBUG */
526
 
        ulint count_os_wait;    /* Count of os_waits. May not be accurate */
527
467
        const char*     cfile_name;/* File name where lock created */
528
 
        /* last s-lock file/line is not guaranteed to be correct */
529
468
        const char*     last_s_file_name;/* File name where last s-locked */
530
469
        const char*     last_x_file_name;/* File name where last x-locked */
531
470
        ibool           writer_is_wait_ex;