19-MySQL DBA笔记-操做系统、硬件、网络的优化

第19章 操做系统、硬件、网络的优化
本章将介绍操做系统和硬件的性能优化,对于硬件,咱们主要讲述CPU、内存、磁盘阵列及固态硬盘。
任何优化,首先都须要有足够的数据支持,对于操做系统下性能数据的收集,这里将再也不赘述,请参考前面章节的相关内容。
19.1 基本概念
以下是须要了解的一些基本概念。
(1)什么是进程
进程能够简单地理解为程序加数据,程序自己只是指令、数据及其组织形式的描述,进程才是程序(那些指令和数据)的真正运行实例。
若干进程都有可能与同一个程序有关系,且每一个进程均可以用同步(循序)或异步(平行)的方式独立运行。
用户下达运行程序的命令以后,就会产生进程。
同一程序能够产生多个进程(一对多的关系),以容许同时有多位用户运行同一程序,却不会发生冲突。
进程在运行时,状态会发生改变,如新生、运行、等待、就绪、结束等,各状态的名称也可能会随着操做系统的不一样而不一样。
(2)什么是线程
线程是操做系统可以进行运算调度的最小单位。它被包含在进程之中,是进程中的实际运做单位。
一个进程能够有许多线程,每条线程并行执行不一样的任务。
使用多线程技术(多线程即每个线程都表明一个进程内的一个独立执行的控制流)的操做系统或计算机架构,
同一个程序的平行线程,可在多CPU主机或网络上真正作到同时运行(在不一样的CPU上)。
多线程技术可让一个进程充分利用多个CPU。
同一进程中的多条线程将会共享该进程中的所有系统资源,如虚拟地址空间、文件描述符和信号处理等。
但同一进程中的多个线程也都有各自的调用栈(callstack)、寄存器环境(registercontext)和线程本地存储(thread localstorage)。
在多核或多CPU上使用多线程程序设计的好处是显而易见的,即提升了程序的执行吞吐率。
(3)什么是内核调度
内核调度将把CPU的运行时间分红许多片,而后安排给各个进程轮流运行,使得全部进程仿佛在同时运行,
内核须要决定运行哪一个进程/线程,哪一个须要等待,选择要在哪一个CPU核上运行线程。
内核运行于一个特殊的CPU态,内核态。
拥有彻底的权限访问设备,内核将仲裁对设备的访问,以支持多任务,避免用户进程访问彼此的空间而破坏数据,除非显式被容许访问。
用户程序通常运行在用户态,它们经过系统调用的方式执行一些限制权限的操做,例如I/O操做。
(4)什么是虚拟内存
虚拟内存是计算机系统内存管理的一种技术。
它使得应用程序认为它拥有连续的、可用的内存(一个连续的、完整的地址空间),
而实际上,它一般是被分隔成多个物理内存碎片,还有部分被暂时存储在外部磁盘存储器上,在须要时将会进行数据交换。
与没有使用虚拟内存技术的系统相比,使用这种技术的系统将使得大型程序的编写变得更容易,对真正的物理内存(例如RAM)的使用也更有效率。
对虚拟内存的定义是基于对地址空间的重定义的,即把地址空间定义为“连续的虚拟内存地址”,以此来“欺骗”程序,使它们觉得本身正在使用一大块的“连续”的地址。
对于每一个进程或内核而言,它们操做大块的虚拟内存,而实际虚拟内存到物理内存的映射,是由咱们的虚拟内存管理系统来实现的,
也就是说,虚拟内存给进程或内核提供了一个它们独有的几乎无限内存的视图。
对于操做系统的优化,主要是对一些内核参数及文件系统进行优化。
因为默认的Linux内核参数已经基本够用,所以本书将只关注文件系统的优化。 算法

19.2 文件系统的优化
文件系统是一种向用户提供底层数据访问的机制。它将设备中的空间划分为特定大小的块(扇区),通常每块有512B。
数据存储在这些块中,由文件系统软件来负责将这些块组织为文件和目录,并记录哪些块被分配给了哪一个文件,以及哪些块没有被使用。
如下仅针对文件系统和MySQL相关的部分作一些说明。
经常使用的文件系统有ext三、ext四、XFS等,你能够检查Linux系统的/etc/fstab文件,以肯定当前分区使用的是什么文件系统,
ext3即第三代扩展文件系统,是一个日志文件系统,低版本的Linux发行版将会使用到这种文件系统,它存在的一个问题是删除大文件时比较缓慢,这可能会致使严重的I/O问题。
ext4即第四代扩展文件系 统,是ext3文件系统的后继版本。2008年12月25日,Linux 2.6.29版公开发布以后,ext4成为了Linux官方建议的默认的文件系统。
ext4改进了大文件的操做效率,使删除大的数据文件再也不可能致使严重的I/O性能问题,一个100多GB的文件,也只须要几秒就能够被删除掉。
文件系统使用缓存来提高读性能,使用缓冲来提高写性能。
在咱们调整操做系统和数据库的时候,要注意批量写入数据的冲击,一些系统会缓冲写数据几十秒,而后合并刷新到磁盘中,这将表现为时不时的I/O冲击。
默认状况下,Linux会记录文件最近一次被读取的时间信息,咱们能够在挂载文件系统的时候使用noatime来提高性能。
为了保证数据的安全,Linux默认在进行数据提交的时候强制底层设备刷新缓存,
对于可以在断电或发生其余主机故障时保护缓存中数据的设备,应该以nobarrier选项挂载XFS文件系统,
也就是说,若是咱们使用带电池的RAID卡,或者使用Flash卡,那么咱们可使用nobarrier选项挂载文件系统,由于带电池的RAID卡和FLASH卡自己就有数据保护的机制。
还有其余的一些挂载参数也会对性能产生影响,你须要衡量调整参数所带来的益处是否值得,笔者通常不建议调整这些挂载参数,它们对性能的提高并不显著。
你可能须要留意文件系统的碎片化,碎片化意味着文件系统上的文件数据块存放得不那么连续,而是以碎片化的方式进行分布,那么顺序I/O将得不到好的性能,会变成屡次随机I/O。
因此在某些状况下,使用大数据块和预先分配连续的空间是有道理的,但你也须要知道,文件碎片是一个常态,最开始的表没有什么碎片,
但随着你更新和删除数据,数据表会变得碎片化,这会是一个长期的过程,并且在绝大多数状况下,你会感受不到表的碎片对于性能的影响,
所以,除非你可以证实表的碎片化已经严重影响了性能,不然不建议进行表的整理,好比运行OPTIMIZE TABLE命令。
Direct I/O容许应用程序在使用文件系统的同时绕过文件系统的缓存。
你能够用Direct I/O执行文件备份,这样作能够避免缓存那些只被读取一次的数据。
若是应用或数据库,已经实现了本身的缓存,那么使用Direct I/O能够避免双重缓存。
许多人指望使用mmap的方式来解决文件系统的性能问题,mmap的方式有助于咱们减小一些系统调用,
可是,若是咱们碰到的是磁盘I/O瓶颈,那么减小一些系统调用的开销,对于提高总体性能/吞吐的贡献将会不多。由于主要的瓶颈,主要花费的时间是在I/O上。
许多NoSQL的数据库使用了mmap的方式来持久化数据,在I/O写入量大的时候,其性能急剧降低就是这个道理。
通常来讲,文件系统缓存,对于MySQL的帮助不大,能够考虑减少文件系统缓存,如vm.dirty_ratio=5。
咱们推荐在Linux下使用XFS文件系统,它是一种高性能的日志文件系统,特别擅长处理大文件,对比ext三、ext4,MySQL在XFS上通常会有更好的性能,更高的吞吐。
Red Hat Enterprise Linux 7默认使用XFS文件系统。
Red Hat Enterprise Linux 五、6的内核完整支持XFS,但未包含建立和使用XFS的命令行工具,你须要自行安装。 数据库

19.3 内存
咱们须要了解CPU、内存、固态硬盘及普通机械硬盘访问速度的差别,
好比内存为几十纳秒(ns),而固态硬盘大概是25μs(25000ns),而机械硬盘大概是6毫秒(6000000ns),
它们差得不是一两个数量级,机械硬盘对比内存差了五六个数量级,因此内存访问比磁盘访问要快得多,
因此总会有许多人想尽办法优化数据的访问,尽可能在内存当中来访问数据。
内存每每是影响性能最重要的因素,你应该确保热点数据存储在内存中,较少的内存每每意味着更多的I/O压力。
许多应用通常是有热点数据的,且热点数据并不大,能够保存在内存中。
对于MySQL来讲,应将innodb_buffer_pool_size设置得大于咱们的热点数据,
不然可能会出现某个MySQL实例InnoDB的缓冲不够大,从而产生过多的物理读,进而致使I/O瓶颈。
数据库服务器应该只部署数据库服务,以避免被其余程序影响,有时其余程序也会致使内存压力,如占据大量文件的系统缓存,就会致使可用内存不够。 后端

19.4 CPU
现实世界中,CPU的技术发展得很快,一颗CPU上每每集成了4/6/8个核,因为多核不多会所有利用到,因此通常会在生产机器上部署多实例,以充分利用CPU资源。
还能够更进一步,使用CPU绑定技术将进程或线程绑定到一个CPU或一组CPU上,这样作能够提高CPU缓存的效率,提高CPU访问内存的性能。
对于NUMA架构的系统,也能够提升内存访问的局部性,从而也能提升性能。
CPU利用率衡量的是在某个时间段,CPU忙于执行操做的时间的百分比,可是,许多人不知道的是,CPU利用率高并不必定是在执行操做,而极可能是在等待内存I/O。
CPU执行指令,须要多个步骤,这其中,内存访问是最慢的,可能须要几十个时钟周期来读写内存。因此CPU缓存技术和内存总线技术是很是重要的。
咱们对CPU时钟频率这个主要的指标可能有一些误解。若是CPU利用率高,那么更快的CPU不必定可以提高性能。
也就是说,若是CPU的大部分时间是在等待锁、等待内存访问,那么使用更快的CPU不必定可以提升吞吐。
关于容量规划。
对于访问模式比较固定的应用,好比一些传统制造业的生产系统,则比较容易对CPU进行容量规划,
能够按照将来的访问请求或访问客户端数量,肯定CPU须要扩容的幅度,
你能够监控当前系统的CPU利用率,估算每一个客户端/每一个访问请求的CPU消耗,进而估算CPU100%利用率时的吞吐,安排扩容计划。
因为互联网业务,负荷每每变化比较大,多实例有时会致使CPU的容量模型更为复杂,
咱们更多地依靠监控的手段提早进行预警,在CPU到达必定利用率,负载到达必定阈值时,进行优化或扩容。
如何选购CPU。
对于企业用户来讲,CPU的性能并非最重要的,最重要的是性价比,新上市的CPU每每价格偏贵,通常来讲建议选择上市已经有必定时间的CPU。
而对于大规模采购,你须要衡量不一样CPU的价格及测试验证明际业务的吞吐,进而可以得出一个预算成本比较合适的方案,
可能你还须要综合平衡各类其余硬件的成本以肯定选购的CPU型号。 缓存

19.5 I/O
19.5.1 概述
I/O每每是数据库应用最须要关注的资源。做为数据库管理人员,你须要作好磁盘I/O的监控,持续优化I/O的性能,以避免I/O资源成为整个系统的瓶颈。
本节将讲述一些硬件维护人员须要了解的磁盘硬件知识,并对其的规划和调整作一些介绍。
一些基础概念的介绍以下:
逻辑I/O:能够理解为是应用发送给文件系统的I/O指令。
物理I/O:能够理解为是文件系统发送给磁盘设备的I/O指令。
磁盘IOPS:每秒的输入输出量(或读写次数),是衡量磁盘性能的主要指标之一。
IOPS是指单位时间内系统能处理的I/O请求数量,通常以每秒处理的I/O请求数量为单位,I/O请求一般为读或写数据操做的请求。OLTP应用更看重IOPS。
磁盘吞吐:指单位时间内能够成功传输的数据数量。OLAP应用更看重磁盘吞吐。
实践当中,咱们要关注的磁盘I/O的基本指标有磁盘利用率、平均等待时间、平均服务时间等。
若是磁盘利用率超过60%,则可能致使性能问题,磁盘利用率每每是你们容易忽视的一个指标,认为磁盘利用率没有达到100%,就能够接受,
其实,磁盘利用率在超过60%的时候,就应该考虑进行优化了。
对于磁盘利用率的监控,在生产中,每每也会犯一个错误,因为监控的粒度太大,好比10分钟、2分钟一次,所以会没有捕捉到磁盘高利用率的场景。
Linux有4种I/O调度算法:CFQ、Deadline、Anticipatory和NOOP,CFQ是默认的I/O调度算法。
在彻底随机的访问环境下,CFQ与Deadline、NOOP的性能差别很小,
可是一旦有大的连续I/O,CFQ可能会形成小I/O的响应延时增长,数据库环境能够修改成Deadline算法,表现也将更稳定。
以下命令将实时修改I/O调度算法: echo deadline > /sys/block/sdb/queue/scheduler
若是你须要永久生效,则能够把命令写入/etc/rc.local文件内,或者写入grub.conf文件中。 安全

19.5.2 传统磁盘
传统磁盘本质上是一种机械装置,影响磁盘的关键因素是磁盘服务时间,即磁盘完成一个I/O请求所花费的时间,它由寻道时间、旋转延迟和数据传输时间三部分构成。
通常读取磁盘的时候,步骤以下:
1)寻道:磁头移动到数据所在的磁道。
2)旋转延迟:盘片旋转将请求数据所在的扇区移至读写磁头下方。
3)传输数据。
通常随机读写取决于前两个步骤,而大数据顺序读写更多地取决于第3)个步骤,因为固态硬盘消除了前两个步骤,因此在随机读写上会比传统机械硬盘的IOPS高得多。
优化传统磁盘随机读写,也就是优化寻道时间和旋转延迟时间,一些可供考虑的措施有缓存、分离负载到不一样的磁盘、硬件优化减小延时及减小震荡等。
好比,操做系统和数据库使用的是不一样的盘,咱们须要了解读写比率,若是大部分是读的负载,那么咱们加缓存会更有效;
而若是大部分是写的负载,那么咱们增长磁盘提升吞吐会更有意义。
对于Web访问,因为自己就可能有几百毫秒的延时,那么100毫秒的磁盘延时也许并非问题;
而对于数据库应用,对于延时则要求很苛刻,那么咱们须要优化或使用延时更小的磁盘。
对于数据库类应用,传统磁盘通常作了RAID,那么RAID卡自身也可能会成为整个系统的瓶颈,也须要考虑优化。 性能优化

19.5.3 关于RAID
几种经常使用的RAID类型以下:
RAID0:将两个以上的磁盘串联起来,成为一个大容量的磁盘。
在存放数据时,数据被分散地存储在这些磁盘中,由于读写时均可以并行处理,因此在全部的级别中,RAID0的速度是最快的。
可是RAID0既没有冗余功能,也不具有容错能力,若是一个磁盘(物理)损坏,那么全部的数据都会丢失。
RAID1:RAID1就是镜像,其原理为在主硬盘上存放数据的同时也在镜像硬盘上写同样的数据。当主硬盘(物理)损坏时,镜像硬盘则代替主硬盘工做。
由于有镜像硬盘作数据备份,因此RAID1的数据安全性在全部的RAID级别上来讲是最好的。
理论上读取速度等于硬盘数量的倍数,写入速度有微小的下降。
Raid10:指的是RAID1+0,RAID1提供了数据镜像功能,保证数据安全,RAID0把数据分布到各个磁盘,提升了性能。
RAID5:是一种性能、安全和成本兼顾的存储解决方案。
RAID5至少须要3块硬盘,RAID5不是对存储的数据进行备份,而是把数据和相对应的奇偶校验信息存储到组成RAID5的各个磁盘上。
当RAID5的一个磁盘数据被损坏后,能够利用剩下的数据和相应的奇偶校验信息去恢复被损坏的数据。
几种RAID的区别以下:
1)RAID10理论上能够提供比RAID5更好的读写性能由于它不须要进行奇偶性校验。
RAID5具备和RAID0相近似的数据读取速度,只是由于多了一个奇偶校验信息,写入数据的速度相对单独写入一块硬盘的速度略慢。
2)RAID10提供了更高的安全性。RAID5只能坏一块盘,RAID10视状况而定,最多能够坏一半数量的硬盘。
3)RAID5成本更低,也就是说空间利用率更高。RAID5能够理解为是RAID0和RAID1的折中方案。
RAID5能够为系统提供数据安全保障,但保障程度要比镜像低而磁盘空间利用率要比镜像高,存储成本相对较便宜。
以上的区别是一些理论上的说明,实际状况可能还会由于算法、缓存的设计而不一样。
咱们是使用多个RAID,仍是使用一个大RAID,将取决于咱们是否有足够多的磁盘。
若是咱们有许多盘,好比超过10多块盘,那么咱们使用多个阵列,是可取的;
而若是你只有几块盘,好比6块盘,那么单独使用两块盘来作一个RAID1用于存放操做系统,就不太可取了。
RAID卡有两种写入策略:Write Through和Write Back。
Write Through:将数据同步写入缓存(如有Cache的状况)和后端的物理磁盘。
Write Back:将数据写入缓存,而后再批量刷新到后端的物理磁盘。
通常状况下,对于带电池模块的RAID卡,咱们将写入策略设置为Write Back。写缓存能够大大提升I/O性能,但因为掉电会丢失数据,因此须要用带电池的RAID卡。
若是电池模块异常,那么为了数据安全,会自动将写入策略切换为Write Through,因为没法利用缓存写操做,所以写入性能会大大下降。
通常的RAID卡电池模块仅仅保证在服务器掉电的状况下,Cache中的数据不会丢失,在电池模块电量耗尽前须要启动服务器让缓存中的数据写盘。
若是咱们碰到I/O瓶颈,咱们须要更强劲的存储。普通的PC服务器加传统磁盘RAID(通常是RAID1+0)加带电池的RAID卡,是一种常见的方案。
在RAID的设置中,咱们须要关闭预读,磁盘的缓存也须要被关闭。一样的,你须要关闭或减小操做系统的预读。 服务器

19.5.4 关于SSD
SSD也称为固态硬盘,目前SSD设备主要分为两类,基于PCI-E的SSD和普通SATA接口的SSD。
PCE-E SSD卡性能高得多,能够达到几十万IOPS,容量能够达到几个TB以上,经常使用的品牌有Fusion-io,而普通的SSD虽然才几千IOPS,但性价比更好,经常使用的品牌有Intel等。
PCI-E相对来讲稳定性、可靠性都更好,因为I/O资源的极大富余,能够大大节省机架。
普通SSD,基于容量和安全的考虑,许多公司仍然使用了RAID技术,随着SSD容量的增大和可靠性的提高,RAID技术再也不显得重要甚至再也不被使用。
因为许多公司的SSD的I/O资源每每运行不饱和,所以SSD的稳定、性能一致、安全、寿命显得更重要,而性能可能不是最须要考虑的因素。
依据笔者的使用经验,许多SSD的设备故障,其缘由并不在于SSD设备自己,而在于SSD设备和传统电器组件之间的链接出现了问题,
主机搭载传统机械硬盘的技术已经很是成熟,而在主机上搭载SSD,仍然须要时间来提升其可靠性。
因此咱们在选购主机的时候,SSD在其上运行的可靠性也是一个要考虑的因素。
咱们对于磁盘RAID也应该加以监控,防止由于磁盘RAID异常而致使数据文件损毁。
传统的机械硬盘,瓶颈每每在于I/O,而在使用了固态硬盘以后,整个系统的瓶颈开始转向CPU,甚至在极端状况下,还会出现网络瓶颈。
因为固态硬盘的性能比较优越,DBA再也不像之前那样须要常常进行I/O优化,能够把更多的时间和精力放在业务逻辑的设计上,
固态硬盘的成本下降了,也能够节省内存的使用,热点数据不必定须要常驻内存,即便有时须要从磁盘上访问,也可以知足响应的需求了。
传统的I/O隔离和虚拟化难度较高,很重要的缘由是I/O资源自己就比较紧缺,自己就紧缺的资源,难以进行分割和共享,而高性能的PCI-E SSD卡使得虚拟化更可能落地。
传统的文件系统已经针对传统的机械磁盘阵列有许多优化,因此想在其上再作一些软件层的优化和算法设计,极可能会费力不讨好,
可是若是是SSD设备,则另当别论,用好了SSD设备,可能能够大大减小SSD设备的故障率,充分利用它的潜能,
随着固态硬盘大规模的使用,将来将须要在文件系统和数据库引擎上都作出相应的优化,以减小使用SSD的成本。 网络

19.6 网络
对于数据库应用来讲,网络通常不会成为瓶颈,CPU和I/O更容易成为瓶颈。
网络的瓶颈通常表现为流量超过物理极限,若是超过了单块网卡的物理极限,那么你能够考虑使用网卡绑定的技术增长网络带宽,同时也能提升可用性,
若是是超过了运营商的限制,那么你须要快速定位流量大的业务,以减小流量,而请运营商调整带宽在短期内可能难以完成。
网络瓶颈也可能由于网络包的处理而致使CPU瓶颈。
交换机和路由器经过微处理器处理网络包,它们也可能会成为瓶颈,
对于主机来讲,若是对于网络包的处理没有一个CPU负载均衡策略,那么网卡流量只能被一个CPU处理,CPU也可能会成为瓶颈。
网络端口,也可能会成为瓶颈所在,不过这种状况不多见,即便是有大量短链接的场合。
首先你须要优化链接,减小短链接,或者使用链接池,若是实在优化不下去了,能够考虑修改系统的内核参数net/ipv4/ip_local_port_range,调整随机端口范围,
或者减小net/ipv4/tcp_fin_timeout的值,或者使用多个逻辑IP扩展端口的使用范围。
在进行网络优化以前,咱们须要清楚本身的网络架构,了解你应用的网络数据流路径,
好比是否通过了DNS服务器,你须要使用网络监控工具好比Cacti监控流量,在超过必定阈值或有丢包的状况下及时预警。
你须要意识到,跨IDC的网络彻底不能和IDC内网的质量相比,且速度也可能会成为问题,
跨IDC复制,其实本质上是为了安全,是为了在其余机房中有一份数据,而不是为了实时同步,也不能要求必须是实时同步。
你须要确保应用程序可以处理网络异常,若是两个节点间距离3000英里 [1],光速是186000英里/秒,那么单程须要16毫秒,来回就须要32毫秒,
而后节点之间还有各类设备(路由器、交换机、中继器),它们均可能影响到网络质量。
因此,若是你不得不进行跨IDC的数据库同步,或者让应用程序远程访问数据库,
那么你须要确保你的应用程序可以处理网络异常,你须要确认因为跨IDC网络异常致使的复制延时不致影响到业务。
因为网络异常,Web服务器可能链接数暴涨、挂死、启动缓慢(因为须要初始化链接池),这些都是潜在的风险,你须要当心处理。
当有新的链接进来时,MySQL主线程须要花一些时间(尽管不多)来检查链接并启动一个新的线程,
MySQL有一个参数back_log来指定在中止响应新请求前在短期内能够堆起多少请求,
你能够将其理解为一个新链接的请求队列,若是你须要在短期内容许大量链接,则能够增长该数值。
Linux操做系统也有相似的参数 net.core.somaxconn、tcp_max_syn_backlog,你可能须要增大它们。 多线程

小结:
本章介绍了文件系统及硬件的一些知识。
读者平时应该关注资源的使用状况,并跟踪硬件的发展。
经过对操做系统的观察,如资源的使用状况和报错日志,在某些状况下更容易发现程序的性能问题。
本书介绍的许多知识都只是“泛泛而谈”,笔者本身也不多对操做系统或硬件进行调优,读者若是有兴趣深刻研究操做系统和硬件,那么建议多阅读相关领域的专门著做。
[1] 1英里=1.609公里。架构

相关文章
相关标签/搜索