List:Commits« Previous MessageNext Message »
From:Sunny Bains Date:June 10 2010 9:23am
Subject:bzr commit into mysql-next-mr-innodb branch (Sunny.Bains:3230)
View as plain text  
#At file:///Users/sunny/innodb/bzr-new/next-mr/ based on revid:sunny.bains@stripped

 3230 Sunny Bains	2010-06-10 [merge]
      Merge changes from parent.

    added:
      mysql-test/suite/innodb/r/innodb_monitor.result
      mysql-test/suite/innodb/t/innodb_monitor.test
      storage/innobase/include/srv0mon.h
      storage/innobase/include/srv0mon.ic
      storage/innobase/srv/srv0mon.c
    modified:
      mysql-test/r/mysqlshow.result
      mysql-test/suite/sys_vars/r/all_vars.result
      storage/innobase/CMakeLists.txt
      storage/innobase/Makefile.am
      storage/innobase/btr/btr0btr.c
      storage/innobase/buf/buf0flu.c
      storage/innobase/dict/dict0dict.c
      storage/innobase/handler/ha_innodb.cc
      storage/innobase/handler/handler0alter.cc
      storage/innobase/handler/i_s.cc
      storage/innobase/handler/i_s.h
      storage/innobase/include/srv0srv.h
      storage/innobase/lock/lock0lock.c
      storage/innobase/log/log0log.c
      storage/innobase/os/os0file.c
      storage/innobase/page/page0zip.c
      storage/innobase/row/row0purge.c
      storage/innobase/srv/srv0srv.c
      storage/innobase/trx/trx0purge.c
      storage/innobase/trx/trx0roll.c
      storage/innobase/trx/trx0trx.c
=== modified file 'mysql-test/r/mysqlshow.result'
--- a/mysql-test/r/mysqlshow.result	revid:sunny.bains@stripped
+++ b/mysql-test/r/mysqlshow.result	revid:sunny.bains@stripped
@@ -111,11 +111,11 @@ Database: information_schema
 | VIEWS                                 |
 | INNODB_SYS_FIELDS                     |
 | INNODB_TRX                            |
-| INNODB_SYS_INDEXES                    |
+| INNODB_SYS_COLUMNS                    |
 | INNODB_LOCK_WAITS                     |
 | INNODB_SYS_TABLESTATS                 |
 | INNODB_CMP                            |
-| INNODB_SYS_COLUMNS                    |
+| INNODB_METRICS                        |
 | INNODB_CMP_RESET                      |
 | INNODB_SYS_FOREIGN_COLS               |
 | INNODB_LOCKS                          |
@@ -123,6 +123,7 @@ Database: information_schema
 | INNODB_CMPMEM                         |
 | INNODB_SYS_FOREIGN                    |
 | INNODB_SYS_TABLES                     |
+| INNODB_SYS_INDEXES                    |
 +---------------------------------------+
 Database: INFORMATION_SCHEMA
 +---------------------------------------+
@@ -160,11 +161,11 @@ Database: INFORMATION_SCHEMA
 | VIEWS                                 |
 | INNODB_SYS_FIELDS                     |
 | INNODB_TRX                            |
-| INNODB_SYS_INDEXES                    |
+| INNODB_SYS_COLUMNS                    |
 | INNODB_LOCK_WAITS                     |
 | INNODB_SYS_TABLESTATS                 |
 | INNODB_CMP                            |
-| INNODB_SYS_COLUMNS                    |
+| INNODB_METRICS                        |
 | INNODB_CMP_RESET                      |
 | INNODB_SYS_FOREIGN_COLS               |
 | INNODB_LOCKS                          |
@@ -172,6 +173,7 @@ Database: INFORMATION_SCHEMA
 | INNODB_CMPMEM                         |
 | INNODB_SYS_FOREIGN                    |
 | INNODB_SYS_TABLES                     |
+| INNODB_SYS_INDEXES                    |
 +---------------------------------------+
 Wildcard: inf_rmation_schema
 +--------------------+

=== added file 'mysql-test/suite/innodb/r/innodb_monitor.result'
--- a/mysql-test/suite/innodb/r/innodb_monitor.result	1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/innodb/r/innodb_monitor.result	revid:sunny.bains@stripped
@@ -0,0 +1,566 @@
+select * from information_schema.innodb_metrics;
+name	subsystem	value_since_start	max_since_start	min_since_start	avg_since_start	value_since_reset	max_since_reset	min_since_reset	avg_since_reset	start_time	stop_time	reset_time	status	type	description
+server_table_open	Server Metadata	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of table handler opened
+server_table_close	Server Metadata	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of table handler closed
+lock_deadlock_count	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of deadlocks
+lock_timeout	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of lock timeout
+lock_lockrec_wait	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of times wait for record lock
+lock_lockrec_request	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of record lock requested
+lock_lockrec_created	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of record lock created
+lock_lockrec_removed	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of record lock destroyed
+lock_num_lockrec	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Total number of record locks
+lock_tablelock_created	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of table locks created
+lock_tablelock_removed	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of table lock destroyed
+lock_num_tablelock	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Total number of table locks
+lock_row_lock_current_wait	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Current row lock wait
+lock_row_lock_wait_time	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Time waited for lock acquisition
+lock_row_lock_wait	Lock	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Total row lock waits
+buffer_reads	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of reads from disk
+buffer_read_request	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of read requests
+buffer_write_request	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of write requests
+buffer_page_in_flush	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pages in flush list
+buffer_wait_free	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of times wait for free buffer
+buffer_read_ahead	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pages read as read ahead
+buffer_read_ahead_evict	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Read ahead pages evicted without being accessed
+buffer_pool_total_page	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Total buffer pool pages
+buffer_pool_page_misc	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Buffer pages for misc use
+buffer_pool_page_data	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Buffer pages contain data
+buffer_pool_page_dirty	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Buffer pages currently dirty
+buffer_pool_page_free	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Buffer pages currently free
+buffer_page_created	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pages created
+buffer_page_written	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pages written
+buffer_page_read	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pages read
+buffer_byte_read	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Amount data read in bytes
+buffer_byte_written	Buffer	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Amount data written in bytes
+os_num_reads	OS	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of reads initiated
+os_num_writes	OS	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of writes inititated
+os_num_fsync	OS	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of fsync() call
+os_num_pending_reads	OS	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of reads pending
+os_num_pending_writes	OS	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of writes pending
+os_log_byte_written	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Bytes of log written
+os_log_fsync	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of fsync log writes
+os_log_pending_fsync	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pending fsync write
+os_log_pending_write	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of pending log file writes
+trx_num_commit	Transaction	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of transactions committed
+trx_num_abort	Transaction	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of transactions aborted
+trx_active_trx	Transaction	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of active transactions
+trx_num_row_purged	Transaction	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of rows purged
+trx_purge_delay	DML	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	microseconds DML to be delayed due to purge lagging
+trx_rseg_history_len	Transaction	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Length of the TRX_RSEG_HISTORY list
+log_num_checkpoint	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of checkpoints
+log_lsn_last_flush	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Last flush's LSN
+log_lsn_last_checkpoint	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	LSN at last checkpoint
+log_current_lsn	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Current LSN value
+log_pending_log_write	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Pending Log Writes
+log_pending_checkpoint	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Pending Checkpoints
+log_num_log_io	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of log I/Os
+log_waits	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of log waits due to small log buffer
+log_write_request	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of log write requests
+log_writes	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of log writes
+log_flush_io_capacity	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	current_value	Percent of Server IO capacity during flushing
+log_flush_dirty_page_exceed	Recovery	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of flush calls when the max dirty page pct was hit
+compress_num_page_compressed	Compression	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of page compressed
+compress_num_page_decompressed	Compression	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of page decompressed
+index_num_split	Index	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of index split
+index_num_merge	Index	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of index merge
+dml_num_reads	DML	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of rows read
+dml_num_inserts	DML	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of rows inserted
+dml_num_deletes	DML	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of rows deleted
+dml_updates	DML	0	NULL	NULL	NULL	0	NULL	NULL	NULL	NULL	NULL	NULL	stopped	counter_value	Number of rows updated
+select name, status from information_schema.innodb_metrics;
+name	status
+server_table_open	stopped
+server_table_close	stopped
+lock_deadlock_count	stopped
+lock_timeout	stopped
+lock_lockrec_wait	stopped
+lock_lockrec_request	stopped
+lock_lockrec_created	stopped
+lock_lockrec_removed	stopped
+lock_num_lockrec	stopped
+lock_tablelock_created	stopped
+lock_tablelock_removed	stopped
+lock_num_tablelock	stopped
+lock_row_lock_current_wait	stopped
+lock_row_lock_wait_time	stopped
+lock_row_lock_wait	stopped
+buffer_reads	stopped
+buffer_read_request	stopped
+buffer_write_request	stopped
+buffer_page_in_flush	stopped
+buffer_wait_free	stopped
+buffer_read_ahead	stopped
+buffer_read_ahead_evict	stopped
+buffer_pool_total_page	stopped
+buffer_pool_page_misc	stopped
+buffer_pool_page_data	stopped
+buffer_pool_page_dirty	stopped
+buffer_pool_page_free	stopped
+buffer_page_created	stopped
+buffer_page_written	stopped
+buffer_page_read	stopped
+buffer_byte_read	stopped
+buffer_byte_written	stopped
+os_num_reads	stopped
+os_num_writes	stopped
+os_num_fsync	stopped
+os_num_pending_reads	stopped
+os_num_pending_writes	stopped
+os_log_byte_written	stopped
+os_log_fsync	stopped
+os_log_pending_fsync	stopped
+os_log_pending_write	stopped
+trx_num_commit	stopped
+trx_num_abort	stopped
+trx_active_trx	stopped
+trx_num_row_purged	stopped
+trx_purge_delay	stopped
+trx_rseg_history_len	stopped
+log_num_checkpoint	stopped
+log_lsn_last_flush	stopped
+log_lsn_last_checkpoint	stopped
+log_current_lsn	stopped
+log_pending_log_write	stopped
+log_pending_checkpoint	stopped
+log_num_log_io	stopped
+log_waits	stopped
+log_write_request	stopped
+log_writes	stopped
+log_flush_io_capacity	stopped
+log_flush_dirty_page_exceed	stopped
+compress_num_page_compressed	stopped
+compress_num_page_decompressed	stopped
+index_num_split	stopped
+index_num_merge	stopped
+dml_num_reads	stopped
+dml_num_inserts	stopped
+dml_num_deletes	stopped
+dml_updates	stopped
+set global innodb_monitor_counter_on = all;
+select name, status from information_schema.innodb_metrics;
+name	status
+server_table_open	started
+server_table_close	started
+lock_deadlock_count	started
+lock_timeout	started
+lock_lockrec_wait	started
+lock_lockrec_request	started
+lock_lockrec_created	started
+lock_lockrec_removed	started
+lock_num_lockrec	started
+lock_tablelock_created	started
+lock_tablelock_removed	started
+lock_num_tablelock	started
+lock_row_lock_current_wait	started
+lock_row_lock_wait_time	started
+lock_row_lock_wait	started
+buffer_reads	started
+buffer_read_request	started
+buffer_write_request	started
+buffer_page_in_flush	started
+buffer_wait_free	started
+buffer_read_ahead	started
+buffer_read_ahead_evict	started
+buffer_pool_total_page	started
+buffer_pool_page_misc	started
+buffer_pool_page_data	started
+buffer_pool_page_dirty	started
+buffer_pool_page_free	started
+buffer_page_created	started
+buffer_page_written	started
+buffer_page_read	started
+buffer_byte_read	started
+buffer_byte_written	started
+os_num_reads	started
+os_num_writes	started
+os_num_fsync	started
+os_num_pending_reads	started
+os_num_pending_writes	started
+os_log_byte_written	started
+os_log_fsync	started
+os_log_pending_fsync	started
+os_log_pending_write	started
+trx_num_commit	started
+trx_num_abort	started
+trx_active_trx	started
+trx_num_row_purged	started
+trx_purge_delay	started
+trx_rseg_history_len	started
+log_num_checkpoint	started
+log_lsn_last_flush	started
+log_lsn_last_checkpoint	started
+log_current_lsn	started
+log_pending_log_write	started
+log_pending_checkpoint	started
+log_num_log_io	started
+log_waits	started
+log_write_request	started
+log_writes	started
+log_flush_io_capacity	started
+log_flush_dirty_page_exceed	started
+compress_num_page_compressed	started
+compress_num_page_decompressed	started
+index_num_split	started
+index_num_merge	started
+dml_num_reads	started
+dml_num_inserts	started
+dml_num_deletes	started
+dml_updates	started
+set global innodb_monitor_counter_on = aaa;
+ERROR 42000: Variable 'innodb_monitor_counter_on' can't be set to the value of 'aaa'
+set global innodb_monitor_counter_on = default;
+Warnings:
+Warning	1230	Default value is not defined for this set option. Please specify counter or module name to turn on/off or reset monitor counters.
+show warnings;
+Level	Code	Message
+Warning	1230	Default value is not defined for this set option. Please specify counter or module name to turn on/off or reset monitor counters.
+set global innodb_monitor_counter_off = All;
+select name, status from information_schema.innodb_metrics;
+name	status
+server_table_open	stopped
+server_table_close	stopped
+lock_deadlock_count	stopped
+lock_timeout	stopped
+lock_lockrec_wait	stopped
+lock_lockrec_request	stopped
+lock_lockrec_created	stopped
+lock_lockrec_removed	stopped
+lock_num_lockrec	stopped
+lock_tablelock_created	stopped
+lock_tablelock_removed	stopped
+lock_num_tablelock	stopped
+lock_row_lock_current_wait	stopped
+lock_row_lock_wait_time	stopped
+lock_row_lock_wait	stopped
+buffer_reads	stopped
+buffer_read_request	stopped
+buffer_write_request	stopped
+buffer_page_in_flush	stopped
+buffer_wait_free	stopped
+buffer_read_ahead	stopped
+buffer_read_ahead_evict	stopped
+buffer_pool_total_page	stopped
+buffer_pool_page_misc	stopped
+buffer_pool_page_data	stopped
+buffer_pool_page_dirty	stopped
+buffer_pool_page_free	stopped
+buffer_page_created	stopped
+buffer_page_written	stopped
+buffer_page_read	stopped
+buffer_byte_read	stopped
+buffer_byte_written	stopped
+os_num_reads	stopped
+os_num_writes	stopped
+os_num_fsync	stopped
+os_num_pending_reads	stopped
+os_num_pending_writes	stopped
+os_log_byte_written	stopped
+os_log_fsync	stopped
+os_log_pending_fsync	stopped
+os_log_pending_write	stopped
+trx_num_commit	stopped
+trx_num_abort	stopped
+trx_active_trx	stopped
+trx_num_row_purged	stopped
+trx_purge_delay	stopped
+trx_rseg_history_len	stopped
+log_num_checkpoint	stopped
+log_lsn_last_flush	stopped
+log_lsn_last_checkpoint	stopped
+log_current_lsn	stopped
+log_pending_log_write	stopped
+log_pending_checkpoint	stopped
+log_num_log_io	stopped
+log_waits	stopped
+log_write_request	stopped
+log_writes	stopped
+log_flush_io_capacity	stopped
+log_flush_dirty_page_exceed	stopped
+compress_num_page_compressed	stopped
+compress_num_page_decompressed	stopped
+index_num_split	stopped
+index_num_merge	stopped
+dml_num_reads	stopped
+dml_num_inserts	stopped
+dml_num_deletes	stopped
+dml_updates	stopped
+set global innodb_monitor_counter_reset_all = all;
+select name, value_since_start, status from information_schema.innodb_metrics;
+name	value_since_start	status
+server_table_open	0	stopped
+server_table_close	0	stopped
+lock_deadlock_count	0	stopped
+lock_timeout	0	stopped
+lock_lockrec_wait	0	stopped
+lock_lockrec_request	0	stopped
+lock_lockrec_created	0	stopped
+lock_lockrec_removed	0	stopped
+lock_num_lockrec	0	stopped
+lock_tablelock_created	0	stopped
+lock_tablelock_removed	0	stopped
+lock_num_tablelock	0	stopped
+lock_row_lock_current_wait	0	stopped
+lock_row_lock_wait_time	0	stopped
+lock_row_lock_wait	0	stopped
+buffer_reads	0	stopped
+buffer_read_request	0	stopped
+buffer_write_request	0	stopped
+buffer_page_in_flush	0	stopped
+buffer_wait_free	0	stopped
+buffer_read_ahead	0	stopped
+buffer_read_ahead_evict	0	stopped
+buffer_pool_total_page	0	stopped
+buffer_pool_page_misc	0	stopped
+buffer_pool_page_data	0	stopped
+buffer_pool_page_dirty	0	stopped
+buffer_pool_page_free	0	stopped
+buffer_page_created	0	stopped
+buffer_page_written	0	stopped
+buffer_page_read	0	stopped
+buffer_byte_read	0	stopped
+buffer_byte_written	0	stopped
+os_num_reads	0	stopped
+os_num_writes	0	stopped
+os_num_fsync	0	stopped
+os_num_pending_reads	0	stopped
+os_num_pending_writes	0	stopped
+os_log_byte_written	0	stopped
+os_log_fsync	0	stopped
+os_log_pending_fsync	0	stopped
+os_log_pending_write	0	stopped
+trx_num_commit	0	stopped
+trx_num_abort	0	stopped
+trx_active_trx	0	stopped
+trx_num_row_purged	0	stopped
+trx_purge_delay	0	stopped
+trx_rseg_history_len	0	stopped
+log_num_checkpoint	0	stopped
+log_lsn_last_flush	0	stopped
+log_lsn_last_checkpoint	0	stopped
+log_current_lsn	0	stopped
+log_pending_log_write	0	stopped
+log_pending_checkpoint	0	stopped
+log_num_log_io	0	stopped
+log_waits	0	stopped
+log_write_request	0	stopped
+log_writes	0	stopped
+log_flush_io_capacity	0	stopped
+log_flush_dirty_page_exceed	0	stopped
+compress_num_page_compressed	0	stopped
+compress_num_page_decompressed	0	stopped
+index_num_split	0	stopped
+index_num_merge	0	stopped
+dml_num_reads	0	stopped
+dml_num_inserts	0	stopped
+dml_num_deletes	0	stopped
+dml_updates	0	stopped
+set global innodb_monitor_counter_on = server_table_open;
+create table monitor_test(col int) engine = innodb;
+select * from monitor_test;
+col
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	1	NULL	1	1	NULL	1	started
+set global innodb_monitor_counter_reset = server_table_open;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	1	NULL	1	NULL	NULL	0	started
+drop table monitor_test;
+create table monitor_test(col int) engine = innodb;
+select * from monitor_test;
+col
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	1	NULL	1	started
+set global innodb_monitor_counter_reset_all = server_table_open;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	1	NULL	1	started
+set global innodb_monitor_counter_off = server_table_open;
+set global innodb_monitor_counter_reset = server_table_open;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	NULL	NULL	0	stopped
+drop table monitor_test;
+create table monitor_test(col int) engine = innodb;
+select * from monitor_test;
+col
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	NULL	NULL	0	stopped
+set global innodb_monitor_counter_reset_all = server_table_open;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	NULL	NULL	0	NULL	NULL	0	stopped
+set global innodb_monitor_counter_on = server_table_open;
+drop table monitor_test;
+create table monitor_test(col int) engine = innodb;
+select * from monitor_test;
+col
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	1	NULL	1	1	NULL	1	started
+set global innodb_monitor_counter_on = server_table_close;
+create index idx on monitor_test(col);
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_close";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_close	1	NULL	1	1	NULL	1	started
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	2	NULL	2	started
+server_table_close	1	NULL	1	1	NULL	1	started
+set global innodb_monitor_counter_off = module_server;
+set global innodb_monitor_counter_reset = module_server;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	2	NULL	2	NULL	NULL	0	stopped
+server_table_close	1	NULL	1	NULL	NULL	0	stopped
+set global innodb_monitor_counter_reset_all = module_server;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+server_table_open	NULL	NULL	0	NULL	NULL	0	stopped
+server_table_close	NULL	NULL	0	NULL	NULL	0	stopped
+set global innodb_monitor_counter_on = module_trx;
+begin;
+insert into monitor_test values(9);
+commit;
+begin;
+insert into monitor_test values(9);
+rollback;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "trx_num_abort" or name like "trx_active_trx";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+trx_num_abort	1	NULL	1	1	NULL	1	started
+trx_active_trx	1	0	0	1	0	0	started
+set global innodb_monitor_counter_off = module_trx;
+set global innodb_monitor_counter_on = module_dml;
+insert into monitor_test values(9);
+update monitor_test set col = 10 where col = 9;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	4	NULL	4	4	NULL	4	started
+dml_num_inserts	1	NULL	1	1	NULL	1	started
+dml_num_deletes	0	NULL	0	0	NULL	0	started
+dml_updates	2	NULL	2	2	NULL	2	started
+delete from monitor_test;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	6	NULL	6	6	NULL	6	started
+dml_num_inserts	1	NULL	1	1	NULL	1	started
+dml_num_deletes	2	NULL	2	2	NULL	2	started
+dml_updates	2	NULL	2	2	NULL	2	started
+set global innodb_monitor_counter_reset =  module_dml;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	6	NULL	6	0	NULL	0	started
+dml_num_inserts	1	NULL	1	0	NULL	0	started
+dml_num_deletes	2	NULL	2	0	NULL	0	started
+dml_updates	2	NULL	2	0	NULL	0	started
+insert into monitor_test values(9);
+insert into monitor_test values(1);
+delete from monitor_test;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	8	NULL	8	2	NULL	2	started
+dml_num_inserts	3	NULL	3	2	NULL	2	started
+dml_num_deletes	4	NULL	4	2	NULL	2	started
+dml_updates	2	NULL	2	0	NULL	0	started
+set global innodb_monitor_counter_reset_all  =  module_dml;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	8	NULL	8	2	NULL	2	started
+dml_num_inserts	3	NULL	3	2	NULL	2	started
+dml_num_deletes	4	NULL	4	2	NULL	2	started
+dml_updates	2	NULL	2	0	NULL	0	started
+set global innodb_monitor_counter_off = module_dml;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	8	NULL	8	2	NULL	2	stopped
+dml_num_inserts	3	NULL	3	2	NULL	2	stopped
+dml_num_deletes	4	NULL	4	2	NULL	2	stopped
+dml_updates	2	NULL	2	0	NULL	0	stopped
+set global innodb_monitor_counter_reset_all  = module_dml;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	NULL	NULL	0	NULL	NULL	0	stopped
+dml_num_inserts	NULL	NULL	0	NULL	NULL	0	stopped
+dml_num_deletes	NULL	NULL	0	NULL	NULL	0	stopped
+dml_updates	NULL	NULL	0	NULL	NULL	0	stopped
+set global innodb_monitor_counter_on = dml_num_inserts;
+insert into monitor_test values(9);
+insert into monitor_test values(1);
+delete from monitor_test;
+select name, max_since_start, min_since_start, value_since_start,
+max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+name	max_since_start	min_since_start	value_since_start	max_since_reset	min_since_reset	value_since_reset	status
+dml_num_reads	NULL	NULL	0	NULL	NULL	0	stopped
+dml_num_inserts	2	NULL	2	2	NULL	2	started
+dml_num_deletes	NULL	NULL	0	NULL	NULL	0	stopped
+dml_updates	NULL	NULL	0	NULL	NULL	0	stopped
+set global innodb_monitor_counter_off = module_dml;
+drop table monitor_test;
+set global innodb_monitor_counter_on = default;
+set global innodb_monitor_counter_off = default;
+set global innodb_monitor_counter_reset = default;
+set global innodb_monitor_counter_reset_all = default;

=== added file 'mysql-test/suite/innodb/t/innodb_monitor.test'
--- a/mysql-test/suite/innodb/t/innodb_monitor.test	1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/innodb/t/innodb_monitor.test	revid:sunny.bains@stripped
@@ -0,0 +1,278 @@
+# This is the test for Metrics Monitor Table feature.
+# Test the metrics monitor system's control system
+# and counter accuracy.
+
+--source include/have_innodb.inc
+
+select * from information_schema.innodb_metrics;
+
+# Test turn on/off the monitor counter  with "all" option
+# By default, they will be off
+select name, status from information_schema.innodb_metrics;
+
+# Turn on all monitor counters
+set global innodb_monitor_counter_on = all;
+
+# status should all change to "started"
+select name, status from information_schema.innodb_metrics;
+
+# Test wrong argument to the global configure option
+--error ER_WRONG_VALUE_FOR_VAR
+set global innodb_monitor_counter_on = aaa;
+
+# We require a valid monitor counter/module name. There is no default
+# counter name or module. A warning will be printed asking user to
+# specify a valid counter name.
+set global innodb_monitor_counter_on = default;
+
+show warnings;
+
+# Turn off all monitor counters, option name should be case
+# insensitive
+set global innodb_monitor_counter_off = All;
+
+# status should all change to "stopped"
+select name, status from information_schema.innodb_metrics;
+
+# Reset all counter values
+set global innodb_monitor_counter_reset_all = all;
+
+# value_since_start should all change to 0
+select name, value_since_start, status from information_schema.innodb_metrics;
+
+# Only turn on "table_open" counter
+set global innodb_monitor_counter_on = server_table_open;
+
+# Create a new table to test "server_table_open" counter
+create table monitor_test(col int) engine = innodb;
+
+# This will open the monitor_test table
+select * from monitor_test;
+
+# "server_table_open" should increment by 1
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Reset the counter value while counter is still on (started)
+# This will reset value "value_since_reset" but not
+# "value_since_start"
+set global innodb_monitor_counter_reset = server_table_open;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# re-create table again to increment "server_table_open" again
+drop table monitor_test;
+
+# Create a new table to test "server_table_open" counter
+create table monitor_test(col int) engine = innodb;
+
+select * from monitor_test;
+
+# "server_table_open" should increment
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Cannot reset all monitor value while the counter is on
+set global innodb_monitor_counter_reset_all = server_table_open;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Turn off the counter "server_table_open"
+set global innodb_monitor_counter_off = server_table_open;
+
+# Reset the counter value while counter is off (stopped)
+set global innodb_monitor_counter_reset = server_table_open;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# re-create table again. Since monitor is off, "server_table_open"
+# should not be incremented
+drop table monitor_test;
+
+# Create a new table to test "server_table_open" counter
+create table monitor_test(col int) engine = innodb;
+
+# "server_table_open" should increment
+select * from monitor_test;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Reset all the counters, include those counter *_since_start
+set global innodb_monitor_counter_reset_all = server_table_open;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Turn on "table_open" counter again
+set global innodb_monitor_counter_on = server_table_open;
+
+# Test server_table_open again to see if it is working correctly
+# after above round of turning on/off/reset
+drop table monitor_test;
+
+# Create a new table to test "server_table_open" counter
+create table monitor_test(col int) engine = innodb;
+
+select * from monitor_test;
+
+# "server_table_open" should increment
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_open";
+
+# Test counter "server_table_close", create index will close the old handle
+set global innodb_monitor_counter_on = server_table_close;
+
+create index idx on monitor_test(col);
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name = "server_table_close";
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+
+# Reset counters only in "module_server" module
+set global innodb_monitor_counter_off = module_server;
+
+set global innodb_monitor_counter_reset = module_server;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+
+set global innodb_monitor_counter_reset_all = module_server;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "server%";
+
+# Test Transaction Module
+set global innodb_monitor_counter_on = module_trx;
+
+begin;
+insert into monitor_test values(9);
+commit;
+
+begin;
+insert into monitor_test values(9);
+rollback;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "trx_num_abort" or name like "trx_active_trx";
+
+set global innodb_monitor_counter_off = module_trx;
+
+# Test DML Module
+set global innodb_monitor_counter_on = module_dml;
+
+insert into monitor_test values(9);
+
+update monitor_test set col = 10 where col = 9;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+delete from monitor_test;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+	from information_schema.innodb_metrics
+	where name like "dml%";
+
+# test reset counter while the counter is on
+set global innodb_monitor_counter_reset =  module_dml;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+# insert/delete some rows after the reset
+insert into monitor_test values(9);
+insert into monitor_test values(1);
+
+delete from monitor_test;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+# We do not allow reset_all while the counter is on, nothing
+# should be reset here
+set global innodb_monitor_counter_reset_all  =  module_dml;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+# Turn off the counter
+set global innodb_monitor_counter_off = module_dml;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+# Reset all counter values
+set global innodb_monitor_counter_reset_all  = module_dml;
+
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+# Open individual counter "dml_num_inserts"
+set global innodb_monitor_counter_on = dml_num_inserts;
+
+insert into monitor_test values(9);
+insert into monitor_test values(1);
+
+delete from monitor_test;
+
+# Only counter "dml_num_inserts" should be updated
+select name, max_since_start, min_since_start, value_since_start,
+	max_since_reset, min_since_reset, value_since_reset, status
+from information_schema.innodb_metrics
+where name like "dml%";
+
+set global innodb_monitor_counter_off = module_dml;
+
+drop table monitor_test;
+
+-- disable_warnings
+set global innodb_monitor_counter_on = default;
+set global innodb_monitor_counter_off = default;
+set global innodb_monitor_counter_reset = default;
+set global innodb_monitor_counter_reset_all = default;
+-- enable_warnings

=== modified file 'mysql-test/suite/sys_vars/r/all_vars.result'
--- a/mysql-test/suite/sys_vars/r/all_vars.result	revid:sunny.bains@stripped
+++ b/mysql-test/suite/sys_vars/r/all_vars.result	revid:sunny.bains@stripped
@@ -10,5 +10,13 @@ There should be *no* long test name list
 select variable_name as `There should be *no* variables listed below:` from t2
 left join t1 on variable_name=test_name where test_name is null;
 There should be *no* variables listed below:
+INNODB_MONITOR_COUNTER_RESET
+INNODB_MONITOR_COUNTER_RESET_ALL
+INNODB_MONITOR_COUNTER_ON
+INNODB_MONITOR_COUNTER_OFF
+INNODB_MONITOR_COUNTER_RESET
+INNODB_MONITOR_COUNTER_RESET_ALL
+INNODB_MONITOR_COUNTER_ON
+INNODB_MONITOR_COUNTER_OFF
 drop table t1;
 drop table t2;

=== modified file 'storage/innobase/CMakeLists.txt'
--- a/storage/innobase/CMakeLists.txt	revid:sunny.bains@stripped
+++ b/storage/innobase/CMakeLists.txt	revid:sunny.bains@stripped
@@ -236,7 +236,7 @@ SET(INNOBASE_SOURCES	btr/btr0btr.c btr/b
 			rem/rem0cmp.c rem/rem0rec.c
 			row/row0ext.c row/row0ins.c row/row0merge.c row/row0mysql.c row/row0purge.c row/row0row.c
 			row/row0sel.c row/row0uins.c row/row0umod.c row/row0undo.c row/row0upd.c row/row0vers.c
-			srv/srv0srv.c srv/srv0start.c
+			srv/srv0mon.c srv/srv0srv.c srv/srv0start.c
 			sync/sync0arr.c sync/sync0rw.c sync/sync0sync.c
 			thr/thr0loc.c
 			trx/trx0i_s.c trx/trx0purge.c trx/trx0rec.c trx/trx0roll.c trx/trx0rseg.c

=== modified file 'storage/innobase/Makefile.am'
--- a/storage/innobase/Makefile.am	revid:sunny.bains@stripped
+++ b/storage/innobase/Makefile.am	revid:sunny.bains@stripped
@@ -174,6 +174,8 @@ noinst_HEADERS=		\
 			include/row0upd.ic	\
 			include/row0vers.h	\
 			include/row0vers.ic	\
+			include/srv0mon.h	\
+			include/srv0mon.ic	\
 			include/srv0srv.h	\
 			include/srv0srv.ic	\
 			include/srv0start.h	\
@@ -298,6 +300,7 @@ libinnobase_a_SOURCES=	\
 			row/row0undo.c			\
 			row/row0upd.c			\
 			row/row0vers.c			\
+			srv/srv0mon.c			\
 			srv/srv0srv.c			\
 			srv/srv0start.c			\
 			sync/sync0arr.c			\

=== modified file 'storage/innobase/btr/btr0btr.c'
--- a/storage/innobase/btr/btr0btr.c	revid:sunny.bains@stripped
+++ b/storage/innobase/btr/btr0btr.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1994, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -41,6 +41,7 @@ Created 6/2/1994 Heikki Tuuri
 #include "lock0lock.h"
 #include "ibuf0ibuf.h"
 #include "trx0trx.h"
+#include "srv0mon.h"
 
 /*
 Latching strategy of the InnoDB B-tree
@@ -2229,6 +2230,7 @@ func_exit:
 		buf_block_get_page_no(left_block),
 		buf_block_get_page_no(right_block));
 #endif
+	MONITOR_INC(MONITOR_INDEX_SPLIT);
 
 	ut_ad(page_validate(buf_block_get_frame(left_block), cursor->index));
 	ut_ad(page_validate(buf_block_get_frame(right_block), cursor->index));

=== modified file 'storage/innobase/buf/buf0flu.c'
--- a/storage/innobase/buf/buf0flu.c	revid:sunny.bains@stripped
+++ b/storage/innobase/buf/buf0flu.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -43,6 +43,7 @@ Created 11/11/1995 Heikki Tuuri
 #include "log0log.h"
 #include "os0file.h"
 #include "trx0sys.h"
+#include "srv0mon.h"
 
 /**********************************************************************
 These statistics are generated for heuristics used in estimating the
@@ -225,6 +226,8 @@ buf_flush_free_flush_rbt(void)
 
 		buf_flush_list_mutex_enter(buf_pool);
 
+	MONITOR_INC(MONITOR_PAGE_INFLUSH);
+
 #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
 		ut_a(buf_flush_validate_low(buf_pool));
 #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */
@@ -378,6 +381,8 @@ buf_flush_insert_sorted_into_flush_list(
 	ut_a(buf_flush_validate_low(buf_pool));
 #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */
 
+	MONITOR_DEC(MONITOR_PAGE_INFLUSH);
+
 	buf_flush_list_mutex_exit(buf_pool);
 }
 

=== modified file 'storage/innobase/dict/dict0dict.c'
--- a/storage/innobase/dict/dict0dict.c	revid:sunny.bains@stripped
+++ b/storage/innobase/dict/dict0dict.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1996, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -54,6 +54,7 @@ UNIV_INTERN dict_index_t*	dict_ind_compa
 #include "row0merge.h"
 #include "m_ctype.h" /* my_isspace() */
 #include "ha_prototypes.h" /* innobase_strcasecmp() */
+#include "srv0mon.h"
 
 #include <ctype.h>
 
@@ -311,6 +312,8 @@ dict_table_decrement_handle_count(
 
 	table->n_mysql_handles_opened--;
 
+	MONITOR_INC(MONITOR_TABLE_CLOSE);
+
 	if (!dict_locked) {
 		mutex_exit(&dict_sys->mutex);
 	}
@@ -712,6 +715,8 @@ dict_table_get(
 
 	if (inc_mysql_count && table) {
 		table->n_mysql_handles_opened++;
+
+		MONITOR_INC(MONITOR_TABLE_OPEN);
 	}
 
 	mutex_exit(&(dict_sys->mutex));

=== modified file 'storage/innobase/handler/ha_innodb.cc'
--- a/storage/innobase/handler/ha_innodb.cc	revid:sunny.bains@stripped
+++ b/storage/innobase/handler/ha_innodb.cc	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 2000, 2010, MySQL AB & Innobase Oy. All Rights Reserved.
+Copyright (c) 2000, 2010, Oracle and/or its affiliates. All Rights Reserved.
 Copyright (c) 2008, 2009 Google Inc.
 Copyright (c) 2009, Percona Inc.
 
@@ -87,6 +87,7 @@ extern "C" {
 #include "ha_prototypes.h"
 #include "ut0mem.h"
 #include "ibuf0ibuf.h"
+#include "srv0mon.h"
 }
 
 #include "ha_innodb.h"
@@ -148,6 +149,10 @@ static char*	innobase_data_file_path			=
 static char*	innobase_log_group_home_dir		= NULL;
 static char*	innobase_file_format_name		= NULL;
 static char*	innobase_change_buffering		= NULL;
+static char*	innobase_monitor_counter_on		= NULL;
+static char*	innobase_monitor_counter_off		= NULL;
+static char*	innobase_monitor_counter_reset		= NULL;
+static char*	innobase_monitor_counter_reset_all	= NULL;
 
 /* Note: This variable can be set to on/off and any of the supported
 file formats in the configuration file, but can only be set to any
@@ -2453,6 +2458,11 @@ innobase_change_buffering_inited_ok:
 	/* Get the current high water mark format. */
 	innobase_file_format_check = (char*) trx_sys_file_format_max_get();
 
+	/* Currently, monitor counter information are not persistent. */
+	memset(monitor_set_tbl, 0, sizeof monitor_set_tbl);
+
+	memset(innodb_counter_value, 0, sizeof innodb_counter_value);
+
 	DBUG_RETURN(FALSE);
 error:
 	DBUG_RETURN(TRUE);
@@ -10741,6 +10751,244 @@ innodb_change_buffering_update(
 		 *static_cast<const char*const*>(save);
 }
 
+/*************************************************************//**
+Validate the passed in monitor name, find and save the
+corresponding monitor id in the function parameter "save".
+@return	0 if monitor name is valid */
+static
+int
+innodb_monitor_valid_byname(
+/*========================*/
+	void*			save,	/*!< out: immediate result
+					for update function */
+	const char*		name)	/*!< in: incoming monitor name */
+{
+	if (name) {
+		ulint	use;
+
+		for (use = 0; use < NUM_MONITOR; use++) {
+			if (!innobase_strcasecmp(
+				name, srv_mon_get_name((monitor_id_t)use))) {
+				*(ulint*) save = use;
+				return(0);
+			}
+		}
+	}
+
+	return(1);
+}
+/*************************************************************//**
+Validate passed-in "value" is a valid monitor counter name.
+This function is registered as a callback with MySQL.
+@return	0 for valid name */
+static
+int
+innodb_monitor_validate(
+/*====================*/
+	THD*				thd,	/*!< in: thread handle */
+	struct st_mysql_sys_var*	var,	/*!< in: pointer to system
+						variable */
+	void*				save,	/*!< out: immediate result
+						for update function */
+	struct st_mysql_value*		value)	/*!< in: incoming string */
+{
+	const char*	monitor_name;
+	char		buff[STRING_BUFFER_USUAL_SIZE];
+	int		len = sizeof(buff);
+
+	ut_a(save != NULL);
+	ut_a(value != NULL);
+
+	monitor_name = value->val_str(value, buff, &len);
+
+	return(innodb_monitor_valid_byname(save, monitor_name));
+}
+
+/****************************************************************//**
+Update the system variable innodb_monitor_counter_* according to
+the "set_option" and turn on/off or reset specified monitor counter. */
+static
+void
+innodb_monitor_update(
+/*==================*/
+	THD*			thd,		/*!< in: thread handle */
+	void*			var_ptr,	/*!< out: where the
+						formal string goes */
+	const void*		save,		/*!< in: immediate result
+						from check function */
+	mon_option_t		set_option)	/*!< in: the set option,
+						whether to turn on/off or
+						reset the counter */
+{
+	monitor_info_t*	monitor_info;
+	monitor_id_t	monitor_id;
+	ulint		err_monitor = 0;
+
+	ut_a(var_ptr != NULL);
+	ut_a(save != NULL);
+	ut_a((*(monitor_id_t*) save) <= NUM_MONITOR);
+
+	monitor_id = *(const monitor_id_t*) save;
+
+	if (monitor_id == MONITOR_DEFAULT_START) {
+		/* If user set the variable to "default", we will
+		print a message and make this set operation a "noop".
+		The check is being made here is because "set default"
+		does not go through validation function */
+		push_warning_printf(thd,
+				    MYSQL_ERROR::WARN_LEVEL_WARN,
+				    ER_NO_DEFAULT,
+				    "Default value is not defined for "
+				    "this set option. Please specify "
+				    "counter or module name to turn on/off "
+				    "or reset monitor counters.");
+		*(const char**) var_ptr = NULL;
+	} else {
+		monitor_info = srv_mon_get_info(monitor_id);
+
+		ut_a(monitor_info);
+
+		/* If monitor is already truned on, someone could already
+		collect monitor data, exit and ask user to turn off the
+		monitor before turn it on again. */
+		if (set_option == MONITOR_TURN_ON
+		    && MONITOR_IS_ON(monitor_id)) {
+			err_monitor = monitor_id;
+			goto exit;
+		}
+
+		*(const char**) var_ptr = monitor_info->monitor_name;
+
+		/* Depending on the monitor name is for a module or
+		a counter, process counters in the whole module or
+		individual counter. */
+		if (monitor_info->monitor_type & MONITOR_MODULE) {
+			err_monitor = srv_mon_set_module_control(monitor_id,
+								 set_option);
+		} else {
+			switch (set_option) {
+			case MONITOR_TURN_ON:
+				MONITOR_ON(monitor_id);
+				MONITOR_INIT(monitor_id);
+				MONITOR_SET_START(monitor_id);
+
+				/* If the monitor to be turned on uses
+				exisitng monitor counter (status variable),
+				make special processing to remember existing
+				counter value. */
+				if (monitor_info->monitor_type
+				    & MONITOR_EXISTING) {
+					srv_mon_process_existing_counter(
+						monitor_id, MONITOR_TURN_ON);
+				}
+			break;
+
+			case MONITOR_TURN_OFF:
+				if (monitor_info->monitor_type
+				    & MONITOR_EXISTING) {
+					srv_mon_process_existing_counter(
+						monitor_id, MONITOR_TURN_OFF);
+				}
+				MONITOR_OFF(monitor_id);
+				MONITOR_SET_OFF(monitor_id);
+				break;
+
+			case MONITOR_RESET_VALUE:
+				srv_mon_reset(monitor_id);
+				break;
+
+			case MONITOR_RESET_ALL_VALUE:
+				srv_mon_reset_all(monitor_id);
+				break;
+
+			default:
+				ut_error;
+			}
+		}
+	}
+exit:
+	/* Only if we are trying to turn on a monitor that already
+	been turned on, we will set err_monitor. Print related
+	information */
+	if (err_monitor) {
+		sql_print_warning("Monitor %s already turned on.",
+				  srv_mon_get_name((monitor_id_t)err_monitor));
+	}
+
+	return;
+}
+/****************************************************************//**
+Update the system variable innodb_monitor_counter_on and turn on
+specified monitor counter.
+This function is registered as a callback with MySQL. */
+static
+void
+innodb_monitor_on_update(
+/*=====================*/
+	THD*				thd,	/*!< in: thread handle */
+	struct st_mysql_sys_var*	var,	/*!< in: pointer to
+						system variable */
+	void*				var_ptr,/*!< out: where the
+						formal string goes */
+	const void*			save)	/*!< in: immediate result
+						from check function */
+{
+	innodb_monitor_update(thd, var_ptr, save, MONITOR_TURN_ON);
+}
+/****************************************************************//**
+Update the system variable innodb_monitor_counter_off and turn
+off specified monitor counter. */
+static
+void
+innodb_monitor_off_update(
+/*======================*/
+	THD*				thd,	/*!< in: thread handle */
+	struct st_mysql_sys_var*	var,	/*!< in: pointer to
+						system variable */
+	void*				var_ptr,/*!< out: where the
+						formal string goes */
+	const void*			save)	/*!< in: immediate result
+						from check function */
+{
+	innodb_monitor_update(thd, var_ptr, save, MONITOR_TURN_OFF);
+}
+/****************************************************************//**
+Update the system variable innodb_monitor_counter_reset and reset
+specified monitor counter(s).
+This function is registered as a callback with MySQL. */
+static
+void
+innodb_monitor_reset_update(
+/*========================*/
+	THD*				thd,	/*!< in: thread handle */
+	struct st_mysql_sys_var*	var,	/*!< in: pointer to
+						system variable */
+	void*				var_ptr,/*!< out: where the
+						formal string goes */
+	const void*			save)	/*!< in: immediate result
+						from check function */
+{
+	innodb_monitor_update(thd, var_ptr, save, MONITOR_RESET_VALUE);
+}
+/****************************************************************//**
+Update the system variable innodb_monitor_counter_reset_all and reset
+all value related monitor counter.
+This function is registered as a callback with MySQL. */
+static
+void
+innodb_monitor_reset_all_update(
+/*============================*/
+	THD*				thd,	/*!< in: thread handle */
+	struct st_mysql_sys_var*	var,	/*!< in: pointer to
+						system variable */
+	void*				var_ptr,/*!< out: where the
+						formal string goes */
+	const void*			save)	/*!< in: immediate result
+						from check function */
+{
+	innodb_monitor_update(thd, var_ptr, save, MONITOR_RESET_ALL_VALUE);
+}
+
 static int show_innodb_vars(THD *thd, SHOW_VAR *var, char *buff)
 {
   innodb_export_status();
@@ -11101,6 +11349,30 @@ static MYSQL_SYSVAR_ULONG(read_ahead_thr
   "trigger a readahead.",
   NULL, NULL, 56, 0, 64, 0);
 
+static MYSQL_SYSVAR_STR(monitor_counter_on, innobase_monitor_counter_on,
+  PLUGIN_VAR_RQCMDARG,
+  "Turn on a monitor counter",
+  innodb_monitor_validate,
+  innodb_monitor_on_update, NULL);
+
+static MYSQL_SYSVAR_STR(monitor_counter_off, innobase_monitor_counter_off,
+  PLUGIN_VAR_RQCMDARG,
+  "Turn off a monitor counter",
+  innodb_monitor_validate,
+  innodb_monitor_off_update, NULL);
+
+static MYSQL_SYSVAR_STR(monitor_counter_reset, innobase_monitor_counter_reset,
+  PLUGIN_VAR_RQCMDARG,
+  "Reset a monitor counter",
+  innodb_monitor_validate,
+  innodb_monitor_reset_update, NULL);
+
+static MYSQL_SYSVAR_STR(monitor_counter_reset_all, innobase_monitor_counter_reset_all,
+  PLUGIN_VAR_RQCMDARG,
+  "Reset all values for a monitor counter",
+  innodb_monitor_validate,
+  innodb_monitor_reset_all_update, NULL);
+
 static struct st_mysql_sys_var* innobase_system_variables[]= {
   MYSQL_SYSVAR(additional_mem_pool_size),
   MYSQL_SYSVAR(autoextend_increment),
@@ -11159,6 +11431,10 @@ static struct st_mysql_sys_var* innobase
   MYSQL_SYSVAR(change_buffering),
   MYSQL_SYSVAR(read_ahead_threshold),
   MYSQL_SYSVAR(io_capacity),
+  MYSQL_SYSVAR(monitor_counter_on),
+  MYSQL_SYSVAR(monitor_counter_off),
+  MYSQL_SYSVAR(monitor_counter_reset),
+  MYSQL_SYSVAR(monitor_counter_reset_all),
   MYSQL_SYSVAR(purge_threads),
   MYSQL_SYSVAR(purge_batch_size),
   NULL
@@ -11192,7 +11468,8 @@ i_s_innodb_sys_indexes,
 i_s_innodb_sys_columns,
 i_s_innodb_sys_fields,
 i_s_innodb_sys_foreign,
-i_s_innodb_sys_foreign_cols
+i_s_innodb_sys_foreign_cols,
+i_s_innodb_metrics
 
 mysql_declare_plugin_end;
 

=== modified file 'storage/innobase/handler/handler0alter.cc'
--- a/storage/innobase/handler/handler0alter.cc	revid:sunny.bains@stripped
+++ b/storage/innobase/handler/handler0alter.cc	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 2005, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 2005, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -34,6 +34,7 @@ extern "C" {
 #include "trx0roll.h"
 #include "ha_prototypes.h"
 #include "handler0alter.h"
+#include "srv0mon.h"
 }
 
 #include "ha_innodb.h"
@@ -881,6 +882,8 @@ error_handling:
 
 		indexed_table->n_mysql_handles_opened++;
 
+		MONITOR_INC(MONITOR_TABLE_OPEN);
+
 		error = row_merge_drop_table(trx, innodb_table);
 		innodb_table = indexed_table;
 		goto convert_error;

=== modified file 'storage/innobase/handler/i_s.cc'
--- a/storage/innobase/handler/i_s.cc	revid:sunny.bains@stripped
+++ b/storage/innobase/handler/i_s.cc	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 2007, 2009, Innobase Oy. All Rights Reserved.
+Copyright (c) 2007, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -47,6 +47,7 @@ extern "C" {
 #include "srv0start.h" /* for srv_was_started */
 #include "trx0i_s.h"
 #include "trx0trx.h" /* for TRX_QUE_STATE_STR_MAX_LEN */
+#include "srv0mon.h"
 }
 
 static const char plugin_author[] = "Innobase Oy";
@@ -150,16 +151,20 @@ field_store_time_t(
 	MYSQL_TIME	my_time;
 	struct tm	tm_time;
 
+	if (time) {
 #if 0
-	/* use this if you are sure that `variables' and `time_zone'
-	are always initialized */
-	thd->variables.time_zone->gmt_sec_to_TIME(
-		&my_time, (my_time_t) time);
+		/* use this if you are sure that `variables' and `time_zone'
+		are always initialized */
+		thd->variables.time_zone->gmt_sec_to_TIME(
+			&my_time, (my_time_t) time);
 #else
-	localtime_r(&time, &tm_time);
-	localtime_to_TIME(&my_time, &tm_time);
-	my_time.time_type = MYSQL_TIMESTAMP_DATETIME;
+		localtime_r(&time, &tm_time);
+		localtime_to_TIME(&my_time, &tm_time);
+		my_time.time_type = MYSQL_TIMESTAMP_DATETIME;
 #endif
+	} else {
+		memset(&my_time, 0, sizeof(my_time));
+	}
 
 	return(field->store_time(&my_time, MYSQL_TIMESTAMP_DATETIME));
 }
@@ -1894,6 +1899,438 @@ UNIV_INTERN struct st_mysql_plugin	i_s_i
 	STRUCT_FLD(__reserved1, NULL)
 };
 
+/* Fields of the dynamic table INFORMATION_SCHEMA.innodb_metrics */
+static ST_FIELD_INFO	innodb_metrics_fields_info[] =
+{
+#define	METRIC_NAME		0
+	{STRUCT_FLD(field_name,		"name"),
+	 STRUCT_FLD(field_length,	NAME_LEN + 1),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_STRING),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_SUBSYS		1
+	{STRUCT_FLD(field_name,		"subsystem"),
+	 STRUCT_FLD(field_length,	NAME_LEN + 1),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_STRING),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_VALUE_START	2
+	{STRUCT_FLD(field_name,		"value_since_start"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_MAX_VALUE_START	3
+	{STRUCT_FLD(field_name,		"max_since_start"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_MIN_VALUE_START	4
+	{STRUCT_FLD(field_name,		"min_since_start"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_AVG_VALUE_START	5
+	{STRUCT_FLD(field_name,		"avg_since_start"),
+	 STRUCT_FLD(field_length,	0),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_FLOAT),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_VALUE_RESET	6
+	{STRUCT_FLD(field_name,		"value_since_reset"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_MAX_VALUE_RESET	7
+	{STRUCT_FLD(field_name,		"max_since_reset"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_MIN_VALUE_RESET	8
+	{STRUCT_FLD(field_name,		"min_since_reset"),
+	 STRUCT_FLD(field_length,	MY_INT64_NUM_DECIMAL_DIGITS),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_LONGLONG),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_AVG_VALUE_RESET	9
+	{STRUCT_FLD(field_name,		"avg_since_reset"),
+	 STRUCT_FLD(field_length,	0),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_FLOAT),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_START_TIME	10
+	{STRUCT_FLD(field_name,		"start_time"),
+	 STRUCT_FLD(field_length,	0),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_DATETIME),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_STOP_TIME	11
+	{STRUCT_FLD(field_name,		"stop_time"),
+	 STRUCT_FLD(field_length,	0),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_DATETIME),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_RESET_TIME	12
+	{STRUCT_FLD(field_name,		"reset_time"),
+	 STRUCT_FLD(field_length,	0),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_DATETIME),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	MY_I_S_MAYBE_NULL),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_STATUS		13
+	{STRUCT_FLD(field_name,		"status"),
+	 STRUCT_FLD(field_length,	NAME_LEN + 1),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_STRING),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_TYPE		14
+	{STRUCT_FLD(field_name,		"type"),
+	 STRUCT_FLD(field_length,	NAME_LEN + 1),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_STRING),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+#define	METRIC_DESC		15
+	{STRUCT_FLD(field_name,		"description"),
+	 STRUCT_FLD(field_length,	NAME_LEN + 1),
+	 STRUCT_FLD(field_type,		MYSQL_TYPE_STRING),
+	 STRUCT_FLD(value,		0),
+	 STRUCT_FLD(field_flags,	0),
+	 STRUCT_FLD(old_name,		""),
+	 STRUCT_FLD(open_method,	SKIP_OPEN_TABLE)},
+
+	END_OF_ST_FIELD_INFO
+};
+
+/**********************************************************************//**
+Fill the information schema metrics table.
+@return	0 on success */
+static
+int
+i_s_metrics_fill(
+/*=============*/
+	THD*		thd,		/*!< in: thread */
+	TABLE*		table_to_fill)  /*!< in/out: fill this table */
+{
+	int		count;
+	Field**		fields;
+	double		time_diff;
+	monitor_info_t*	monitor_info;
+	lint		min_val;
+	lint		max_val;
+
+	DBUG_ENTER("i_s_metrics_fill");
+	fields = table_to_fill->field;
+
+	for (count = 0; count < NUM_MONITOR; count++) {
+		monitor_info = srv_mon_get_info((monitor_id_t)count);
+
+		/* A good place to sanity check the Monitor ID */
+		ut_a(count == monitor_info->monitor_id);
+
+		/* If the item refers to a Module, nothing to fill,
+		continue. */
+		if (monitor_info->monitor_type & MONITOR_MODULE) {
+			continue;
+		}
+
+		/* If this is an existing "status variable", and
+		its corresponding counter is still on, we need
+		to calculate the result from its corresponding
+		counter. */
+		if (monitor_info->monitor_type & MONITOR_EXISTING
+		    && MONITOR_IS_ON(count)) {
+			srv_mon_process_existing_counter((monitor_id_t)count,
+							 MONITOR_GET_VALUE);
+		}
+
+		/* Fill in counter's basic information */
+		OK(field_store_string(fields[METRIC_NAME],
+				      monitor_info->monitor_name));
+
+		OK(field_store_string(fields[METRIC_SUBSYS],
+				      monitor_info->monitor_module));
+
+		OK(field_store_string(fields[METRIC_DESC],
+				      monitor_info->monitor_desc));
+
+		/* Fill in counter values */
+		OK(fields[METRIC_VALUE_RESET]->store(MONITOR_VALUE(count)));
+
+		OK(fields[METRIC_VALUE_START]->store(
+			MONITOR_VALUE_SINCE_START(count)));
+
+		/* If the max value is MAX_RESERVED, counter max
+		value has not been updated. Set the column value
+		to NULL. */
+		if (MONITOR_MAX_VALUE(count) == MAX_RESERVED
+		    || MONITOR_MAX_MIN_NOT_INIT(count)) {
+			fields[METRIC_MAX_VALUE_RESET]->set_null();
+		} else {
+			OK(fields[METRIC_MAX_VALUE_RESET]->store(
+				MONITOR_MAX_VALUE(count)));
+			fields[METRIC_MAX_VALUE_RESET]->set_notnull();
+		}
+
+		/* If the min value is MAX_RESERVED, counter min
+		value has not been updated. Set the column value
+		to NULL. */
+		if (MONITOR_MIN_VALUE(count) == MIN_RESERVED
+		    || MONITOR_MAX_MIN_NOT_INIT(count)) {
+			fields[METRIC_MIN_VALUE_RESET]->set_null();
+		} else {
+			OK(fields[METRIC_MIN_VALUE_RESET]->store(
+				MONITOR_MIN_VALUE(count)));
+			fields[METRIC_MIN_VALUE_RESET]->set_notnull();
+		}
+
+		/* Calculate the max value since counter started */
+		max_val = srv_mon_calc_max_since_start((monitor_id_t)count);
+
+		if (max_val == MAX_RESERVED
+		    || MONITOR_MAX_MIN_NOT_INIT(count)) {
+			fields[METRIC_MAX_VALUE_START]->set_null();
+		} else {
+			OK(fields[METRIC_MAX_VALUE_START]->store(max_val));
+			fields[METRIC_MAX_VALUE_START]->set_notnull();
+		}
+
+		/* Calculate the min value since counter started */
+		min_val = srv_mon_calc_min_since_start((monitor_id_t)count);
+
+		if (min_val == MIN_RESERVED
+		    || MONITOR_MAX_MIN_NOT_INIT(count)) {
+			fields[METRIC_MIN_VALUE_START]->set_null();
+		} else {
+			OK(fields[METRIC_MIN_VALUE_START]->store(min_val));
+			fields[METRIC_MIN_VALUE_START]->set_notnull();
+		}
+
+		if (monitor_info->monitor_type & MONITOR_AVERAGE) {
+			if (MONITOR_IS_ON(count)) {
+				time_diff = difftime(time(NULL),
+					MONITOR_FIELD(count, mon_start_time));
+			} else {
+				time_diff =  difftime(
+					MONITOR_FIELD(count, mon_stop_time),
+					MONITOR_FIELD(count, mon_start_time));
+			}
+
+			if (time_diff) {
+				OK(fields[METRIC_AVG_VALUE_START]->store(
+					MONITOR_VALUE_SINCE_START(count)
+					/ time_diff));
+				fields[METRIC_AVG_VALUE_START]->set_notnull();
+
+				OK(fields[METRIC_AVG_VALUE_RESET]->store(
+					MONITOR_VALUE(count) / time_diff));
+
+				fields[METRIC_AVG_VALUE_RESET]->set_notnull();
+			} else {
+				fields[METRIC_AVG_VALUE_START]->set_null();
+				fields[METRIC_AVG_VALUE_RESET]->set_null();
+			}
+		} else {
+			fields[METRIC_AVG_VALUE_START]->set_null();
+			fields[METRIC_AVG_VALUE_RESET]->set_null();
+		}
+
+		if (MONITOR_FIELD(count, mon_start_time)) {
+			OK(field_store_time_t(fields[METRIC_START_TIME],
+				(time_t)MONITOR_FIELD(count, mon_start_time)));
+			fields[METRIC_START_TIME]->set_notnull();
+		} else {
+			fields[METRIC_START_TIME]->set_null();
+		}
+
+		if (MONITOR_IS_ON(count)) {
+			/* If monitor is on, the stop time will set to NULL */
+			fields[METRIC_STOP_TIME]->set_null();
+
+			/* Display latest Monitor Reset Time only if Monitor
+			counter is on. */
+			if (MONITOR_FIELD(count, mon_reset_time)) {
+				OK(field_store_time_t(
+					fields[METRIC_RESET_TIME],
+					(time_t)MONITOR_FIELD(
+						count, mon_reset_time)));
+				fields[METRIC_RESET_TIME]->set_notnull();
+			} else {
+				fields[METRIC_RESET_TIME]->set_null();
+			}
+
+			/* Display the monitor status to be "started" */
+			OK(field_store_string(fields[METRIC_STATUS],
+					      "started"));
+		} else {
+			if (MONITOR_FIELD(count, mon_stop_time)) {
+				OK(field_store_time_t(fields[METRIC_STOP_TIME],
+				(time_t)MONITOR_FIELD(count, mon_stop_time)));
+				fields[METRIC_STOP_TIME]->set_notnull();
+			} else {
+				fields[METRIC_STOP_TIME]->set_null();
+			}
+
+			fields[METRIC_RESET_TIME]->set_null();
+
+			OK(field_store_string(fields[METRIC_STATUS],
+					      "stopped"));
+		}
+
+		if (monitor_info->monitor_type & MONITOR_DISPLAY_CURRENT) {
+			OK(field_store_string(fields[METRIC_TYPE],
+					      "current_value"));
+		} else {
+			OK(field_store_string(fields[METRIC_TYPE],
+					      "counter_value"));
+		}
+
+		OK(schema_table_store_record(thd, table_to_fill));
+	}
+
+	DBUG_RETURN(0);
+}
+
+/*******************************************************************//**
+Function to fill information schema metrics tables.
+@return	0 on success */
+static
+int
+i_s_metrics_fill_table(
+/*===================*/
+	THD*		thd,    /*!< in: thread */
+	TABLE_LIST*	tables, /*!< in/out: tables to fill */
+	COND*		cond)   /*!< in: condition (not used) */
+{
+	DBUG_ENTER("i_s_metrics_fill_table");
+
+	/* deny access to non-superusers */
+	if (check_global_access(thd, PROCESS_ACL)) {
+
+                DBUG_RETURN(0);
+	}
+
+	i_s_metrics_fill(thd, tables->table);
+
+	DBUG_RETURN(0);
+}
+/*******************************************************************//**
+Bind the dynamic table INFORMATION_SCHEMA.innodb_metrics
+@return	0 on success */
+static
+int
+innodb_metrics_init(
+/*================*/
+	void*	p)	/*!< in/out: table schema object */
+{
+	ST_SCHEMA_TABLE*	schema;
+
+	DBUG_ENTER("innodb_metrics_init");
+
+	schema = (ST_SCHEMA_TABLE*) p;
+
+	schema->fields_info = innodb_metrics_fields_info;
+	schema->fill_table = i_s_metrics_fill_table;
+
+	DBUG_RETURN(0);
+}
+
+UNIV_INTERN struct st_mysql_plugin	i_s_innodb_metrics =
+{
+	/* the plugin type (a MYSQL_XXX_PLUGIN value) */
+	/* int */
+	STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN),
+
+	/* pointer to type-specific plugin descriptor */
+	/* void* */
+	STRUCT_FLD(info, &i_s_info),
+
+	/* plugin name */
+	/* const char* */
+	STRUCT_FLD(name, "INNODB_METRICS"),
+
+	/* plugin author (for SHOW PLUGINS) */
+	/* const char* */
+	STRUCT_FLD(author, "Oracle and/or its affiliates."),
+
+	/* general descriptive text (for SHOW PLUGINS) */
+	/* const char* */
+	STRUCT_FLD(descr, "InnoDB Metrics Info"),
+
+	/* the plugin license (PLUGIN_LICENSE_XXX) */
+	/* int */
+	STRUCT_FLD(license, PLUGIN_LICENSE_GPL),
+
+	/* the function to invoke when plugin is loaded */
+	/* int (*)(void*); */
+	STRUCT_FLD(init, innodb_metrics_init),
+
+	/* the function to invoke when plugin is unloaded */
+	/* int (*)(void*); */
+	STRUCT_FLD(deinit, i_s_common_deinit),
+
+	/* plugin version (for SHOW PLUGINS) */
+	/* unsigned int */
+	STRUCT_FLD(version, INNODB_VERSION_SHORT),
+
+	/* struct st_mysql_show_var* */
+	STRUCT_FLD(status_vars, NULL),
+
+	/* struct st_mysql_sys_var** */
+	STRUCT_FLD(system_vars, NULL),
+
+	/* reserved for dependency checking */
+	/* void* */
+	STRUCT_FLD(__reserved1, NULL)
+};
+
 /*******************************************************************//**
 Unbind a dynamic INFORMATION_SCHEMA table.
 @return	0 on success */

=== modified file 'storage/innobase/handler/i_s.h'
--- a/storage/innobase/handler/i_s.h	revid:sunny.bains@stripped
+++ b/storage/innobase/handler/i_s.h	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 2007, 2009, Innobase Oy. All Rights Reserved.
+Copyright (c) 2007, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -40,5 +40,6 @@ extern struct st_mysql_plugin   i_s_inno
 extern struct st_mysql_plugin   i_s_innodb_sys_fields;
 extern struct st_mysql_plugin   i_s_innodb_sys_foreign;
 extern struct st_mysql_plugin   i_s_innodb_sys_foreign_cols;
+extern struct st_mysql_plugin   i_s_innodb_metrics;
 
 #endif /* i_s_h */

=== added file 'storage/innobase/include/srv0mon.h'
--- a/storage/innobase/include/srv0mon.h	1970-01-01 00:00:00 +0000
+++ b/storage/innobase/include/srv0mon.h	revid:sunny.bains@stripped
@@ -0,0 +1,529 @@
+/***********************************************************************
+
+Copyright (c) 2010, Oracle and/or its affiliates. All Rights Reserved.
+
+This program is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; version 2 of the License.
+
+This program is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
+Public License for more details.
+
+You should have received a copy of the GNU General Public License along
+with this program; if not, write to the Free Software Foundation, Inc.,
+59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+
+***********************************************************************/
+
+/**************************************************//**
+@file include/srv0mon.h
+Server monitor counter related defines
+
+Created 12/15/2009	Jimmy Yang
+*******************************************************/
+
+#ifndef srv0mon_h
+#define srv0mon_h
+
+#include "univ.i"
+
+
+/** Possible status values for "mon_status" in "struct monitor_value" */
+enum monitor_running_status {
+	MONITOR_STARTED = 1,	/*!< Monitor has been turned on */
+	MONITOR_STOPPED = 2	/*!< Monitor has been turned off */
+};
+
+typedef enum monitor_running_status	monitor_running_t;
+
+/** Two monitor structures are defined in this file. One is
+"monitor_value_t" which contains dynamic counter values for each
+counter. The other is "monitor_info_t", which contains
+static information (counter name, desc etc.) for each counter.
+In addition, an enum datatype "monitor_id_t" is also defined,
+it identifies each monitor with an internally used symbol, whose
+integer value indexes into above two structure for its dynamic
+and static information.
+Developer who intend to add new counters would require to
+fill in counter information as described in "monitor_info_t" and
+create the internal counter ID in "monitor_id_t". */
+
+/** Structure containing the actual values of a monitor counter. */
+struct monitor_value_struct {
+	ib_time_t	mon_start_time;	/*!< Start time of monitoring  */
+	ib_time_t	mon_stop_time;	/*!< Stop time of monitoring */
+	ib_time_t	mon_reset_time;	/*!< Time counter resetted */
+	lint		mon_value;	/*!< Current counter Value */
+	lint		mon_max_value;	/*!< Current Max value */
+	lint		mon_min_value;	/*!< Current Min value */
+	lint		mon_value_reset;/*!< value at last reset */
+	lint		mon_max_value_start; /*!< Max value since start */
+	lint		mon_min_value_start; /*!< Min value since start */
+	lint		mon_start_value;/*!< Value at the start time */
+	lint		mon_last_value;	/*!< Last set of values */
+	monitor_running_t mon_status;	/* whether monitor still running */
+};
+
+typedef struct monitor_value_struct	monitor_value_t;
+
+/** Follwoing defines are possible values for "monitor_type" field in
+"struct monitor_info" */
+enum monitor_type_value {
+	MONITOR_MODULE = 1,	/*!< This is a monitor module type,
+				not a counter */
+	MONITOR_EXISTING = 2,	/*!< The monitor carries information from
+				an existing system status variable */
+	MONITOR_AVERAGE = 4,	/*!< Set this status if we want to
+				calculate the average value (over time)
+				for the counter. */
+	MONITOR_DISPLAY_CURRENT = 8 /*!< Display current value of the
+				counter, rather than incremental value
+				over the period. Mostly for counters
+				displaying current resource usage */
+};
+
+typedef enum monitor_type_value	monitor_type_t;
+
+/** Counter minimum value is initialized to be max value of lint */
+#define	MIN_RESERVED		((lint)(ULINT_MAX >> 1))
+#define	MAX_RESERVED		(~MIN_RESERVED)
+
+/** This enumeration defines internal monitor identifier used internally
+to identify each particular counter. Its value indexes into two arrays,
+one is the "innodb_counter_value" array which records actual monitor
+counter values, the other is "innodb_counter_info" array which describes
+each counter's basic information (name, desc etc.). A couple of
+naming rules here:
+1) If the monitor defines a module, it starts with MONITOR_MODULE
+2) If the monitor uses exisitng counters from "status variable", its ID
+name shall start with MONITOR_OVLD
+
+Please refer to "innodb_counter_info" in srv/srv0mon.c for detail
+information for each monitor counter */
+
+enum monitor_id_value {
+	/* This is to identify the default value set by the metrics
+	control global variables */
+	MONITOR_DEFAULT_START = 0,
+
+	/* Start of Metadata counter */
+	MONITOR_MODULE_METADATA,
+	MONITOR_TABLE_OPEN,
+	MONITOR_TABLE_CLOSE,
+
+	/* Lock manager related counters */
+	MONITOR_MODULE_LOCK,
+	MONITOR_DEADLOCK,
+	MONITOR_TIMEOUT,
+	MONITOR_LOCKREC_WAIT,
+	MONITOR_NUM_RECLOCK_REQ,
+	MONITOR_RECLOCK_CREATED,
+	MONITOR_RECLOCK_REMOVED,
+	MONITOR_NUM_RECLOCK,
+	MONITOR_TABLELOCK_CREATED,
+	MONITOR_TABLELOCK_REMOVED,
+	MONITOR_NUM_TABLELOCK,
+	MONITOR_ROW_LOCK_CURRENT_WAIT,
+	MONITOR_LOCK_WAIT_TIME,
+	MONITOR_OVLD_ROW_LOCK_WAIT,
+
+	/* Buffer and I/O realted counters. */
+	MONITOR_MODULE_BUFFER,
+	MONITOR_OVLD_BUF_POOL_READS,
+	MONITOR_OVLD_BUF_POOL_READ_REQUESTS,
+	MONITOR_OVLD_BUF_POOL_WRITE_REQUEST,
+	MONITOR_PAGE_INFLUSH,
+	MONITOR_OVLD_BUF_POOL_WAIT_FREE,
+	MONITOR_OVLD_BUF_POOL_READ_AHEAD,
+	MONITOR_OVLD_BUF_POOL_READ_AHEAD_EVICTED,
+	MONITOR_OVLD_BUF_POOL_PAGE_TOTAL,
+	MONITOR_OVLD_BUF_POOL_PAGE_MISC,
+	MONITOR_OVLD_BUF_POOL_PAGES_DATA,
+	MONITOR_OVLD_BUF_POOL_PAGES_DIRTY,
+	MONITOR_OVLD_BUF_POOL_PAGES_FREE,
+	MONITOR_OVLD_PAGE_CREATED,
+	MONITOR_OVLD_PAGES_WRITTEN,
+	MONITOR_OVLD_PAGES_READ,
+	MONITOR_OVLD_BYTE_READ,
+	MONITOR_OVLD_BYTE_WRITTEN,
+
+	/* OS level counters (I/O) */
+	MONITOR_MODULE_OS,
+	MONITOR_OVLD_OS_FILE_READ,
+	MONITOR_OVLD_OS_FILE_WRITE,
+	MONITOR_OVLD_OS_FSYNC,
+	MONITOR_OS_PENDING_READS,
+	MONITOR_OS_PENDING_WRITES,
+	MONITOR_OVLD_OS_LOG_WRITTEN,
+	MONITOR_OVLD_OS_LOG_FSYNC,
+	MONITOR_OVLD_OS_LOG_PENDING_FSYNC,
+	MONITOR_OVLD_OS_LOG_PENDING_WRITES,
+
+	/* Transaction related counters */
+	MONITOR_MODULE_TRX,
+	MONITOR_TRX_COMMIT,
+	MONITOR_TRX_ABORT,
+	MONITOR_TRX_ACTIVE,
+	MONITOR_NUM_ROW_PURGE,
+	MONITOR_DML_PURGE_DELAY,
+	MONITOR_RSEG_HISTORY_LEN,
+
+	/* Recovery related counters */
+	MONITOR_MODULE_RECOVERY,
+	MONITOR_NUM_CHECKPOINT,
+	MONITOR_LSN_FLUSHDISK,
+	MONITOR_LSN_CHECKPOINT,
+	MONITOR_LSN_CURRENT,
+	MONITOR_PENDING_LOG_WRITE,
+	MONITOR_PENDING_CHECKPOINT_WRITE,
+	MONITOR_LOG_IO,
+	MONITOR_OVLD_LOG_WAITS,
+	MONITOR_OVLD_LOG_WRITE_REQUEST,
+	MONITOR_OVLD_LOG_WRITES,
+	MONITOR_FLUSH_IO_CAPACITY,
+	MONITOR_FLUSH_DIRTY_PAGE_EXCEED,
+
+	/* Page Manager related counters */
+	MONITOR_MODULE_PAGE,
+	MONITOR_PAGE_COMPRESS,
+	MONITOR_PAGE_DECOMPRESS,
+
+	/* Index related counters */
+	MONITOR_MODULE_INDEX,
+	MONITOR_INDEX_SPLIT,
+	MONITOR_INDEX_MERGE,
+
+	/* Data DML related counters */
+	MONITOR_MODULE_DMLSTATS,
+	MONITOR_OLVD_ROW_READ,
+	MONITOR_OLVD_ROW_INSERTED,
+	MONITOR_OLVD_ROW_DELETED,
+	MONITOR_OLVD_ROW_UPDTATED,
+
+	/* This is used only for control system to turn
+	on/off and reset all monitor counters */
+	MONITOR_ALL_COUNTER,
+
+	/* This must be the last member */
+	NUM_MONITOR
+};
+
+typedef enum monitor_id_value		monitor_id_t;
+
+/** struct monitor_info describes the basic/static information
+about each monitor counter. */
+struct monitor_info_struct {
+	const char*	monitor_name;	/*!< Monitor name */
+	const char*	monitor_module;	/*!< Sub Module the monitor
+					belongs to */
+	const char*	monitor_desc;	/*!< Brief desc of monitor counter */
+	monitor_type_t	monitor_type;	/*!< Type of Monitor Info */
+	monitor_id_t	monitor_id;	/*!< Monitor ID as defined in enum
+					monitor_id_t */
+};
+
+typedef struct monitor_info_struct	monitor_info_t;
+
+/** Following are the "set_option" values allowed for
+srv_mon_process_existing_counter() and srv_mon_process_existing_counter()
+functions. To turn on/off/reset the monitor counters. */
+enum mon_set_option {
+	MONITOR_TURN_ON = 1,		/*!< Turn on the counter */
+	MONITOR_TURN_OFF,		/*!< Turn off the counter */
+	MONITOR_RESET_VALUE,		/*!< Reset current values */
+	MONITOR_RESET_ALL_VALUE,	/*!< Reset all values */
+	MONITOR_GET_VALUE		/*!< Option for
+					srv_mon_process_existing_counter()
+					function */
+};
+
+typedef enum mon_set_option		mon_option_t;
+
+/** Number of bit in a ulint datatype */
+#define	NUM_BITS_ULINT	(sizeof(ulint) * CHAR_BIT)
+
+/** This "monitor_set_tbl" is a bitmap records whether a particular monitor
+counter has been turned on or off */
+extern ulint		monitor_set_tbl[(NUM_MONITOR + NUM_BITS_ULINT - 1) /
+					NUM_BITS_ULINT];
+
+/** Macros to turn on/off the control bit in monitor_set_tbl for a monitor
+counter option. */
+#define MONITOR_ON(monitor)				\
+	(monitor_set_tbl[monitor / NUM_BITS_ULINT] |=	\
+			((ulint)1 << (monitor % NUM_BITS_ULINT)))
+
+#define MONITOR_OFF(monitor)				\
+	(monitor_set_tbl[monitor / NUM_BITS_ULINT] &=	\
+			~((ulint)1 << (monitor % NUM_BITS_ULINT)))
+
+/** Check whether the requested monitor is turned on/off */
+#define MONITOR_IS_ON(monitor)				\
+	(monitor_set_tbl[monitor / NUM_BITS_ULINT] &	\
+			((ulint)1 << (monitor % NUM_BITS_ULINT)))
+
+/** The actual monitor counter array that records each monintor counter
+value */
+extern monitor_value_t	 innodb_counter_value[NUM_MONITOR];
+
+/** Following are macro defines for basic montior counter manipulations.
+Please note we do not provide any synchronization for these monitor
+operations due to performance consideration. Most counters can
+be placed under existing mutex protections in respective code
+module. */
+
+/** Macros to access various fields of a monitor counters */
+#define MONITOR_FIELD(monitor, field)			\
+		(innodb_counter_value[monitor].field)
+
+#define MONITOR_VALUE(monitor)				\
+		MONITOR_FIELD(monitor, mon_value)
+
+#define MONITOR_MAX_VALUE(monitor)			\
+		MONITOR_FIELD(monitor, mon_max_value)
+
+#define MONITOR_MIN_VALUE(monitor)			\
+		MONITOR_FIELD(monitor, mon_min_value)
+
+#define MONITOR_VALUE_RESET(monitor)			\
+		MONITOR_FIELD(monitor, mon_value_reset)
+
+#define MONITOR_MAX_VALUE_START(monitor)		\
+		MONITOR_FIELD(monitor, mon_max_value_start)
+
+#define MONITOR_MIN_VALUE_START(monitor)		\
+		MONITOR_FIELD(monitor, mon_min_value_start)
+
+#define MONITOR_LAST_VALUE(monitor)			\
+		MONITOR_FIELD(monitor, mon_last_value)
+
+#define MONITOR_START_VALUE(monitor)			\
+		MONITOR_FIELD(monitor, mon_start_value)
+
+#define MONITOR_VALUE_SINCE_START(monitor)		\
+		(MONITOR_VALUE(monitor) + MONITOR_VALUE_RESET(monitor))
+
+#define MONITOR_STATUS(monitor)				\
+		MONITOR_FIELD(monitor, mon_status)
+
+#define MONITOR_SET_START(monitor)					\
+	do {								\
+		MONITOR_STATUS(monitor) = MONITOR_STARTED;		\
+		MONITOR_FIELD((monitor), mon_start_time) = time(NULL);	\
+	} while (0)
+
+#define MONITOR_SET_OFF(monitor)					\
+	do {								\
+		MONITOR_STATUS(monitor) = MONITOR_STOPPED;		\
+		MONITOR_FIELD((monitor), mon_stop_time) = time(NULL);	\
+	} while (0)
+
+#ifdef HAVE_ATOMIC_BUILTINS
+#define INC_VALUE(value, amount)					\
+		(value = os_atomic_increment_lint(&value, amount))
+#else
+#define INC_VALUE(value, amount)	((value) += (amount))
+#endif /* HAVE_ATOMIC_BUILTINS */
+
+#define	MONITOR_INIT_ZERO_VALUE		0
+
+/** Max and min values are initialized when we first turn on the monitor
+counter, and set the MONITOR_STATUS. */
+#define MONITOR_MAX_MIN_NOT_INIT(monitor)				\
+		(MONITOR_STATUS(monitor) == MONITOR_INIT_ZERO_VALUE	\
+		 && MONITOR_MIN_VALUE(monitor) == MONITOR_INIT_ZERO_VALUE \
+		 && MONITOR_MAX_VALUE(monitor) == MONITOR_INIT_ZERO_VALUE)
+
+#define MONITOR_INIT(monitor)						\
+	if (MONITOR_MAX_MIN_NOT_INIT(monitor)) {			\
+		MONITOR_MIN_VALUE(monitor) = MIN_RESERVED;		\
+		MONITOR_MIN_VALUE_START(monitor) = MIN_RESERVED;	\
+		MONITOR_MAX_VALUE(monitor) = MAX_RESERVED;		\
+		MONITOR_MAX_VALUE_START(monitor) = MAX_RESERVED;	\
+	}
+
+/** Macros to increment/decrement the counters. The normal
+monitor counter operation expects appropriate synchronization
+already exists. No additional mutex is necessary when operating
+on the counters */
+#define	MONITOR_INC(monitor)						\
+	if (MONITOR_IS_ON(monitor)) {					\
+		INC_VALUE(MONITOR_VALUE(monitor), 1);			\
+		if (MONITOR_VALUE(monitor) > MONITOR_MAX_VALUE(monitor)) {  \
+			MONITOR_MAX_VALUE(monitor) = MONITOR_VALUE(monitor);\
+		}							\
+	}
+
+#define	MONITOR_DEC(monitor)						\
+	if (MONITOR_IS_ON(monitor)) {					\
+		INC_VALUE(MONITOR_VALUE(monitor), -1);			\
+		if (MONITOR_VALUE(monitor) < MONITOR_MIN_VALUE(monitor)) {  \
+			MONITOR_MIN_VALUE(monitor) = MONITOR_VALUE(monitor);\
+		}							\
+	}
+
+/** Directly set a monitor counter's value */
+#define	MONITOR_SET(monitor, value)					\
+	if (MONITOR_IS_ON(monitor)) {					\
+		MONITOR_VALUE(monitor) = (value);			\
+		if (MONITOR_VALUE(monitor) > MONITOR_MAX_VALUE(monitor)) {  \
+			MONITOR_MAX_VALUE(monitor) = MONITOR_VALUE(monitor);\
+		}							\
+		if (MONITOR_VALUE(monitor) < MONITOR_MIN_VALUE(monitor)) {  \
+			MONITOR_MIN_VALUE(monitor) = MONITOR_VALUE(monitor);\
+		}							\
+	}
+
+/** Directly set a monitor counter's value, and if the value
+is monotonically increasing, only max value needs to be updated */
+#define	MONITOR_SET_UPD_MAX_ONLY(monitor, value)			\
+	if (MONITOR_IS_ON(monitor)) {					\
+		MONITOR_VALUE(monitor) = (value);			\
+		if (MONITOR_VALUE(monitor) > MONITOR_MAX_VALUE(monitor)) {  \
+			MONITOR_MAX_VALUE(monitor) = MONITOR_VALUE(monitor);\
+		}							\
+	}
+
+/** Some values such as log sequence number are montomically increasing
+number, do not need to record max/min values */
+#define MONITOR_SET_SIMPLE(monitor, value)				\
+	if (MONITOR_IS_ON(monitor)) {					\
+		MONITOR_VALUE(monitor) = (lint)(value);			\
+	}
+
+/** Reset the monitor value and max/min value to zero. The reset
+operation would only be conducted when the counter is turned off */
+#define MONITOR_RESET_ALL(monitor)					\
+	do {								\
+		MONITOR_VALUE(monitor) = MONITOR_INIT_ZERO_VALUE;	\
+		MONITOR_MAX_VALUE(monitor) = MAX_RESERVED;		\
+		MONITOR_MIN_VALUE(monitor) = MIN_RESERVED;		\
+		MONITOR_VALUE_RESET(monitor) = MONITOR_INIT_ZERO_VALUE;	\
+		MONITOR_MAX_VALUE_START(monitor) = MAX_RESERVED;	\
+		MONITOR_MIN_VALUE_START(monitor) = MIN_RESERVED;	\
+		MONITOR_LAST_VALUE(monitor) = MONITOR_INIT_ZERO_VALUE;	\
+		MONITOR_FIELD(monitor, mon_start_time) =		\
+					MONITOR_INIT_ZERO_VALUE;	\
+		MONITOR_FIELD(monitor, mon_stop_time) =			\
+					MONITOR_INIT_ZERO_VALUE;	\
+	} while (0)
+
+/** Following four macros defines necessary operations to fetch and
+consolidate information from existing system status variables. */
+
+/** Save the passed-in value to mon_start_value field of monitor
+counters */
+#define MONITOR_SAVE_START(monitor, value)				\
+	(MONITOR_START_VALUE(monitor) =					\
+		 (value) - MONITOR_VALUE_RESET(monitor))
+
+/** Save the passed-in value to mon_last_value field of monitor
+counters */
+#define MONITOR_SAVE_LAST(monitor)					\
+	do {								\
+		MONITOR_LAST_VALUE(monitor) = MONITOR_VALUE(monitor);	\
+		MONITOR_START_VALUE(monitor) += MONITOR_VALUE(monitor);	\
+	} while (0)
+
+/** Set monitor value to the difference of value and mon_start_value
+compensated by mon_last_value if accumulated value is required. */
+#define MONITOR_SET_DIFF(monitor, value)				\
+	MONITOR_SET_UPD_MAX_ONLY(monitor, ((value)			\
+	- MONITOR_VALUE_RESET(monitor)					\
+	- MONITOR_FIELD(monitor, mon_start_value)			\
+	+ MONITOR_FIELD(monitor, mon_last_value)))
+
+/****************************************************************//**
+Get monitor's monitor_info_t by its monitor id (index into the
+innodb_counter_info array
+@return	Point to corresponding monitor_info_t, or NULL if no such
+monitor */
+UNIV_INTERN
+monitor_info_t*
+srv_mon_get_info(
+/*=============*/
+	monitor_id_t	monitor_id);	/*!< id index into the
+					innodb_counter_info array */
+/****************************************************************//**
+Get monitor's name by its monitor id (index into the
+innodb_counter_info array
+@return	corresponding monitor name, or NULL if no such
+monitor */
+UNIV_INTERN
+const char*
+srv_mon_get_name(
+/*=============*/
+	monitor_id_t	monitor_id);	/*!< id index into the
+					innodb_counter_info array */
+
+/****************************************************************//**
+Turn on/off/reset monitor counters in a module. If module_value
+is NUM_MONITOR then turn on all monitor counters.
+@return	0 if successful, or the first monitor that cannot be
+turned on because it is already turned on. */
+UNIV_INTERN
+ulint
+srv_mon_set_module_control(
+/*=======================*/
+	monitor_id_t	module_id,	/*!< in: Module ID as in
+					monitor_counter_id. If it is
+					set to NUM_MONITOR, this means
+					we shall turn on all the counters */
+	mon_option_t	set_option);	/*!< in: Turn on/off reset the
+					counter */
+/****************************************************************//**
+This function consolidates some existing server counters used
+by "system status variables". These existing system variables do not have
+mechanism to start/stop and reset the counters, so we simulate these
+controls by remembering the corresponding counter values when the
+corresponding monitors are turned on/off/reset, and do appropriate
+mathematics to deduct the actual value. */
+UNIV_INTERN
+void
+srv_mon_process_existing_counter(
+/*=============================*/
+	monitor_id_t	monitor_id,	/*!< in: the monitor's ID as in
+					monitor_counter_id */
+	mon_option_t	set_option);	/*!< in: Turn on/off reset the
+					counter */
+/*************************************************************//**
+This function is used to calculate the maximum counter value
+since the start of monitor counter
+@return	max counter value since start. */
+UNIV_INLINE
+lint
+srv_mon_calc_max_since_start(
+/*=========================*/
+	monitor_id_t	monitor);	/*!< in: monitor id */
+/*************************************************************//**
+This function is used to calculate the minimum counter value
+since the start of monitor counter
+@return	min counter value since start. */
+UNIV_INLINE
+lint
+srv_mon_calc_min_since_start(
+/*=========================*/
+	monitor_id_t	monitor);	/*!< in: monitor id*/
+/*************************************************************//**
+Reset a monitor, create a new base line with the current monitor
+value. This baseline is recorded by MONITOR_VALUE_RESET(monitor) */
+UNIV_INTERN
+void
+srv_mon_reset(
+/*==========*/
+	monitor_id_t	monitor);	/*!< in: monitor id*/
+/*************************************************************//**
+This function resets all values of a monitor counter */
+UNIV_INLINE
+void
+srv_mon_reset_all(
+/*==============*/
+	monitor_id_t	monitor);	/*!< in: monitor id*/
+
+#ifndef UNIV_NONINL
+#include "srv0mon.ic"
+#endif
+
+#endif

=== added file 'storage/innobase/include/srv0mon.ic'
--- a/storage/innobase/include/srv0mon.ic	1970-01-01 00:00:00 +0000
+++ b/storage/innobase/include/srv0mon.ic	revid:sunny.bains@stripped
@@ -0,0 +1,113 @@
+/*****************************************************************************
+
+Copyright (c) 2010, Oracle and/or its affiliates. All Rights Reserved.
+
+This program is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free Software
+Foundation; version 2 of the License.
+
+This program is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License along with
+this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+Place, Suite 330, Boston, MA 02111-1307 USA
+
+*****************************************************************************/
+
+/*******************************************************************//**
+@file include/srv0mon.ic
+Server monitoring system
+
+Created 1/20/2010	Jimmy Yang
+************************************************************************/
+
+/*************************************************************//**
+This function is used to calculate the maximum counter value
+since the start of monitor counter
+@return	max counter value since start. */
+UNIV_INLINE
+lint
+srv_mon_calc_max_since_start(
+/*=========================*/
+	monitor_id_t	monitor)	/*!< in: monitor id */
+{
+	if (MONITOR_MAX_VALUE_START(monitor) == MAX_RESERVED) {
+
+		/* MONITOR_MAX_VALUE_START has not yet been
+		initialized, the max value since start is the
+		max count in MONITOR_MAX_VALUE */
+		MONITOR_MAX_VALUE_START(monitor) =
+				MONITOR_MAX_VALUE(monitor);
+
+	} else if (MONITOR_MAX_VALUE(monitor) != MAX_RESERVED
+		   && (MONITOR_MAX_VALUE(monitor)
+		       + MONITOR_VALUE_RESET(monitor)
+		      > MONITOR_MAX_VALUE_START(monitor))) {
+
+		/* If the max value since reset (as specified
+		in MONITOR_MAX_VALUE) plus the reset value is
+		larger than MONITOR_MAX_VALUE_START, reset
+		MONITOR_MAX_VALUE_START to this new max value */
+		MONITOR_MAX_VALUE_START(monitor) =
+				MONITOR_MAX_VALUE(monitor)
+				+ MONITOR_VALUE_RESET(monitor);
+	}
+
+	return(MONITOR_MAX_VALUE_START(monitor));
+}
+
+/*************************************************************//**
+This function is used to calculate the minimum counter value
+since the start of monitor counter
+@return	min counter value since start. */
+UNIV_INLINE
+lint
+srv_mon_calc_min_since_start(
+/*=========================*/
+	monitor_id_t	monitor)	/*!< in: monitor id */
+{
+	if (MONITOR_MIN_VALUE_START(monitor) == MIN_RESERVED) {
+
+		/* MONITOR_MIN_VALUE_START has not yet been
+		initialized, the min value since start is the
+		min count in MONITOR_MIN_VALUE */
+		MONITOR_MIN_VALUE_START(monitor) =
+				MONITOR_MIN_VALUE(monitor);
+
+	} else if (MONITOR_MIN_VALUE(monitor) != MIN_RESERVED
+		   && (MONITOR_MIN_VALUE(monitor)
+		       + MONITOR_VALUE_RESET(monitor)
+		       < MONITOR_MIN_VALUE_START(monitor))) {
+
+		/* If the min value since reset (as specified
+		in MONITOR_MIN_VALUE) plus the reset value is
+		less than MONITOR_MIN_VALUE_START, reset
+		MONITOR_MIN_VALUE_START to this new min value */
+		MONITOR_MIN_VALUE_START(monitor) =
+			MONITOR_MIN_VALUE(monitor)
+                        + MONITOR_VALUE_RESET(monitor);
+        }
+
+	return(MONITOR_MIN_VALUE_START(monitor));
+}
+
+/*************************************************************//**
+This function resets all values of a monitor counter */
+UNIV_INLINE
+void
+srv_mon_reset_all(
+/*==============*/
+	monitor_id_t	monitor)	/*!< in: monitor id */
+{
+	/* Do not reset all counter values if monitor is still on. */
+	if (MONITOR_IS_ON(monitor)) {
+		fprintf(stderr, "InnoDB: Cannot reset all values for "
+			"monitor counter %s while it is on. Please "
+			"turn it off and retry. \n",
+			srv_mon_get_name(monitor));
+	} else {
+		MONITOR_RESET_ALL(monitor);
+	}
+}

=== modified file 'storage/innobase/include/srv0srv.h'
--- a/storage/innobase/include/srv0srv.h	revid:sunny.bains@stripped
+++ b/storage/innobase/include/srv0srv.h	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Oracle and/or its affiliates. All Rights Reserved.
 Copyright (c) 2008, 2009, Google Inc.
 Copyright (c) 2009, Percona Inc.
 
@@ -222,6 +222,8 @@ extern ulong	srv_thread_sleep_delay;
 extern ulong	srv_spin_wait_delay;
 extern ibool	srv_priority_boost;
 
+extern ulint	srv_n_lock_wait_count;
+
 extern	ulint	srv_mem_pool_size;
 extern	ulint	srv_lock_table_size;
 

=== modified file 'storage/innobase/lock/lock0lock.c'
--- a/storage/innobase/lock/lock0lock.c	revid:sunny.bains@stripped
+++ b/storage/innobase/lock/lock0lock.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1996, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -38,6 +38,7 @@ Created 5/7/1996 Heikki Tuuri
 #include "trx0purge.h"
 #include "dict0mem.h"
 #include "trx0sys.h"
+#include "srv0mon.h"
 
 /* Restricts the length of search we will do in the waits-for
 graph of transactions */
@@ -1726,6 +1727,9 @@ lock_rec_create(
 		lock_set_lock_and_trx_wait(lock, trx);
 	}
 
+	MONITOR_INC(MONITOR_RECLOCK_CREATED);
+	MONITOR_INC(MONITOR_NUM_RECLOCK);
+
 	return(lock);
 }
 
@@ -1826,6 +1830,8 @@ lock_rec_enqueue_waiting(
 	}
 #endif /* UNIV_DEBUG */
 
+	MONITOR_INC(MONITOR_LOCKREC_WAIT);
+
 	return(DB_LOCK_WAIT);
 }
 
@@ -2264,6 +2270,9 @@ lock_rec_dequeue_from_page(
 
 	UT_LIST_REMOVE(trx_locks, trx->trx_locks, in_lock);
 
+	MONITOR_INC(MONITOR_RECLOCK_REMOVED);
+	MONITOR_DEC(MONITOR_NUM_RECLOCK);
+
 	/* Check if waiting locks in the queue can now be granted: grant
 	locks if there are no conflicting locks ahead. */
 
@@ -2306,6 +2315,9 @@ lock_rec_discard(
 		    lock_rec_fold(space, page_no), in_lock);
 
 	UT_LIST_REMOVE(trx_locks, trx->trx_locks, in_lock);
+
+	MONITOR_INC(MONITOR_RECLOCK_REMOVED);
+	MONITOR_DEC(MONITOR_NUM_RECLOCK);
 }
 
 /*************************************************************//**
@@ -3485,6 +3497,7 @@ lock_deadlock_recursive(
 					      stderr);
 				}
 #endif /* UNIV_DEBUG */
+				MONITOR_INC(MONITOR_DEADLOCK);
 
 				if (trx_weight_cmp(wait_lock->trx,
 						   start) >= 0) {
@@ -3621,6 +3634,9 @@ lock_table_create(
 		lock_set_lock_and_trx_wait(lock, trx);
 	}
 
+	MONITOR_INC(MONITOR_TABLELOCK_CREATED);
+	MONITOR_INC(MONITOR_NUM_TABLELOCK);
+
 	return(lock);
 }
 
@@ -3675,6 +3691,9 @@ lock_table_remove_low(
 
 	UT_LIST_REMOVE(trx_locks, trx->trx_locks, lock);
 	UT_LIST_REMOVE(un_member.tab_lock.locks, table->locks, lock);
+
+	MONITOR_INC(MONITOR_TABLELOCK_REMOVED);
+	MONITOR_DEC(MONITOR_NUM_TABLELOCK);
 }
 
 /*********************************************************************//**
@@ -5214,6 +5233,8 @@ lock_clust_rec_modify_check_and_lock(
 		err = DB_SUCCESS;
 	}
 
+	MONITOR_INC(MONITOR_NUM_RECLOCK_REQ);
+
 	return(err);
 }
 

=== modified file 'storage/innobase/log/log0log.c'
--- a/storage/innobase/log/log0log.c	revid:sunny.bains@stripped
+++ b/storage/innobase/log/log0log.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Oracle and/or its affiliates. All Rights Reserved.
 Copyright (c) 2009, Google Inc.
 
 Portions of this file contain modifications contributed and copyrighted by
@@ -48,6 +48,7 @@ Created 12/9/1995 Heikki Tuuri
 #include "srv0start.h"
 #include "trx0sys.h"
 #include "trx0trx.h"
+#include "srv0mon.h"
 
 /*
 General philosophy of InnoDB redo-logs:
@@ -826,6 +827,8 @@ log_init(void)
 
 	log_sys->next_checkpoint_no = 0;
 	log_sys->last_checkpoint_lsn = log_sys->lsn;
+	MONITOR_SET_SIMPLE(MONITOR_LSN_CHECKPOINT,
+			   log_sys->last_checkpoint_lsn);
 	log_sys->n_pending_checkpoint_writes = 0;
 
 	rw_lock_create(checkpoint_lock_key, &log_sys->checkpoint_lock,
@@ -1135,6 +1138,7 @@ log_io_complete(
 
 	group->n_pending_writes--;
 	log_sys->n_pending_writes--;
+	MONITOR_DEC(MONITOR_PENDING_LOG_WRITE);
 
 	unlock = log_group_check_flush_completion(group);
 	unlock = unlock | log_sys_check_flush_completion();
@@ -1183,6 +1187,8 @@ log_group_file_header_flush(
 	if (log_do_write) {
 		log_sys->n_log_ios++;
 
+		MONITOR_INC(MONITOR_LOG_IO);
+
 		srv_os_log_pending_writes++;
 
 		fil_io(OS_FILE_WRITE | OS_FILE_LOG, TRUE, group->space_id, 0,
@@ -1303,6 +1309,8 @@ loop:
 	if (log_do_write) {
 		log_sys->n_log_ios++;
 
+		MONITOR_INC(MONITOR_LOG_IO);
+
 		srv_os_log_pending_writes++;
 
 		fil_io(OS_FILE_WRITE | OS_FILE_LOG, TRUE, group->space_id, 0,
@@ -1442,6 +1450,7 @@ loop:
 	}
 #endif /* UNIV_DEBUG */
 	log_sys->n_pending_writes++;
+	MONITOR_INC(MONITOR_PENDING_LOG_WRITE);
 
 	group = UT_LIST_GET_FIRST(log_sys->log_groups);
 	group->n_pending_writes++;	/*!< We assume here that we have only
@@ -1507,12 +1516,18 @@ loop:
 
 		log_sys->flushed_to_disk_lsn = log_sys->write_lsn;
 
+		MONITOR_SET_SIMPLE(MONITOR_LSN_FLUSHDISK,
+				   log_sys->flushed_to_disk_lsn);
+
 	} else if (flush_to_disk) {
 
 		group = UT_LIST_GET_FIRST(log_sys->log_groups);
 
 		fil_flush(group->space_id);
 		log_sys->flushed_to_disk_lsn = log_sys->write_lsn;
+
+		MONITOR_SET_SIMPLE(MONITOR_LSN_FLUSHDISK,
+				   log_sys->flushed_to_disk_lsn);
 	}
 
 	mutex_enter(&(log_sys->mutex));
@@ -1524,6 +1539,7 @@ loop:
 
 	group->n_pending_writes--;
 	log_sys->n_pending_writes--;
+	MONITOR_DEC(MONITOR_PENDING_LOG_WRITE);
 
 	unlock = log_group_check_flush_completion(group);
 	unlock = unlock | log_sys_check_flush_completion();
@@ -1683,6 +1699,9 @@ log_complete_checkpoint(void)
 
 	log_sys->last_checkpoint_lsn = log_sys->next_checkpoint_lsn;
 
+	MONITOR_SET_SIMPLE(MONITOR_LSN_CHECKPOINT,
+			   log_sys->last_checkpoint_lsn);
+
 	rw_lock_x_unlock_gen(&(log_sys->checkpoint_lock), LOG_CHECKPOINT);
 }
 
@@ -1698,6 +1717,7 @@ log_io_complete_checkpoint(void)
 	ut_ad(log_sys->n_pending_checkpoint_writes > 0);
 
 	log_sys->n_pending_checkpoint_writes--;
+	MONITOR_DEC(MONITOR_PENDING_CHECKPOINT_WRITE);
 
 	if (log_sys->n_pending_checkpoint_writes == 0) {
 		log_complete_checkpoint();
@@ -1847,9 +1867,12 @@ log_group_checkpoint(
 		}
 
 		log_sys->n_pending_checkpoint_writes++;
+		MONITOR_INC(MONITOR_PENDING_CHECKPOINT_WRITE);
 
 		log_sys->n_log_ios++;
 
+		MONITOR_INC(MONITOR_LOG_IO);
+
 		/* We send as the last parameter the group machine address
 		added with 1, as we want to distinguish between a normal log
 		file write and a checkpoint field write */
@@ -1933,6 +1956,8 @@ log_group_read_checkpoint_info(
 
 	log_sys->n_log_ios++;
 
+	MONITOR_INC(MONITOR_LOG_IO);
+
 	fil_io(OS_FILE_READ | OS_FILE_LOG, TRUE, group->space_id, 0,
 	       field / UNIV_PAGE_SIZE, field % UNIV_PAGE_SIZE,
 	       OS_FILE_LOG_BLOCK_SIZE, log_sys->checkpoint_buf, NULL);
@@ -2042,6 +2067,8 @@ log_checkpoint(
 
 	log_groups_write_checkpoint_info();
 
+	MONITOR_INC(MONITOR_NUM_CHECKPOINT);
+
 	mutex_exit(&(log_sys->mutex));
 
 	if (sync) {
@@ -2220,6 +2247,8 @@ loop:
 
 	log_sys->n_log_ios++;
 
+	MONITOR_INC(MONITOR_LOG_IO);
+
 	fil_io(OS_FILE_READ | OS_FILE_LOG, sync, group->space_id, 0,
 	       source_offset / UNIV_PAGE_SIZE, source_offset % UNIV_PAGE_SIZE,
 	       len, buf, NULL);
@@ -2281,6 +2310,8 @@ log_group_archive_file_header_write(
 
 	log_sys->n_log_ios++;
 
+	MONITOR_INC(MONITOR_LOG_IO);
+
 	fil_io(OS_FILE_WRITE | OS_FILE_LOG, TRUE, group->archive_space_id,
 	       dest_offset / UNIV_PAGE_SIZE,
 	       dest_offset % UNIV_PAGE_SIZE,
@@ -2314,6 +2345,8 @@ log_group_archive_completed_header_write
 
 	log_sys->n_log_ios++;
 
+	MONITOR_INC(MONITOR_LOG_IO);
+
 	fil_io(OS_FILE_WRITE | OS_FILE_LOG, TRUE, group->archive_space_id,
 	       dest_offset / UNIV_PAGE_SIZE,
 	       dest_offset % UNIV_PAGE_SIZE,
@@ -2441,6 +2474,8 @@ loop:
 
 	log_sys->n_log_ios++;
 
+	MONITOR_INC(MONITOR_LOG_IO);
+
 	fil_io(OS_FILE_WRITE | OS_FILE_LOG, FALSE, group->archive_space_id,
 	       next_offset / UNIV_PAGE_SIZE, next_offset % UNIV_PAGE_SIZE,
 	       ut_calc_align(len, OS_FILE_LOG_BLOCK_SIZE), buf,

=== modified file 'storage/innobase/os/os0file.c'
--- a/storage/innobase/os/os0file.c	revid:sunny.bains@stripped
+++ b/storage/innobase/os/os0file.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /***********************************************************************
 
-Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Oracle and/or its affiliates. All Rights Reserved.
 Copyright (c) 2009, Percona Inc.
 
 Portions of this file contain modifications contributed and copyrighted
@@ -43,6 +43,7 @@ Created 10/21/1995 Heikki Tuuri
 #include "srv0start.h"
 #include "fil0fil.h"
 #include "buf0buf.h"
+#include "srv0mon.h"
 #ifndef UNIV_HOTBACKUP
 # include "os0sync.h"
 # include "os0thread.h"
@@ -2210,6 +2211,7 @@ os_file_pread(
 	os_mutex_enter(os_file_count_mutex);
 	os_file_n_pending_preads++;
 	os_n_pending_reads++;
+	MONITOR_INC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 	n_bytes = pread(file, buf, (ssize_t)n, offs);
@@ -2217,6 +2219,7 @@ os_file_pread(
 	os_mutex_enter(os_file_count_mutex);
 	os_file_n_pending_preads--;
 	os_n_pending_reads--;
+	MONITOR_DEC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 	return(n_bytes);
@@ -2230,6 +2233,7 @@ os_file_pread(
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_reads++;
+		MONITOR_INC(MONITOR_OS_PENDING_READS);
 		os_mutex_exit(os_file_count_mutex);
 
 #ifndef UNIV_HOTBACKUP
@@ -2253,6 +2257,7 @@ os_file_pread(
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_reads--;
+		MONITOR_DEC(MONITOR_OS_PENDING_READS);
 		os_mutex_exit(os_file_count_mutex);
 
 		return(ret);
@@ -2301,6 +2306,7 @@ os_file_pwrite(
 	os_mutex_enter(os_file_count_mutex);
 	os_file_n_pending_pwrites++;
 	os_n_pending_writes++;
+	MONITOR_INC(MONITOR_OS_PENDING_WRITES);
 	os_mutex_exit(os_file_count_mutex);
 
 	ret = pwrite(file, buf, (ssize_t)n, offs);
@@ -2308,6 +2314,7 @@ os_file_pwrite(
 	os_mutex_enter(os_file_count_mutex);
 	os_file_n_pending_pwrites--;
 	os_n_pending_writes--;
+	MONITOR_DEC(MONITOR_OS_PENDING_WRITES);
 	os_mutex_exit(os_file_count_mutex);
 
 # ifdef UNIV_DO_FLUSH
@@ -2333,6 +2340,7 @@ os_file_pwrite(
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_writes++;
+		MONITOR_INC(MONITOR_OS_PENDING_WRITES);
 		os_mutex_exit(os_file_count_mutex);
 
 # ifndef UNIV_HOTBACKUP
@@ -2372,6 +2380,7 @@ func_exit:
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_writes--;
+		MONITOR_DEC(MONITOR_OS_PENDING_WRITES);
 		os_mutex_exit(os_file_count_mutex);
 
 		return(ret);
@@ -2423,6 +2432,7 @@ try_again:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_reads++;
+	MONITOR_INC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 #ifndef UNIV_HOTBACKUP
@@ -2442,6 +2452,7 @@ try_again:
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_reads--;
+		MONITOR_DEC(MONITOR_OS_PENDING_READS);
 		os_mutex_exit(os_file_count_mutex);
 
 		goto error_handling;
@@ -2455,6 +2466,7 @@ try_again:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_reads--;
+	MONITOR_DEC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 	if (ret && len == n) {
@@ -2549,6 +2561,7 @@ try_again:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_reads++;
+	MONITOR_INC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 #ifndef UNIV_HOTBACKUP
@@ -2568,6 +2581,7 @@ try_again:
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_reads--;
+		MONITOR_DEC(MONITOR_OS_PENDING_READS);
 		os_mutex_exit(os_file_count_mutex);
 
 		goto error_handling;
@@ -2581,6 +2595,7 @@ try_again:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_reads--;
+	MONITOR_DEC(MONITOR_OS_PENDING_READS);
 	os_mutex_exit(os_file_count_mutex);
 
 	if (ret && len == n) {
@@ -2679,6 +2694,7 @@ retry:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_writes++;
+	MONITOR_INC(MONITOR_OS_PENDING_WRITES);
 	os_mutex_exit(os_file_count_mutex);
 
 #ifndef UNIV_HOTBACKUP
@@ -2698,6 +2714,7 @@ retry:
 
 		os_mutex_enter(os_file_count_mutex);
 		os_n_pending_writes--;
+		MONITOR_DEC(MONITOR_OS_PENDING_WRITES);
 		os_mutex_exit(os_file_count_mutex);
 
 		ut_print_timestamp(stderr);
@@ -2734,6 +2751,7 @@ retry:
 
 	os_mutex_enter(os_file_count_mutex);
 	os_n_pending_writes--;
+	MONITOR_DEC(MONITOR_OS_PENDING_WRITES);
 	os_mutex_exit(os_file_count_mutex);
 
 	if (ret && len == n) {

=== modified file 'storage/innobase/page/page0zip.c'
--- a/storage/innobase/page/page0zip.c	revid:sunny.bains@stripped
+++ b/storage/innobase/page/page0zip.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 2005, 2009, Innobase Oy. All Rights Reserved.
+Copyright (c) 2005, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -42,6 +42,7 @@ Created June 2005 by Marko Makela
 # include "btr0sea.h"
 # include "dict0boot.h"
 # include "lock0lock.h"
+# include "srv0mon.h"
 #else /* !UNIV_HOTBACKUP */
 # define lock_move_reorganize_page(block, temp_block)	((void) 0)
 # define buf_LRU_stat_inc_unzip()			((void) 0)
@@ -1214,6 +1215,7 @@ page_zip_compress(
 #endif /* PAGE_ZIP_COMPRESS_DBG */
 #ifndef UNIV_HOTBACKUP
 	page_zip_stat[page_zip->ssize - 1].compressed++;
+	MONITOR_INC(MONITOR_PAGE_COMPRESS);
 #endif /* !UNIV_HOTBACKUP */
 
 	if (UNIV_UNLIKELY(n_dense * PAGE_ZIP_DIR_SLOT_SIZE
@@ -3021,6 +3023,7 @@ err_exit:
 			= &page_zip_stat[page_zip->ssize - 1];
 		zip_stat->decompressed++;
 		zip_stat->decompressed_usec += ut_time_us(NULL) - usec;
+		MONITOR_INC(MONITOR_PAGE_DECOMPRESS);
 	}
 #endif /* !UNIV_HOTBACKUP */
 

=== modified file 'storage/innobase/row/row0purge.c'
--- a/storage/innobase/row/row0purge.c	revid:sunny.bains@stripped
+++ b/storage/innobase/row/row0purge.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1997, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -43,6 +43,7 @@ Created 3/14/1997 Heikki Tuuri
 #include "row0vers.h"
 #include "row0mysql.h"
 #include "log0log.h"
+#include "srv0mon.h"
 
 /********************************************************************//**
 Creates a purge node to a query graph.
@@ -753,6 +754,8 @@ row_purge(
 			btr_pcur_close(&(node->pcur));
 		}
 
+		MONITOR_INC(MONITOR_NUM_ROW_PURGE);
+
 		row_mysql_unfreeze_data_dictionary(trx);
 	}
 

=== added file 'storage/innobase/srv/srv0mon.c'
--- a/storage/innobase/srv/srv0mon.c	1970-01-01 00:00:00 +0000
+++ b/storage/innobase/srv/srv0mon.c	revid:sunny.bains@stripped
@@ -0,0 +1,751 @@
+/*****************************************************************************
+
+Copyright (c) 2010,  Oracle and/or its affiliates. All Rights Reserved.
+
+This program is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free Software
+Foundation; version 2 of the License.
+
+This program is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License along with
+this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+Place, Suite 330, Boston, MA 02111-1307 USA
+
+*****************************************************************************/
+
+/**************************************************//**
+@file srv/srv0mon.c
+Database monitor counter interfaces
+
+Created 12/9/2009 Jimmy Yang
+*******************************************************/
+
+#include "os0file.h"
+#include "mach0data.h"
+#include "srv0mon.h"
+#include "srv0srv.h"
+#include "buf0buf.h"
+#include "trx0sys.h"
+#ifdef UNIV_NONINL
+#include "srv0mon.ic"
+#endif
+
+/** This array defines basic static information of monitor counters,
+including each monitor's name, sub module it belongs to, a short
+description and its property/type and corresponding monitor_id. */
+static monitor_info_t	innodb_counter_info[] =
+{
+	/* A dummy item to mark the module start, this is
+	to accomodate the default value (0) set for the
+	global variables with the control system. */
+	{"module_start", "module_start", "module_start",
+	MONITOR_MODULE, MONITOR_DEFAULT_START},
+
+	/* ========== Counters for Server Metadata ========== */
+	{"module_server", "Server Metadata", "Server Metadata",
+	 MONITOR_MODULE, MONITOR_MODULE_METADATA},
+
+	{"server_table_open", "Server Metadata",
+	 "Number of table handler opened", 0, MONITOR_TABLE_OPEN},
+
+	{"server_table_close", "Server Metadata",
+	 "Number of table handler closed", 0, MONITOR_TABLE_CLOSE},
+
+	/* ========== Counters for Lock Module ========== */
+	{"module_lock", "Lock", "Lock Module",
+	 MONITOR_MODULE, MONITOR_MODULE_LOCK},
+
+	{"lock_deadlock_count", "Lock", "Number of deadlocks",
+	 0, MONITOR_DEADLOCK},
+
+	{"lock_timeout", "Lock", "Number of lock timeout",
+	 0, MONITOR_TIMEOUT},
+
+	{"lock_lockrec_wait", "Lock", "Number of times wait for record lock",
+	 0, MONITOR_LOCKREC_WAIT},
+
+	{"lock_lockrec_request", "Lock", "Number of record lock requested",
+	 0, MONITOR_NUM_RECLOCK_REQ},
+
+	{"lock_lockrec_created", "Lock", "Number of record lock created",
+	 0, MONITOR_RECLOCK_CREATED},
+
+	{"lock_lockrec_removed", "Lock", "Number of record lock destroyed",
+	 0, MONITOR_RECLOCK_REMOVED},
+
+	{"lock_num_lockrec", "Lock", "Total number of record locks",
+	 0, MONITOR_NUM_RECLOCK},
+
+	{"lock_tablelock_created", "Lock", "Number of table locks created",
+	 0, MONITOR_TABLELOCK_CREATED},
+
+	{"lock_tablelock_removed", "Lock", "Number of table lock destroyed",
+	 0, MONITOR_TABLELOCK_REMOVED},
+
+	{"lock_num_tablelock", "Lock", "Total number of table locks",
+	 0, MONITOR_NUM_TABLELOCK},
+
+	{"lock_row_lock_current_wait", "Lock", "Current row lock wait",
+	 0, MONITOR_ROW_LOCK_CURRENT_WAIT},
+
+	{"lock_row_lock_wait_time", "Lock", "Time waited for lock acquisition",
+	 0, MONITOR_LOCK_WAIT_TIME},
+
+	{"lock_row_lock_wait", "Lock", "Total row lock waits",
+	 MONITOR_EXISTING, MONITOR_OVLD_ROW_LOCK_WAIT},
+
+	/* ========== Counters for Buffer Manager and I/O ========== */
+	{"module_buffer", "Buffer", "Buufer Manager Module",
+	 MONITOR_MODULE, MONITOR_MODULE_BUFFER},
+
+	{"buffer_reads", "Buffer", "Number of reads from disk",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_READS},
+
+	{"buffer_read_request", "Buffer", "Number of read requests",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_READ_REQUESTS},
+
+	{"buffer_write_request", "Buffer", "Number of write requests",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_WRITE_REQUEST},
+
+	{"buffer_page_in_flush", "Buffer", "Number of pages in flush list",
+	 0, MONITOR_PAGE_INFLUSH},
+
+	{"buffer_wait_free", "Buffer", "Number of times wait for free buffer",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_WAIT_FREE},
+
+	{"buffer_read_ahead", "Buffer", "Number of pages read as read ahead",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_READ_AHEAD},
+
+	{"buffer_read_ahead_evict", "Buffer",
+	 "Read ahead pages evicted without being accessed",
+	 MONITOR_EXISTING, MONITOR_OVLD_BUF_POOL_READ_AHEAD_EVICTED},
+
+	{"buffer_pool_total_page", "Buffer", "Total buffer pool pages",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT,
+	 MONITOR_OVLD_BUF_POOL_PAGE_TOTAL},
+
+	{"buffer_pool_page_misc", "Buffer", "Buffer pages for misc use",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT,
+	 MONITOR_OVLD_BUF_POOL_PAGE_MISC},
+
+	{"buffer_pool_page_data", "Buffer", "Buffer pages contain data",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT,
+	 MONITOR_OVLD_BUF_POOL_PAGES_DATA},
+
+	{"buffer_pool_page_dirty", "Buffer", "Buffer pages currently dirty",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT,
+	 MONITOR_OVLD_BUF_POOL_PAGES_DIRTY},
+
+	{"buffer_pool_page_free", "Buffer", "Buffer pages currently free",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT,
+	 MONITOR_OVLD_BUF_POOL_PAGES_FREE},
+
+	{"buffer_page_created", "Buffer", "Number of pages created",
+	 MONITOR_EXISTING, MONITOR_OVLD_PAGE_CREATED},
+
+	{"buffer_page_written", "Buffer", "Number of pages written",
+	 MONITOR_EXISTING, MONITOR_OVLD_PAGES_WRITTEN},
+
+	{"buffer_page_read", "Buffer", "Number of pages read",
+	 MONITOR_EXISTING, MONITOR_OVLD_PAGES_READ},
+
+	{"buffer_byte_read", "Buffer", "Amount data read in bytes",
+	 MONITOR_EXISTING, MONITOR_OVLD_BYTE_READ},
+
+	{"buffer_byte_written", "Buffer", "Amount data written in bytes",
+	 MONITOR_EXISTING, MONITOR_OVLD_BYTE_WRITTEN},
+
+	/* ========== Counters for OS level operations ========== */
+	{"module_os", "OS", "OS Level Operation",
+	 MONITOR_MODULE, MONITOR_MODULE_OS},
+
+	{"os_num_reads", "OS", "Number of reads initiated",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_FILE_READ},
+
+	{"os_num_writes", "OS", "Number of writes inititated",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_FILE_WRITE},
+
+	{"os_num_fsync", "OS", "Number of fsync() call",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_FSYNC},
+
+	{"os_num_pending_reads", "OS", "Number of reads pending",
+	 0, MONITOR_OS_PENDING_READS},
+
+	{"os_num_pending_writes", "OS", "Number of writes pending",
+	 0, MONITOR_OS_PENDING_WRITES},
+
+	{"os_log_byte_written", "Recovery", "Bytes of log written",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_LOG_WRITTEN},
+
+	{"os_log_fsync", "Recovery", "Number of fsync log writes",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_LOG_FSYNC},
+
+	{"os_log_pending_fsync", "Recovery", "Number of pending fsync write",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_LOG_PENDING_FSYNC},
+
+	{"os_log_pending_write", "Recovery",
+	 "Number of pending log file writes",
+	 MONITOR_EXISTING, MONITOR_OVLD_OS_LOG_PENDING_WRITES},
+
+	/* ========== Counters for Transaction Module ========== */
+	{"module_trx", "Transaction", "Transaction Manager",
+	 MONITOR_MODULE, MONITOR_MODULE_TRX},
+
+	{"trx_num_commit", "Transaction", "Number of transactions committed",
+	 0, MONITOR_TRX_COMMIT},
+
+	{"trx_num_abort", "Transaction", "Number of transactions aborted",
+	 0, MONITOR_TRX_ABORT},
+
+	{"trx_active_trx", "Transaction", "Number of active transactions",
+	 0, MONITOR_TRX_ACTIVE},
+
+	{"trx_num_row_purged", "Transaction", "Number of rows purged",
+	 0, MONITOR_NUM_ROW_PURGE},
+
+	{"trx_purge_delay", "DML",
+	 "microseconds DML to be delayed due to purge lagging",
+	 MONITOR_DISPLAY_CURRENT, MONITOR_DML_PURGE_DELAY},
+
+	{"trx_rseg_history_len", "Transaction",
+	 "Length of the TRX_RSEG_HISTORY list",
+	 MONITOR_EXISTING | MONITOR_DISPLAY_CURRENT, MONITOR_RSEG_HISTORY_LEN},
+
+	/* ========== Counters for Recovery Module ========== */
+	{"module_log", "Recovery", "Recovery Module",
+	 MONITOR_MODULE, MONITOR_MODULE_RECOVERY},
+
+	{"log_num_checkpoint", "Recovery", "Number of checkpoints",
+	 0, MONITOR_NUM_CHECKPOINT},
+
+	{"log_lsn_last_flush", "Recovery", "Last flush's LSN",
+	 0, MONITOR_LSN_FLUSHDISK},
+
+	{"log_lsn_last_checkpoint", "Recovery", "LSN at last checkpoint",
+	 0, MONITOR_LSN_CHECKPOINT},
+
+	{"log_current_lsn", "Recovery", "Current LSN value",
+	 0, MONITOR_LSN_CURRENT},
+
+	{"log_pending_log_write", "Recovery", "Pending Log Writes",
+	 MONITOR_DISPLAY_CURRENT, MONITOR_PENDING_LOG_WRITE},
+
+	{"log_pending_checkpoint", "Recovery", "Pending Checkpoints",
+	 0, MONITOR_PENDING_CHECKPOINT_WRITE},
+
+	{"log_num_log_io", "Recovery", "Number of log I/Os",
+	 0, MONITOR_LOG_IO},
+
+	{"log_waits", "Recovery", "Number of log waits due to small log buffer",
+	 MONITOR_EXISTING, MONITOR_OVLD_LOG_WAITS},
+
+	{"log_write_request", "Recovery", "Number of log write requests",
+	 MONITOR_EXISTING, MONITOR_OVLD_LOG_WRITE_REQUEST},
+
+	{"log_writes", "Recovery", "Number of log writes",
+	 MONITOR_EXISTING, MONITOR_OVLD_LOG_WRITES},
+
+	{"log_flush_io_capacity", "Recovery",
+	 "Percent of Server IO capacity during flushing",
+	 MONITOR_DISPLAY_CURRENT, MONITOR_FLUSH_IO_CAPACITY},
+
+	{"log_flush_dirty_page_exceed", "Recovery",
+	 "Number of flush calls when the max dirty page pct was hit",
+	 0, MONITOR_FLUSH_DIRTY_PAGE_EXCEED},
+
+	/* ========== Counters for Page Compression ========== */
+	{"module_compress", "Compression", "Page Compression Info",
+	 MONITOR_MODULE, MONITOR_MODULE_PAGE},
+
+	{"compress_num_page_compressed", "Compression",
+	 "Number of page compressed", 0, MONITOR_PAGE_COMPRESS},
+
+	{"compress_num_page_decompressed", "Compression",
+	 "Number of page decompressed", 0, MONITOR_PAGE_DECOMPRESS},
+
+	/* ========== Counters for Index ========== */
+	{"module_index", "Index", "Index Manager",
+	 MONITOR_MODULE, MONITOR_MODULE_INDEX},
+
+	{"index_num_split", "Index", "Number of index split",
+	 0, MONITOR_INDEX_SPLIT},
+
+	{"index_num_merge", "Index", "Number of index merge",
+	 0, MONITOR_INDEX_MERGE},
+
+	/* ========== Counters for DML operations ========== */
+	{"module_dml", "DML", "Statistics for DMLs",
+	 MONITOR_MODULE, MONITOR_MODULE_DMLSTATS},
+
+	{"dml_num_reads", "DML", "Number of rows read",
+	 MONITOR_EXISTING, MONITOR_OLVD_ROW_READ},
+
+	{"dml_num_inserts", "DML", "Number of rows inserted",
+	 MONITOR_EXISTING, MONITOR_OLVD_ROW_INSERTED},
+
+	{"dml_num_deletes", "DML", "Number of rows deleted",
+	 MONITOR_EXISTING, MONITOR_OLVD_ROW_DELETED},
+
+	{"dml_updates", "DML", "Number of rows updated",
+	 MONITOR_EXISTING, MONITOR_OLVD_ROW_UPDTATED},
+
+	/* ========== To turn on/off reset all counters ========== */
+	{"all", "All Counters", "Turn on/off and reset all counters",
+	 MONITOR_MODULE, MONITOR_ALL_COUNTER}
+};
+
+/* The "innodb_counter_value" array stores actual counter values */
+UNIV_INTERN monitor_value_t	innodb_counter_value[NUM_MONITOR];
+
+/* monitor_set_tbl is used to record and determine whether a monitor
+has been turned on/off. */
+UNIV_INTERN ulint		monitor_set_tbl[(NUM_MONITOR + NUM_BITS_ULINT
+						- 1) / NUM_BITS_ULINT];
+
+/****************************************************************//**
+Get a monitor's "monitor_info" by its monitor id (index into the
+innodb_counter_info array.
+@return	Point to corresponding monitor_info_t, or NULL if no such
+monitor */
+UNIV_INTERN
+monitor_info_t*
+srv_mon_get_info(
+/*=============*/
+	monitor_id_t	monitor_id)	/*!< id indexing into the
+					innodb_counter_info array */
+{
+	ut_a(monitor_id < NUM_MONITOR);
+
+	return((monitor_id < NUM_MONITOR)
+			? &innodb_counter_info[monitor_id]
+			: NULL);
+}
+
+/****************************************************************//**
+Get monitor's name by its monitor id (indexing into the
+innodb_counter_info array.
+@return	corresponding monitor name, or NULL if no such
+monitor */
+UNIV_INTERN
+const char*
+srv_mon_get_name(
+/*=============*/
+	monitor_id_t	monitor_id)	/*!< id index into the
+					innodb_counter_info array */
+{
+	ut_a(monitor_id < NUM_MONITOR);
+
+	return((monitor_id < NUM_MONITOR)
+			? innodb_counter_info[monitor_id].monitor_name
+			: NULL);
+}
+
+/****************************************************************//**
+Turn on/off, reset monitor counters in a module. If module_id
+is MONITOR_ALL_COUNTER then turn on all monitor counters.
+@return	0 if successful, or the first monitor that cannot be
+turned on because it has already been turned on. */
+UNIV_INTERN
+ulint
+srv_mon_set_module_control(
+/*=======================*/
+	monitor_id_t	module_id,	/*!< in: Module ID as in
+					monitor_counter_id. If it is
+					set to MONITOR_ALL_COUNTER, this means
+					we shall turn on all the counters */
+	mon_option_t	set_option)	/*!< in: Turn on/off reset the
+					counter */
+{
+	ulint	ix;
+
+	ut_a(module_id <= NUM_MONITOR);
+	ut_a(UT_ARR_SIZE(innodb_counter_info) == NUM_MONITOR);
+
+	/* The module_id must be an ID of MONITOR_MODULE type */
+	ut_a(innodb_counter_info[module_id].monitor_type & MONITOR_MODULE);
+
+	/* start with the first monitor in the module. If module_id
+	is MONITOR_ALL_COUNTER, this means we need to turn on all
+	monitor counters. */
+	for (ix = (module_id == MONITOR_ALL_COUNTER) ? 1 : module_id + 1;
+	     ix < NUM_MONITOR; ix++) {
+		/* Cannot turn on a monitor already been turned on. User
+		should be aware some counters are already on before
+		turn them on again (which could reset counter value) */
+		if (MONITOR_IS_ON(ix) && (set_option == MONITOR_TURN_ON)) {
+			return(ix);
+		}
+
+		/* if we hit the next module counter, we will
+		continue if we want to turn on all monitor counters,
+		and break if just turn on the counters in the
+		current module. */
+		if (innodb_counter_info[ix].monitor_type & MONITOR_MODULE) {
+			if (module_id == MONITOR_ALL_COUNTER) {
+				continue;
+			} else {
+				break;
+			}
+		}
+
+		/* For some existing counters (server status variables),
+		we will get its counter value at the start/stop time
+		to calculate the actual value during the time. */
+		if (innodb_counter_info[ix].monitor_type & MONITOR_EXISTING) {
+			srv_mon_process_existing_counter(ix, set_option);
+		}
+
+		/* Currently support 4 operations on the monitor counters:
+		turn on, turn off, reset and reset all operations. */
+		switch (set_option) {
+		case MONITOR_TURN_ON:
+			MONITOR_ON(ix);
+			MONITOR_INIT(ix);
+			MONITOR_SET_START(ix);
+			break;
+
+		case MONITOR_TURN_OFF:
+			MONITOR_OFF(ix);
+			MONITOR_SET_OFF(ix);
+			break;
+
+		case MONITOR_RESET_VALUE:
+			srv_mon_reset(ix);
+			break;
+
+		case MONITOR_RESET_ALL_VALUE:
+			srv_mon_reset_all(ix);
+			break;
+
+		default:
+			ut_error;
+		}
+	}
+
+	return(0);
+}
+
+/****************************************************************//**
+This function consolidates some existing server counters used
+by "system status variables". These existing system variables do not have
+mechanism to start/stop and reset the counters, so we simulate these
+controls by remembering the corresponding counter values when the
+corresponding monitors are turned on/off/reset, and do appropriate
+mathematics to deduct the actual value. Please also refer to
+srv_export_innodb_status() for related global counters used by
+the existing status variables.*/
+UNIV_INTERN
+void
+srv_mon_process_existing_counter(
+/*=============================*/
+	monitor_id_t	monitor_id,	/*!< in: the monitor's ID as in
+					monitor_counter_id */
+	mon_option_t	set_option)	/*!< in: Turn on/off reset the
+					counter */
+{
+	ulint		value;
+	monitor_info_t*	monitor_info;
+	ibool		update_min = FALSE;
+	buf_pool_stat_t	stat;
+	ulint		LRU_len;
+	ulint		free_len;
+	ulint		flush_list_len;
+
+	monitor_info = srv_mon_get_info(monitor_id);
+
+	ut_a(monitor_info->monitor_type & MONITOR_EXISTING);
+	ut_a(monitor_id < NUM_MONITOR);
+
+	/* Get the value from corresponding global variable */
+	switch (monitor_id) {
+	/* export_vars.innodb_buffer_pool_reads. Num Reads from
+	disk (page not in buffer) */
+	case MONITOR_OVLD_BUF_POOL_READS:
+		value = srv_buf_pool_reads;
+		break;
+
+	/* innodb_buffer_pool_read_requests, the number of logical
+	read requests */
+	case MONITOR_OVLD_BUF_POOL_READ_REQUESTS:
+		buf_get_total_stat(&stat);
+		value = stat.n_page_gets;
+		break;
+
+	/* innodb_buffer_pool_write_requests, the number of
+	write request */
+	case MONITOR_OVLD_BUF_POOL_WRITE_REQUEST:
+		value = srv_buf_pool_write_requests;
+		break;
+
+	/* innodb_buffer_pool_wait_free */
+	case MONITOR_OVLD_BUF_POOL_WAIT_FREE:
+		value = srv_buf_pool_wait_free;
+		break;
+
+	/* innodb_buffer_pool_read_ahead */
+	case MONITOR_OVLD_BUF_POOL_READ_AHEAD:
+		buf_get_total_stat(&stat);
+		value = stat.n_ra_pages_read;
+		break;
+
+	/* innodb_buffer_pool_read_ahead_evicted */
+	case MONITOR_OVLD_BUF_POOL_READ_AHEAD_EVICTED:
+		buf_get_total_stat(&stat);
+		value = stat.n_ra_pages_evicted;
+		break;
+
+	/* innodb_buffer_pool_pages_total */
+	case MONITOR_OVLD_BUF_POOL_PAGE_TOTAL:
+		value = buf_pool_get_curr_size();
+		break;
+
+	/* innodb_buffer_pool_pages_misc */
+	case MONITOR_OVLD_BUF_POOL_PAGE_MISC:
+		buf_get_total_list_len(&LRU_len, &free_len, &flush_list_len);
+		value = buf_pool_get_curr_size() - LRU_len - free_len;
+		break;
+
+	/* innodb_buffer_pool_pages_data */
+	case MONITOR_OVLD_BUF_POOL_PAGES_DATA:
+		buf_get_total_list_len(&LRU_len, &free_len, &flush_list_len);
+		value = LRU_len;
+		break;
+
+	/* innodb_buffer_pool_pages_dirty */
+	case MONITOR_OVLD_BUF_POOL_PAGES_DIRTY:
+		buf_get_total_list_len(&LRU_len, &free_len, &flush_list_len);
+		value = flush_list_len;
+		break;
+
+	/* innodb_buffer_pool_pages_free */
+	case MONITOR_OVLD_BUF_POOL_PAGES_FREE:
+		buf_get_total_list_len(&LRU_len, &free_len, &flush_list_len);
+		value = free_len;
+		break;
+
+	/* innodb_pages_created, the number of pages created */
+	case MONITOR_OVLD_PAGE_CREATED:
+		buf_get_total_stat(&stat);
+		value = stat.n_pages_created;
+		break;
+
+	/* innodb_pages_written, the number of page written */
+	case MONITOR_OVLD_PAGES_WRITTEN:
+		buf_get_total_stat(&stat);
+		value = stat.n_pages_written;
+		break;
+
+	/* innodb_pages_read */
+	case MONITOR_OVLD_PAGES_READ:
+		buf_get_total_stat(&stat);
+		value = stat.n_pages_read;
+		break;
+
+	/* innodb_data_writes, the total number of data writes. */
+	case MONITOR_OVLD_BYTE_READ:
+		value = srv_data_read;
+		break;
+
+	/* innodb_data_reads, the total number of data reads */
+	case MONITOR_OVLD_BYTE_WRITTEN:
+		value = srv_data_written;
+		break;
+
+	/* innodb_data_reads, the total number of data reads. */
+	case MONITOR_OVLD_OS_FILE_READ:
+		value = os_n_file_reads;
+		break;
+
+	/* innodb_data_writes, the total number of data writes*/
+	case MONITOR_OVLD_OS_FILE_WRITE:
+		value = os_n_file_writes;
+		break;
+
+	/* innodb_data_fsyncs, number of fsync() operations so far. */
+	case MONITOR_OVLD_OS_FSYNC:
+		value = os_n_fsyncs;
+		break;
+
+	/* innodb_os_log_written */
+	case MONITOR_OVLD_OS_LOG_WRITTEN:
+		value = srv_os_log_written;
+		break;
+
+	/* innodb_os_log_fsyncs */
+	case MONITOR_OVLD_OS_LOG_FSYNC:
+		value = fil_n_log_flushes;
+		break;
+
+	/* innodb_os_log_pending_fsyncs */
+	case MONITOR_OVLD_OS_LOG_PENDING_FSYNC:
+		value = fil_n_pending_log_flushes;
+		update_min = TRUE;
+		break;
+
+	/* innodb_os_log_pending_writes */
+	case MONITOR_OVLD_OS_LOG_PENDING_WRITES:
+		value = srv_os_log_pending_writes;
+		update_min = TRUE;
+		break;
+
+	/* innodb_log_waits */
+	case MONITOR_OVLD_LOG_WAITS:
+		value = srv_log_waits;
+		break;
+
+	/* innodb_log_write_requests */
+	case MONITOR_OVLD_LOG_WRITE_REQUEST:
+		value = srv_log_write_requests;
+		break;
+
+	/* innodb_log_writes */
+	case MONITOR_OVLD_LOG_WRITES:
+		value = srv_log_writes;
+		break;
+
+	/* innodb_rows_read */
+	case MONITOR_OLVD_ROW_READ:
+		value = srv_n_rows_read;
+		break;
+
+	/* innodb_rows_inserted */
+	case MONITOR_OLVD_ROW_INSERTED:
+		value = srv_n_rows_inserted;
+		break;
+
+	/* innodb_rows_deleted */
+	case MONITOR_OLVD_ROW_DELETED:
+		value = srv_n_rows_deleted;
+		break;
+
+	/* innodb_rows_updated */
+	case MONITOR_OLVD_ROW_UPDTATED:
+		value = srv_n_rows_updated;
+		break;
+
+	/* innodb_row_lock_waits */
+	case MONITOR_OVLD_ROW_LOCK_WAIT:
+		value = srv_n_lock_wait_count;
+		break;
+
+	case MONITOR_RSEG_HISTORY_LEN:
+		value = trx_sys->rseg_history_len;
+		break;
+
+	default:
+		ut_error;
+	}
+
+	switch (set_option) {
+	case MONITOR_TURN_ON:
+		/* Save the initial counter value in mon_start_value
+		field */
+		MONITOR_SAVE_START(monitor_id, value);
+		return;
+
+	case MONITOR_TURN_OFF:
+		/* Save the counter value to mon_last_value when we
+		turn off the monitor but not yet reset. Note the
+		counter has not yet been set to off in the bitmap
+		table for normal turn off. We need to check the
+		count status (on/off) to avoid reset the value
+		for an already off conte */
+		if (MONITOR_IS_ON(monitor_id)) {
+			srv_mon_process_existing_counter(monitor_id,
+							 MONITOR_GET_VALUE);
+			MONITOR_SAVE_LAST(monitor_id);
+		}
+		return;
+
+	case MONITOR_GET_VALUE:
+		if (MONITOR_IS_ON(monitor_id)) {
+
+			/* If MONITOR_DISPLAY_CURRENT bit is on, we
+			only record the current value, rather than
+			incremental value over a period. Most of
+`			this type of counters are resource related
+			counters such as number of buffer pages etc. */
+			if (monitor_info->monitor_type
+			    & MONITOR_DISPLAY_CURRENT) {
+				MONITOR_SET(monitor_id, value);
+			} else {
+				/* Most status counters are montonically
+				increasing, no need to update their
+				minimum values. Only do so
+				if "update_min" set to TRUE */
+				MONITOR_SET_DIFF(monitor_id, value);
+
+				if (update_min
+				    && (MONITOR_VALUE(monitor_id)
+					< MONITOR_MIN_VALUE(monitor_id))) {
+					MONITOR_MIN_VALUE(monitor_id) =
+						MONITOR_VALUE(monitor_id);
+				}
+			}
+		}
+		return;
+
+	case MONITOR_RESET_VALUE:
+		if (!MONITOR_IS_ON(monitor_id)) {
+			MONITOR_LAST_VALUE(monitor_id) = 0;
+		}
+		return;
+
+	/* Nothing special for reset all operation for these existing
+	counters */
+	case MONITOR_RESET_ALL_VALUE:
+		return;
+	}
+}
+
+/*************************************************************//**
+Reset a monitor, create a new base line with the current monitor
+value. This baseline is recorded by MONITOR_VALUE_RESET(monitor) */
+UNIV_INTERN
+void
+srv_mon_reset(
+/*==========*/
+	monitor_id_t	monitor)	/*!< in: monitor id */
+{
+	ibool	monitor_was_on;
+
+	monitor_was_on = MONITOR_IS_ON(monitor);
+
+	if (monitor_was_on) {
+		/* Temporarily turn off the counter for the resetting
+		operation */
+		MONITOR_OFF(monitor);
+	}
+
+	/* Before resetting the current monitor value, first
+	calculate and set the max/min value since monitor
+	start */
+	srv_mon_calc_max_since_start(monitor);
+	srv_mon_calc_min_since_start(monitor);
+
+	/* Monitors with MONITOR_DISPLAY_CURRENT bit
+	are not incremental, no need to remember
+	the reset value. */
+	if (innodb_counter_info[monitor].monitor_type
+	    & MONITOR_DISPLAY_CURRENT) {
+		MONITOR_VALUE_RESET(monitor) = 0;
+	} else {
+		/* Remember the new baseline */
+		MONITOR_VALUE_RESET(monitor) = MONITOR_VALUE_RESET(monitor)
+					       + MONITOR_VALUE(monitor);
+	}
+
+	/* Reset the counter value */
+	MONITOR_VALUE(monitor) = 0;
+	MONITOR_MAX_VALUE(monitor) = MAX_RESERVED;
+	MONITOR_MIN_VALUE(monitor) = MIN_RESERVED;
+
+	MONITOR_FIELD((monitor), mon_reset_time) = time(NULL);
+
+	if (monitor_was_on) {
+		MONITOR_ON(monitor);
+	}
+}

=== modified file 'storage/innobase/srv/srv0srv.c'
--- a/storage/innobase/srv/srv0srv.c	revid:sunny.bains@stripped
+++ b/storage/innobase/srv/srv0srv.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1995, 2010, Oracle and/or its affiliates. All Rights Reserved.
 Copyright (c) 2008, 2009 Google Inc.
 Copyright (c) 2009, Percona Inc.
 
@@ -84,6 +84,7 @@ Created 10/8/1995 Heikki Tuuri
 #include "ha_prototypes.h"
 #include "trx0i_s.h"
 #include "os0sync.h" /* for HAVE_ATOMIC_BUILTINS */
+#include "srv0mon.h"
 
 /* This is set to TRUE if the MySQL user has set it in MySQL; currently
 affects only FOREIGN KEY definition parsing */
@@ -1541,6 +1542,7 @@ srv_suspend_mysql_thread(
 	if (thr->lock_state == QUE_THR_LOCK_ROW) {
 		srv_n_lock_wait_count++;
 		srv_n_lock_wait_current_count++;
+		MONITOR_INC(MONITOR_ROW_LOCK_CURRENT_WAIT);
 
 		if (ut_usectime(&sec, &ms) == -1) {
 			start_time = -1;
@@ -1621,6 +1623,7 @@ srv_suspend_mysql_thread(
 		diff_time = (ulint) (finish_time - start_time);
 
 		srv_n_lock_wait_current_count--;
+		MONITOR_DEC(MONITOR_ROW_LOCK_CURRENT_WAIT);
 		srv_n_lock_wait_time = srv_n_lock_wait_time + diff_time;
 		if (diff_time > srv_n_lock_max_wait_time &&
 		    /* only update the variable if we successfully
@@ -2226,6 +2229,7 @@ loop:
 				if (trx->wait_lock) {
 					lock_cancel_waiting_and_release(
 						trx->wait_lock);
+					MONITOR_INC(MONITOR_TIMEOUT);
 				}
 			}
 		}
@@ -2577,6 +2581,7 @@ srv_master_thread(
 	ulint		n_pend_ios;
 	ulint		next_itr_time;
 	ulint		i;
+	ibool		max_modified_ratio_exceeded = FALSE;
 
 #ifdef UNIV_DEBUG_THREAD_CREATION
 	fprintf(stderr, "Master thread starts, id %lu\n",
@@ -2701,6 +2706,9 @@ loop:
 			n_pages_flushed = buf_flush_list(
 				PCT_IO(100), IB_ULONGLONG_MAX);
 
+			/* Record 100% srv_io_capacity for the buffer
+			flush rate */
+			MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY, 100);
 		} else if (srv_adaptive_flushing) {
 
 			/* Try to keep the rate of flushing of dirty
@@ -2716,6 +2724,11 @@ loop:
 					buf_flush_list(
 						n_flush,
 						IB_ULONGLONG_MAX);
+
+				/* Record the IO capacity percentage used
+				for the flush */
+				MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY,
+					    n_flush * 100 / srv_io_capacity)
 			}
 		}
 
@@ -2757,6 +2770,8 @@ loop:
 		srv_main_thread_op_info = "flushing buffer pool pages";
 		buf_flush_list(PCT_IO(100), IB_ULONGLONG_MAX);
 
+		MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY, 100);
+
 		/* Flush logs if needed */
 		srv_sync_log_buffer_in_background();
 	}
@@ -2793,6 +2808,8 @@ loop:
 
 		n_pages_flushed = buf_flush_list(
 			PCT_IO(100), IB_ULONGLONG_MAX);
+
+		MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY, 100);
 	} else {
 		/* Otherwise, we only flush a small number of pages so that
 		we do not unnecessarily use much disk i/o capacity from
@@ -2800,6 +2817,8 @@ loop:
 
 		n_pages_flushed = buf_flush_list(
 			  PCT_IO(10), IB_ULONGLONG_MAX);
+
+		MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY, 10);
 	}
 
 	srv_main_thread_op_info = "making checkpoint";
@@ -2886,9 +2905,16 @@ background_loop:
 flush_loop:
 	srv_main_thread_op_info = "flushing buffer pool pages";
 	srv_main_flush_loops++;
+
 	if (srv_fast_shutdown < 2) {
 		n_pages_flushed = buf_flush_list(
 			  PCT_IO(100), IB_ULONGLONG_MAX);
+
+		MONITOR_SET(MONITOR_FLUSH_IO_CAPACITY, 100);
+
+		if (max_modified_ratio_exceeded) {
+			MONITOR_INC(MONITOR_FLUSH_DIRTY_PAGE_EXCEED);
+		}
 	} else {
 		/* In the fastest shutdown we do not flush the buffer pool
 		to data files: we set n_pages_flushed to 0 artificially. */
@@ -2916,12 +2942,14 @@ flush_loop:
 	log_checkpoint(TRUE, FALSE);
 
 	if (buf_get_modified_ratio_pct() > srv_max_buf_pool_modified_pct) {
+		max_modified_ratio_exceeded = TRUE;
 
 		/* Try to keep the number of modified pages in the
 		buffer pool under the limit wished by the user */
 
 		goto flush_loop;
 	}
+	max_modified_ratio_exceeded = FALSE;
 
 	srv_main_thread_op_info = "reserving kernel mutex";
 

=== modified file 'storage/innobase/trx/trx0purge.c'
--- a/storage/innobase/trx/trx0purge.c	revid:sunny.bains@stripped
+++ b/storage/innobase/trx/trx0purge.c	revid:sunny.bains@stripped
@@ -43,6 +43,7 @@ Created 3/26/1996 Heikki Tuuri
 #include "trx0rec.h"
 #include "srv0srv.h"
 #include "os0thread.h"
+#include "srv0mon.h"
 
 /** The global data structure coordinating a purge */
 UNIV_INTERN trx_purge_t*	purge_sys = NULL;
@@ -1157,6 +1158,8 @@ trx_purge(
 		}
 	}
 
+	MONITOR_SET(MONITOR_DML_PURGE_DELAY, srv_dml_needed_delay);
+
 	purge_sys->view = read_view_oldest_copy_or_open_new(ut_dulint_zero,
 							    purge_sys->heap);
 	mutex_exit(&kernel_mutex);

=== modified file 'storage/innobase/trx/trx0roll.c'
--- a/storage/innobase/trx/trx0roll.c	revid:sunny.bains@stripped
+++ b/storage/innobase/trx/trx0roll.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved.
+Copyright (c) 1996, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -42,6 +42,7 @@ Created 3/26/1996 Heikki Tuuri
 #include "row0mysql.h"
 #include "lock0lock.h"
 #include "pars0pars.h"
+#include "srv0mon.h"
 
 /** This many pages must be undone before a truncate is tried within
 rollback */
@@ -107,6 +108,9 @@ trx_general_rollback_for_mysql(
 		mutex_enter(&kernel_mutex);
 	}
 
+	MONITOR_INC(MONITOR_TRX_ABORT);
+	MONITOR_DEC(MONITOR_TRX_ACTIVE);
+
 	mutex_exit(&kernel_mutex);
 
 	mem_heap_free(heap);

=== modified file 'storage/innobase/trx/trx0trx.c'
--- a/storage/innobase/trx/trx0trx.c	revid:sunny.bains@stripped
+++ b/storage/innobase/trx/trx0trx.c	revid:sunny.bains@stripped
@@ -1,6 +1,6 @@
 /*****************************************************************************
 
-Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved.
+Copyright (c) 1996, 2010, Oracle and/or its affiliates. All Rights Reserved.
 
 This program is free software; you can redistribute it and/or modify it under
 the terms of the GNU General Public License as published by the Free Software
@@ -43,6 +43,7 @@ Created 3/26/1996 Heikki Tuuri
 #include "os0proc.h"
 #include "trx0xa.h"
 #include "ha_prototypes.h"
+#include "srv0mon.h"
 
 /** Dummy session used currently in MySQL interface */
 UNIV_INTERN sess_t*		trx_dummy_sess = NULL;
@@ -685,6 +686,8 @@ trx_start_low(
 
 	UT_LIST_ADD_FIRST(trx_list, trx_sys->trx_list, trx);
 
+	MONITOR_INC(MONITOR_TRX_ACTIVE);
+
 	return(TRUE);
 }
 
@@ -1566,6 +1569,9 @@ trx_commit_for_mysql(
 
 	trx_commit_off_kernel(trx);
 
+	MONITOR_INC(MONITOR_TRX_COMMIT);
+	MONITOR_DEC(MONITOR_TRX_ACTIVE);
+
 	mutex_exit(&kernel_mutex);
 
 	trx->op_info = "";


Attachment: [text/bzr-bundle] bzr/sunny.bains@oracle.com-20100610092339-4r0eqamp7g81lfaf.bundle
Thread
bzr commit into mysql-next-mr-innodb branch (Sunny.Bains:3230) Sunny Bains10 Jun