做论坛网站4g空间够不够用,中山网站代运营,企业网站设计建设服务,wordpress相对地址通常#xff0c;我们很容易观察到数据库服务器的内存和CPU压力。但是对I/O压力没有直观的判断方法。磁盘有两个重要的参数#xff1a; Seek time、 Rotational latency。正常的I/O计数为#xff1a;①1000/(Seek timeRotational latency)*0.75#xff0c;在此范围内属正常。… 通常我们很容易观察到数据库服务器的内存和CPU压力。但是对I/O压力没有直观的判断方法。磁盘有两个重要的参数 Seek time、 Rotational latency。正常的I/O计数为①1000/(Seek timeRotational latency)*0.75在此范围内属正常。当达到85的I/O计数以上时则基本认为已经存在I/O瓶劲。理论情况下磁盘的随机读计数为125、顺序读计数为225。对于数据文件而言是随机读写日志文件是顺序读写。因此数据文件建议存放于RAID5上而日志文件存放于RAID10或RAID1中。 下面假设在有4块硬盘的RAID5中观察到的Physical Disk性能对象的部分值 Avg. Disk Queue Length 12 Avg. Disk Sec/Read .035 Avg. Disk Sec/Write .045 Disk Reads/sec 320 Disk Writes/sec 100 Avg. Disk Queue Length12/43每块磁盘的平均队列建议不超过2。 Avg. Disk Sec/Read一般不要超过1115ms。 Avg. Disk Sec/Write一般建议小于12ms。 从上面的结果我们看到磁盘本身的I/O能力是满足我们的要求的原因是因为有大量的请求才导致队列等待这很可能是因为你的SQL语句导致大量的表扫描所致。在进行优化后如果还是不能达到要求下面的公式可以帮助你计算使用几块硬盘可以满足这样的并发要求 Raid 0 -- I/Os per disk (reads writes) / number of disks Raid 1 -- I/Os per disk [reads (2 * writes)] / 2 Raid 5 -- I/Os per disk [reads (4 * writes)] / number of disks Raid 10 -- I/Os per disk [reads (2 * writes)] / number of disks 我们得到的结果是(320400)/4180这时你可以根据公式①来得到磁盘的正常I/O值。假设现在正常I/O计数为125为了达到这个结果720/1255.76。就是说要用6块磁盘才能达到这样的要求。 但是上面的Disk Reads/sec和Disk Writes/sec是个很难正确估算的值。因此只能在系统比较忙时大概估算一个平均值作为计算公式的依据。另一个是你很难从客户那里得到Seek time、 Rotational latency参数的值这也只能用理论值125进行计算。 ############################################# ############################################# 前言 作为一个数据库管理员关注系统的性能是日常最重要的工作之一而在所关注的各方面的性能只能IO性能却是最令人头痛的一块面对着各种生涩的参数和令人眼花缭乱的新奇的术语再加上存储厂商的忽悠总是让我们有种云里雾里的感觉。本系列文章试图从基本概念开始对磁盘存储相关的各种概念进行综合归纳让大家能够对IO性能相关的基本概念IO性能的监控和调整有个比较全面的了解。 在这一部分里我们先舍弃各种结构复杂的存储系统直接研究一个单独的磁盘的性能问题藉此了解各个衡量IO系统系能的各个指标以及之间的关系。 几个基本的概念 在研究磁盘性能之前我们必须先了解磁盘的结构以及工作原理。不过在这里就不再重复说明了关系硬盘结构和工作原理的信息可以参考维基百科上面的相关词条——Hard disk drive英文和硬盘驱动器中文。 读写IO(Read/Write IO)操作磁盘是用来给我们存取数据用的因此当说到IO操作的时候就会存在两种相对应的操作存数据时候对应的是写IO操作取数据的时候对应的是是读IO操作。单个IO操作当控制磁盘的控制器接到操作系统的读IO操作指令的时候控制器就会给磁盘发出一个读数据的指令并同时将要读取的数据块的地址传递给磁盘然后磁盘会将读取到的数据传给控制器并由控制器返回给操作系统完成一个写IO的操作同样的一个写IO的操作也类似控制器接到写的IO操作的指令和要写入的数据并将其传递给磁盘磁盘在数据写入完成之后将操作结果传递回控制器再由控制器返回给操作系统完成一个写IO的操作。单个IO操作指的就是完成一个写IO或者是读IO的操作。随机访问(Random Access)与连续访问(Sequential Access) 随机访问指的是本次IO所给出的扇区地址和上次IO给出扇区地址相差比较大这样的话磁头在两次IO操作之间需要作比较大的移动动作才能重新开始读/写数据。相反的如果当次IO给出的扇区地址与上次IO结束的扇区地址一致或者是接近的话那磁头就能很快的开始这次IO操作这样的多个IO操作称为连续访问。因此尽管相邻的两次IO操作在同一时刻发出但如果它们的请求的扇区地址相差很大的话也只能称为随机访问而非连续访问。顺序IO模式(Queue Mode)/并发IO模式(Burst Mode)磁盘控制器可能会一次对磁盘组发出一连串的IO命令如果磁盘组一次只能执行一个IO命令时称为顺序IO当磁盘组能同时执行多个IO命令时称为并发IO。并发IO只能发生在由多个磁盘组成的磁盘组上单块磁盘只能一次处理一个IO命令。 单个IO的大小(IO Chunk Size) 熟悉数据库的人都会有这么一个概念那就是数据库存储有个基本的块大小(Block Size)不管是SQL Server还是Oracle默认的块大小都是8KB就是数据库每次读写都是以8k为单位的。那么对于数据库应用发出的固定8k大小的单次读写到了写磁盘这个层面会是怎么样的呢就是对于读写磁盘来说单个IO操作操作数据的大小是多少呢是不是也是一个固定的值答案是不确定。首先操作系统为了提高 IO的性能而引入了文件系统缓存(File System Cache)系统会根据请求数据的情况将多个来自IO的请求先放在缓存里面然后再一次性的提交给磁盘也就是说对于数据库发出的多个8K数据块的读操作有可能放在一个磁盘读IO里就处理了。还有对于有些存储系统也是提供了缓存Cache的接收到操作系统的IO请求之后也是会将多个操作系统的 IO请求合并成一个来处理。不管是操作系统层面的缓存还是磁盘控制器层面的缓存目的都只有一个提高数据读写的效率。因此每次单独的IO操作大小都是不一样的它主要取决于系统对于数据读写效率的判断。 当一次IO操作大小比较小的时候我们成为小的IO操作比如说1K4K8K这样的当一次IO操作的数据量比较的的时候称为大IO操作比如说32K64K甚至更大。 在我们说到块大小Block Size的时候通常我们会接触到多个类似的概念像我们上面提到的那个在数据库里面的数据最小的管理单位Oralce称之为块(Block)大小一般为8KSQL Server称之为页(Page)一般大小也为8k。在文件系统里面我们也能碰到一个文件系统的块在现在很多的Linux系统中都是4K通过 /usr/bin/time -v可以看到它的作用其实跟数据库里面的块/页是一样的都是为了方便数据的管理。但是说到单次IO的大小跟这些块的大小都是没有直接关系的在英文里单次IO大小通常被称为是IO Chunk Size不会说成是IO Block Size的。 IOPS(IO per Second) IOPSIO系统每秒所执行IO操作的次数是一个重要的用来衡量系统IO能力的一个参数。对于单个磁盘组成的IO系统来说计算它的IOPS不是一件很难的事情只要我们知道了系统完成一次IO所需要的时间的话我们就能推算出系统IOPS来。 现在我们就来推算一下磁盘的IOPS假设磁盘的转速(Rotational Speed)为15K RPM平均寻道时间为5ms最大传输速率为40MB/s这里将读写速度视为一样实际会差别比较大。 对于磁盘来说一个完整的IO操作是这样进行的当控制器对磁盘发出一个IO操作命令的时候磁盘的驱动臂(Actuator Arm)带读写磁头(Head)离开着陆区(Landing Zone位于内圈没有数据的区域)移动到要操作的初始数据块所在的磁道(Track)的正上方这个过程被称为寻址(Seeking)对应消耗的时间被称为寻址时间(Seek Time)但是找到对应磁道还不能马上读取数据这时候磁头要等到磁盘盘片(Platter)旋转到初始数据块所在的扇区(Sector)落在读写磁头正上方的之后才能开始读取数据在这个等待盘片旋转到可操作扇区的过程中消耗的时间称为旋转延时(Rotational Delay)接下来就随着盘片的旋转磁头不断的读/写相应的数据块直到完成这次IO所需要操作的全部数据这个过程称为数据传送(Data Transfer)对应的时间称为传送时间(Transfer Time)。完成这三个步骤之后一次IO操作也就完成了。 在我们看硬盘厂商的宣传单的时候我们经常能看到3个参数分别是平均寻址时间、盘片旋转速度以及最大传送速度这三个参数就可以提供给我们计算上述三个步骤的时间。 第一个寻址时间考虑到被读写的数据可能在磁盘的任意一个磁道既有可能在磁盘的最内圈寻址时间最短也可能在磁盘的最外圈寻址时间最长所以在计算中我们只考虑平均寻址时间也就是磁盘参数中标明的那个平均寻址时间这里就采用当前最多的10krmp硬盘的5ms。 第二个旋转延时和寻址一样当磁头定位到磁道之后有可能正好在要读写扇区之上这时候是不需要额外额延时就可以立刻读写到数据但是最坏的情况确实要磁盘旋转整整一圈之后磁头才能读取到数据所以这里我们也考虑的是平均旋转延时对于10krpm的磁盘就是(60s/15k)*(1/2) 2ms。 第三个传送时间磁盘参数提供我们的最大的传输速度当然要达到这种速度是很有难度的但是这个速度却是磁盘纯读写磁盘的速度因此只要给定了单次 IO的大小我们就知道磁盘需要花费多少时间在数据传送上这个时间就是IO Chunk Size / Max Transfer Rate。 现在我们就可以得出这样的计算单次IO时间的公式 IOTime SeekTime 60sec/RotationalSpeed/2 IOChunkSize/TransferRate 于是我们可以这样计算出IOPS IOPS 1/IOTime 1/(SeekTime 60sec/RotationalSpeed/2 IOChunkSize/TransferRate) 对于给定不同的IO大小我们可以得出下面的一系列的数据 4K(1/7.1ms 140IOPS) 5ms (60sec/15000RPM/2) 4K/40MB 5 2 0.1 7.1 8k(1/7.2ms 139IOPS) 5ms (60sec/15000RPM/2) 8K/40MB 5 2 0.2 7.2 16K(1/7.4ms 135IOPS) 5ms (60sec/15000RPM/2) 16K/40MB 5 2 0.4 7.4 32K(1/7.8ms 128IOPS) 5ms (60sec/15000RPM/2) 32K/40MB 5 2 0.8 7.8 64K(1/8.6ms 116IOPS) 5ms (60sec/15000RPM/2) 64K/40MB 5 2 1.6 8.6 从上面的数据可以看出当单次IO越小的时候单次IO所耗费的时间也越少相应的IOPS也就越大。 上面我们的数据都是在一个比较理想的假设下得出来的这里的理想的情况就是磁盘要花费平均大小的寻址时间和平均的旋转延时这个假设其实是比较符合我们实际情况中的随机读写在随机读写中每次IO操作的寻址时间和旋转延时都不能忽略不计有了这两个时间的存在也就限制了IOPS的大小。现在我们考虑一种相对极端的顺序读写操作比如说在读取一个很大的存储连续分布在磁盘的的文件因为文件的存储的分布是连续的磁头在完成一个读IO操作之后不需要从新的寻址也不需要旋转延时在这种情况下我们能到一个很大的IOPS值如下 4K(1/0.1ms 10000IOPS) 0ms 0ms 4K/40MB 0.1 8k(1/0.2ms 5000IOPS) 0ms 0ms 8K/40MB 0.2 16K(1/0.4ms 2500IOPS) 0ms 0ms 16K/40MB 0.4 32K(1/0.8ms 1250IOPS) 0ms 0ms 32K/40MB 0.8 64K(1/1.6ms 625IOPS) 0ms 0ms 64K/40MB 1.6 相比第一组数据来说差距是非常的大的因此当我们要用IOPS来衡量一个IO系统的系能的时候我们一定要说清楚是在什么情况的IOPS也就是要说明读写的方式以及单次IO的大小当然在实际当中特别是在OLTP的系统的随机的小IO的读写是最有说服力的。 传输速度(Transfer Rate)/吞吐率(Throughput) 现在我们要说的传输速度另一个常见的说法是吞吐率不是磁盘上所表明的最大传输速度或者说理想传输速度而是磁盘在实际使用的时候从磁盘系统总线上流过的数据量。有了IOPS数据之后我们是很容易就能计算出对应的传输速度来的 TransferRate IOPS * IOChunkSize 还是那上面的第一组IOPS的数据我们可以得出相应的传输速度如下 4K: 140 * 4K 560K / 40M 1.36% 8K: 139 * 8K 1112K / 40M 2.71% 16K: 135 * 16K 2160K / 40M 5.27% 32K: 116 * 32K 3712K / 40M 9.06% 可以看出实际上的传输速度是很小的对总线的利用率也是非常的小。 这里一定要明确一个概念那就是尽管上面我们使用IOPS来计算传输速度但是实际上传输速度和IOPS是没有直接关系在没有缓存的情况下它们共同的决定因素都是对磁盘系统的访问方式以及单个IO的大小。对磁盘进行随机访问时候我们可以利用IOPS来衡量一个磁盘系统的性能此时的传输速度不会太大但是当对磁盘进行连续访问时此时的IOPS已经没有了参考的价值这个时候限制实际传输速度却是磁盘的最大传输速度。因此在实际的应用当中只会用IOPS来衡量小IO的随机读写的性能而当要衡量大IO连续读写的性能的时候就要采用传输速度而不能是IOPS了。 IO响应时间(IO Response Time) 最后来关注一下能直接描述IO性能的IO响应时间。IO响应时间也被称为IO延时(IO Latency)IO响应时间就是从操作系统内核发出的一个读或者写的IO命令到操作系统内核接收到IO回应的时间注意不要和单个IO时间混淆了单个IO时间仅仅指的是IO操作在磁盘内部处理的时间而IO响应时间还要包括IO操作在IO等待队列中所花费的等待时间。 计算IO操作在等待队列里面消耗的时间有一个衍生于利托氏定理(Little’s Law)的排队模型M/M/1模型可以遵循由于排队模型算法比较复杂到现在还没有搞太明白如果有谁对M/M/1模型比较精通的话欢迎给予指导这里就罗列一下最后的结果还是那上面计算的IOPS数据来说 8KIOChunkSize(135IOPS, 7.2ms) 135 240.0ms 105 29.5ms 75 15.7ms 45 10.6ms 64KIOChunkSize(116IOPS, 8.6ms) 135 没响应了…… 105 88.6ms 75 24.6ms 45 14.6ms 从上面的数据可以看出随着系统实际IOPS越接近理论的最大值IO的响应时间会成非线性的增长越是接近最大值响应时间就变得越大而且会比预期超出很多。一般来说在实际的应用中有一个70%的指导值也就是说在IO读写的队列中当队列大小小于最大IOPS的70%的时候IO的响应时间增加会很小相对来说让人比较能接受的一旦超过70%响应时间就会戏剧性的暴增所以当一个系统的IO压力超出最大可承受压力的70%的时候就是必须要考虑调整或升级了。 另外补充说一下这个70%的指导值也适用于CPU响应时间这也是在实践中证明过的一旦CPU超过70%系统将会变得受不了的慢。很有意思的东西。 从上一篇文章的计算中我们可以看到一个15k转速的磁盘在随机读写访问的情况下IOPS竟然只有140左右但在实际应用中我们却能看到很多标有5000IOPS甚至更高的存储系统有这么大IOPS的存储系统怎么来的呢这就要归结于各种存储技术的使用了在这些存储技术中使用最广的就是高速缓存(Cache)和磁盘冗余阵列(RAID)了本文就将探讨缓存和磁盘阵列提高存储IO性能的方法。 高速缓存(Cache) 在当下的各种存储产品中按照速度从快到慢应该就是内存闪存磁盘磁带了然而速度越快也就意味着价格越高闪存虽然说是发展势头很好但目前来说却还是因为价格问题无法普及因此现在还是一个磁盘作霸王的时代。与CPU和内存速度相比磁盘的速度无疑是计算机系统中最大的瓶颈了所以在必须使用磁盘而又想提高性能的情况下人们想出了在磁盘中嵌入一块高速的内存用来保存经常访问的数据从而提高读写效率的方法来折中的解决这块嵌入的内存就被称为高速缓存。 说到缓存这东西应用现在已经是无处不在从处于上层的应用到操作系统层再到磁盘控制器还有CPU内部单个磁盘的内部也都存在缓存所有这些缓存存在的目的都是相同的就是提高系统执行的效率。当然在这里我们只关心跟IO性能