欧美一区二区三区老妇人-欧美做爰猛烈大尺度电-99久久夜色精品国产亚洲a-亚洲福利视频一区二区

關(guān)于MYSQLflushtable的作用

關(guān)于MySQL flush table的作用

水平有限,還待學(xué)習(xí)。如有錯誤,請指正。

先給出官方文檔:
? FLUSH TABLES
Closes all open tables, forces all tables in use to be closed, and flushes the query cache. FLUSH
TABLES also removes all query results from the query cache, like the RESET QUERY CACHE
statement.
In MySQL 5.6, FLUSH TABLES is not permitted when there is an active LOCK TABLES ... READ.
To flush and lock tables, use FLUSH TABLES tbl_name... WITH READ LOCK instead.
? FLUSH TABLES tbl_name[, tbl_name] ...
With a list of one or more comma-separated table names, this statement is like FLUSH TABLES with
no names except that the server flushes only the named tables. No error occurs if a named table
does not exist.


描述說的是FLUSH TABLE就是關(guān)閉打開的表,并且刷新查詢緩存 ,如果有LOCK TABLES ... READ存在則不允許,
在如果需要同時進行flush和實現(xiàn)READ LOCK 可以使用FLUSH TABLES tbl_name... WITH READ LOCK;




這里的關(guān)閉打開的表,一定會讓會感到困惑,什么是打開的表,
關(guān)閉打開的表又是什么意思,同時關(guān)閉打開的表需要同步臟數(shù)據(jù)到磁盤嗎?



    我們考慮使用innodb_file_per_table 方式建立的INNODB表每個表都有一個相應(yīng)的數(shù)據(jù)文件idb,格式文件frm
但是某些數(shù)據(jù)還是存儲在共享表空間。如果我們的線程要訪問這個表的數(shù)據(jù)必須要首先打開這些文件然后通過
pread()/read() lseek()等系統(tǒng)調(diào)用進行文件位置尋找和讀取。那么我們打開文件的系統(tǒng)調(diào)用應(yīng)該是open()系統(tǒng)調(diào)用。
     當(dāng)然這些必要要有一個LINUX系統(tǒng)及編程基礎(chǔ),先說說一個每個進程都包含了PCB(PCB在內(nèi)核態(tài)空間,進程間是共享的)
PCB是一個進程存在的標(biāo)識存到了進程運行的相關(guān)信息,內(nèi)核中他實際上是一個結(jié)構(gòu)體,其中包含很多信息如我
們熟知的PID PPID(大約100多種信息)其中PCB中保存了一份文件描述符,我們很容易在內(nèi)核代碼task_struct
結(jié)構(gòu)體也就是PCB的信息中找到如下:
/* open file information */
        struct files_struct *files;
其對應(yīng)了內(nèi)核中的file結(jié)構(gòu)體,可以看到進程有一個files_struct結(jié)構(gòu)體用于保存,我們可以簡單認(rèn)為進程進行進程保存
了一份打開所有文件的文件描述符,這個文件描述符從0開始向后計數(shù),每個計數(shù)表示打開的一個文件。如果一個進程要
打開一個文件我們LINUX是使用的open()系統(tǒng)調(diào)用,這個函數(shù)成功放回的就是打開的文件描述符,失敗則設(shè)置返回值為-1
同時給出perror,看看LINUX中對這個函數(shù)的解釋
open() and creat() return the new file descriptor, or -1 if an error occurred (in which case, errno 
is set appropriately).
      
     那么MYSQL既然是一個進程多個線程,那么肯定也逃不掉這樣的LINUX安排,那么MYSQL既然要打開表,那么底層的
調(diào)用必然是OPEN函數(shù),既然文件有打開就有關(guān)閉,當(dāng)進行LINUX系統(tǒng)編程或者C語言編程的時候,我們通常在使用完文件后
使用CLOSE()或者FCLOSE()來關(guān)閉文件,這樣系統(tǒng)釋放打開文件所保留的file信息,防止內(nèi)存泄露。


    那么我們來證明一下使用strace 分別在LINUX進程TRACE LINUX線程信息。




一、關(guān)于打開表


1、首先關(guān)閉重啟mysql,避免其他的打開的表的文件描述的干擾。
[root@hadoop1 kernels]# service mysqldefault restart
     Shutting down MySQL....                                    [  OK  ]
     Starting MySQL...                                          [  OK  ]
2、使用pstree查看mysql所有線程(先找到MYSQL進程ID)
   mysqld(10735)─┬─{mysqld}(10745)
              ├─{mysqld}(10746)
              ...
              ├─{mysqld}(10773)
              └─{mysqld}(10774)
   我們新打開一個MYSQL線程,
   [root@hadoop1 kernels]# pstree -p 10735
mysqld(10735)─┬─{mysqld}(10745)
              ├─{mysqld}(10746)
              ...
              ├─{mysqld}(10774)
              └─{mysqld}(10794)
   這樣我們找到我們新開的會話的線程ID 10794.
3、對線程10794進行STRACE
   strace -T -p 10794
   然后再新的會話打開一個表,我這里打開的是
   select count(*) from tstr;
   
   
   Process 10794 attached - interrupt to quit
......
open("./test/tstr.ibd", O_RDONLY)       = 39 <0.000332>
getcwd("/mysql/data"..., 4096)          = 12 <0.000118>
lstat("/mysql/data/test", {st_mode=S_IFDIR|0700, st_size=4096, ...}) = 0 <0.000114>
lseek(39, 0, SEEK_END)                  = 98304 <0.000109>
pread(39, "*z\322_\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\1\313\332\7\342\0\10\0\0\0\0\0\0"..., 16384, 0) = 16384 <0.016728>
close(39)                               = 0 <0.000243>
open("./test/tstr.ibd", O_RDWR)         = 39 <0.000015>
fcntl(39, F_SETLK, {type=F_WRLCK, whence=SEEK_SET, start=0, len=0}) = 0 <0.000015>
......


我們來分析這里的關(guān)鍵步驟
open("./test/tstr.ibd", O_RDONLY)       = 39 <0.000332> 這里打開表的文件tstr.ibd只讀方式,返回文件描述符39
lseek(39, 0, SEEK_END)                  = 98304 這個是放回當(dāng)前打開文件的大小,也就是初始的96K,因為我只有一條數(shù)據(jù)
pread(39, "*z\322_\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\1\313\332\7\342\0\10\0\0\0\0\0\0"..., 16384, 0) = 16384 <0.016728>
這一行開始真正的讀取數(shù)據(jù) 讀取了16384個字節(jié)。
close(39)                               = 0 <0.000243> 然后關(guān)閉了文件tstr.ibd
open("./test/tstr.ibd", O_RDWR)         = 39 <0.000015> 然后再次以讀寫方式方式打開了tstr.ibd 數(shù)據(jù)文件,返回文件描述符39
fcntl(39, F_SETLK, {type=F_WRLCK, whence=SEEK_SET, start=0, len=0}) = 0 <0.000015>
這一行設(shè)置了tstr.ibd文件的屬性,此函數(shù)用于改變文件屬性,為一需要寫入鎖的屬性,并且開始字節(jié)是0.


如果我們發(fā)現(xiàn)LINUX 在關(guān)閉文件后又一次以寫鎖方式打開了文件。我們現(xiàn)在來看看我們的線程中是否包含了這個文件描述符
4、


[root@hadoop1 fd]# pwd
/proc/10794/fd
[root@hadoop1 fd]# ls -lrt|grep tstr.ibd
lrwx------ 1 root root 64 Dec  5 06:36 39 -> /mysql/data/test/tstr.ibd




二、關(guān)于FLUSH TABLE做了什么操作


1、在某些情況FLUSH TABLE 會被堵塞,如 LOCK TABLES ... READ
   其次我還得到表操作期間文件,比如DML期間(不是事物),表重構(gòu)期間,SELECT 讀取數(shù)據(jù)很慢
   一切不允許進程關(guān)閉文件描述符的操作。
   比如alter table add key(DDL) 這個操作需要將索引系統(tǒng)保存到表空間數(shù)據(jù)文件。
   比如delete from(DML) 這個操作需要將數(shù)據(jù)從表空間數(shù)據(jù)文件刪除。
   比如SELECT 很慢期間 。
   
   
   其等待系統(tǒng)調(diào)用futex(0xbb3f35c, FUTEX_WAIT_PRIVATE, 1, {31535999, 999934000}
   
   
2、FLUSH 實際上做的操作為:


[root@hadoop1 fd]# strace -T -p 15101
Process 15101 attached - interrupt to quit
....
close(24)                               = 0 <0.000115>
close(25)                               = 0 <0.000108>
close(28)                               = 0 <0.000099>
close(29)                               = 0 <0.000097>
close(26)                               = 0 <0.000242>
close(27)                               = 0 <0.000008>
close(30)                               = 0 <0.000008>
close(31)                               = 0 <0.000007>
close(32)                               = 0 <0.000007>
close(33)                               = 0 <0.000007>
close(22)                               = 0 <0.000152>
close(23)                               = 0 <0.000147>
close(20)                               = 0 <0.000110>
close(21)                               = 0 <0.000376>
close(34)                               = 0 <0.000008>
close(35)                               = 0 <0.000007>
close(38)                               = 0 <0.000008>
lseek(37, 0, SEEK_SET)                  = 0 <0.000011>
write(37, "\376\1\354:\1\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"..., 35) = 35 <0.000025>
fsync(37)                               = 0 <0.008020>
close(37)                               = 0 <0.000071>
close(39)                               = 0 <0.000061>
...
Process 15101 detached


我們來觀察這些操作全部是關(guān)閉文件描述符,但是我發(fā)現(xiàn)這里關(guān)閉的文件全部為MYISAM的和CSV文件,如下:
lrwx------ 1 root root 64 Dec  5 08:27 4 -> /mysql/data/test/ibdata1
lrwx------ 1 root root 64 Dec  5 08:27 39 -> /mysql/data/mysql/general_log.CSV
lr-x------ 1 root root 64 Dec  5 08:27 38 -> /mysql/data/mysql/general_log.CSV
lrwx------ 1 root root 64 Dec  5 08:27 37 -> /mysql/data/mysql/general_log.CSM
lrwx------ 1 root root 64 Dec  5 08:27 36 -> socket:[42669]
lrwx------ 1 root root 64 Dec  5 08:27 35 -> /mysql/data/mysql/event.MYD
lrwx------ 1 root root 64 Dec  5 08:27 34 -> /mysql/data/mysql/event.MYI
lrwx------ 1 root root 64 Dec  5 08:27 33 -> /mysql/data/mysql/servers.MYD
lrwx------ 1 root root 64 Dec  5 08:27 32 -> /mysql/data/mysql/servers.MYI
lrwx------ 1 root root 64 Dec  5 08:27 31 -> /mysql/data/mysql/procs_priv.MYD
lrwx------ 1 root root 64 Dec  5 08:27 30 -> /mysql/data/mysql/procs_priv.MYI
lrwx------ 1 root root 64 Dec  5 08:27 3 -> /mysql/data/binlog.index
lrwx------ 1 root root 64 Dec  5 08:27 29 -> /mysql/data/mysql/columns_priv.MYD
lrwx------ 1 root root 64 Dec  5 08:27 28 -> /mysql/data/mysql/columns_priv.MYI
lrwx------ 1 root root 64 Dec  5 08:27 27 -> /mysql/data/mysql/tables_priv.MYD
lrwx------ 1 root root 64 Dec  5 08:27 26 -> /mysql/data/mysql/tables_priv.MYI
lrwx------ 1 root root 64 Dec  5 08:27 25 -> /mysql/data/mysql/proxies_priv.MYD
lrwx------ 1 root root 64 Dec  5 08:27 24 -> /mysql/data/mysql/proxies_priv.MYI
lrwx------ 1 root root 64 Dec  5 08:27 23 -> /mysql/data/mysql/db.MYD
lrwx------ 1 root root 64 Dec  5 08:27 22 -> /mysql/data/mysql/db.MYI
lrwx------ 1 root root 64 Dec  5 08:27 21 -> /mysql/data/mysql/user.MYD
lrwx------ 1 root root 64 Dec  5 08:27 20 -> /mysql/data/mysql/user.MYI


同時,會對
同步的數(shù)據(jù)進行寫到內(nèi)核緩沖區(qū)同時FSYNC此文件然后關(guān)閉。
但是對于INNODB數(shù)據(jù)文件,未發(fā)現(xiàn)關(guān)閉文件的情況。


那么我們可以視乎的得出2個結(jié)論


1、flush table 會關(guān)閉MYISAM和CSV(對其他存儲引擎作用未知)的文件描述符,同時會寫臟數(shù)據(jù)到文件,同時關(guān)閉文件描述符,
   關(guān)閉文件。
2、flush table 在INNODB中不會真正的關(guān)閉文件描述符,同時也不會寫臟數(shù)據(jù),但是FLUSH TABLE確實會由于
   innodb中對文件操作而造成堵塞,堵塞等待為futex系統(tǒng)調(diào)用。所以flush tbale對INNODB可能用處并不大。
   
   
水平有限,還待學(xué)習(xí)。如有錯誤,請指正。


   
   
   
   
   






分享標(biāo)題:關(guān)于MYSQLflushtable的作用
鏈接地址:http://www.chinadenli.net/article10/gepodo.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供Google營銷型網(wǎng)站建設(shè)做網(wǎng)站企業(yè)建站網(wǎng)站設(shè)計響應(yīng)式網(wǎng)站

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

網(wǎng)站建設(shè)網(wǎng)站維護公司