当前位置: 首页 > Linux

linux性能调优总结

时间:2023-04-06 04:18:37 Linux

系统性能一直是热门话题。本人在运维这几年一直从事性能调优,写这篇文章也算是对自己工作的一个总结。调优的第一步就是说说为什么需要调优?也就是系统分析。分析也需要有指标。在性能监控的情况下,只有在发现确实需要调优时才可以进行。不是为了调优而“调优”。那不是调整,那是破坏。性能分析的目的是找出系统性能的瓶颈,为以后的优化提供解决方案或参考,达到善用资源的目的。硬件资源和软件配置。影响性能的因素要确定哪些因素,首先要确定您拥有什么类型的应用程序?例如:cpu密集型,比如像nginxnode.js这样的web服务器需要CPU进行批处理和数学计算,这些都是IO密集型的,比如数据库中常见的mysql,非常消耗内存和存储系统,对CPU和网络要求不高。本应用使用CPU发起IO请求,然后进入休眠状态。确定应用类型后,开始分析哪些条件会影响性能:大量的网页请求会填满运行队列,大量的上下文切换,中断大量的磁盘请求,大量的吞吐量网卡和内存耗尽。.它归结为4个用于cpumemoryi/onetwork系统检测的工具。我们知道这四个块会影响我们的性能,那么我们有什么工具来检测呢?上图是国外高手总结的。个人在工作中经常用到的有:htopvmstatiotopsarstraceiftopsslsofethtoolmtr等。另外推荐阿里的tsar和glances做系统性能监控。CPU性能监控和调优我们可以通过检查cpu使用情况,通过工具观察上下文切换、中断和代码调用来进行优化。先澄清几个名词:缓存:cpu为了提供内存I/O性能而提供的硬件级缓存。查看缓存可以使用lscpu-p命令查看#lscpuL1d缓存:32KL1i缓存:32KL2缓存:256KL3缓存:8192K一级缓存是静态缓存,分为数据缓存和指令缓存。二级和三级缓存是动态缓存,二级缓存是共享缓存。为了提高cpucache的命中率,我们通常的做法是将cpu绑定到某个core上,即“cpuaffinity”。在linux下,我们可以使用“taskset”命令来实现#taskset-pc073890pid73890'scurrentaffinitylist:0pid73890'snewaffinitylist:0但是还是有问题。比如不能保证本地内存分配,那么这时候就需要使用numa来解决NUMA的问题:非统一内存访问机制。每个物理核心都有一段自己使用的内存作为本地节点,有自己的内存控制器,距离最近的内存节点称为关键节点。上图是numa的简单拓扑图,来自网络。numactl可以将程序绑定到特定的numa节点#numactl--show#查看当前numa配置策略:defaultpreferrednode:currentphyscpubind:0cpubind:0nodebind:0membind:0注意:数据库服务器不要使用numa,如果你想使用请在启动数据库时使用numactl--interleave=all。作为运维,可能已经被坑了。cpuschedulingstrategy实时调度策略SCHED_FIFO静态调度策略,一旦cpu被占用,就会一直运行,直到有更高优先级的任务到来或者自己放弃。SCHED_RR时间轮询策略,当进程的时间片用完后,系统会重新分配时间片,放在就绪队列的尾部。将其放在队列的末尾可确保公平调度所有具有相同优先级的RR任务。实时调度策略的取值为1-99,数字越大优先级越高。通用策略SCHED_OTHER默认调度策略由nice和counter值决定权重。nice越小,counter越大,被调度的概率越大,也就是占用CPU最少的进程会被优先调度。效果值为100-139,数字越小,优先级越高。SCHED_BATCHSCHED_IDLEchrt修改实时优先级,生产中一般不修改,默认为rr调度SCHED_OTHER使用nice,renice修改。另外,other支持动态调整。如果直接手动修改,就可以很好的完成。上下文切换:上下文切换linux内核以将每个内核视为一个独立的处理器。一个核心可以同时运行50~50000个进程。每个线程都会被分配一个时间片,直到线程的时间片用完,或者被更高优先级的线程抢占,才会被放回cpu队列。线程切换的过程就是上下文切换。上下文切换越高,内核调度的工作量就越大。vmstat可以看到csrunqueuerunqueue的级别每个cpu都有一个runqueue。线程要么处于睡眠状态(阻塞并等待IO),要么处于运行状态。运行队列越长,等待CPU处理线程的时间就越长。运行队列是全局的,将由所有CPU共享。负载用于描述运行队列。它的值等于当前正在处理的线程+运行队列中的线程。比如当前系统的核心数是2,两个线程在执行行,运行队列中有4个线程,那么它的load=2+4。vmstatwuptime都可以观察到运行队列的负载情况。说了这么多cpu性能监控,那么正常情况下我们需要观察哪些值呢?首先,numa和算法是在特殊情况下优化的。通常,它们不会更改。你需要根据你的业务场景做绑定调整,比如虚拟化、云计算等可能需要调整。那么我们日常需要观察的性能点是:cpuutilizationus60%-70%sy30%-35%id0%-5%cscontextswitchingcs是和cpuutilization相关的,如果能保持上面提到的utilizationA大量交换机可以接受小于或等于4的运行队列。最佳示例:#vmstat15procs------------memory--------------swap-------io------system-------cpu------rbswpdfreebuffcachesisobiboincsussyidwast30115084027162826068455309840021002247300501150840270264260684553103200005873608513137300501150840263940260684553104000046721750715137200401150840263320260684553106800006111711710137600401150840262328260684553107200006854767318136800例子中cpu中断(in)和contextswitch(cs)比较高,说明内核有来回切换进程,同时in也比较高,说明cpu一直在申请资源。Memory内存术语MMU:CPU不能和硬盘打交道,只有数据加载到内存中才能被CPU调用。CPU访问内存时,需要先请求内存监控程序,由监控程序控制分配内存读写请求。这个监控程序叫做MMU(MemoryManagementUnit)线性地址到物理地址的映射,如果按照1字节进行1字节的映射,需要一个非常大的表,这种转换关系会非常复杂。因此,内存空间被划分为另一种存储单元格式,通常是4K。如果每个进程在需要访问内存的时候都需要查找页表,那么就需要使用bufferTLB,但是每次没有tlb或者大量查找还是会导致慢,所以有了分层目录页表的。页表分为一级目录、二级目录和偏移量。此外,还有两种方法可以让系统管理大量内存:增加硬件内存管理单元中的页表数量和增加页面大小。第一种方法不现实,所以我们考虑第二种方法。即:大页面。32位系统有4m大页框,64位系统有2m大页框。Thethickerthepageframe,themoreseriousthewaste.查看系统的大页面:cat/proc/meminfoAnonHugePages:309248kBHugePages_Total:0HugePages_Free:0HugePages_Rsvd:0HugePages_Surp:0Hugepagesize:2048kBDirectMap4k:6144kBDirectMap2M:1042432kBDirectMap1G:0kBAnonHugePages:透明大页面,THP是一个提取层,可自动创建、管理和使用大页面的大多数方面。HP也必须在启动时设置。手动设置大页数:sysctlvm.nr_hugepages=20DMA:直接读内存实现DMA传输时,DMA控制器直接控制总线。因此,存在总线控制传递的问题。即在DMA传输之前,CPU要将总线的控制权交给DMA控制器,DMA传输完成后,DMA控制器要立即将总线的控制权交还给CPU。一个完整的DMA传输过程必须经过4个步骤:DMA请求、DMA响应、DMA传输、DMA结束。虚拟内存:32位系统上每个进程访问内存时,每个进程都认为自己有4G的可用内存空间。这称为虚拟内存(地址)。虚拟内存通过MMU转换为物理内存。完全的。我们尽量不在生产中使用虚拟内存。几个影响系统性能的内存参数:overcommit_memory过度使用内存0默认设置是由系统决定是否过度使用。1不要过度使用2过度使用但要有??一定比例。默认百分比值50由overcommit_ratio确定(默认为50)。比如物理内存8g,swap4g,10g可以超用。注意:在生产中尽量避免过度使用,例如redis应该关闭过度使用。spappines-将非活动进程交换为交换。注意:尽量不要使用swap。生产中设置:echp10>/proc/sys/vm/swappinesreclaimmemory该值设置为1、2或3让内核丢弃页面缓存和slab缓存的各种组合。1系统使所有pagebuffer内存失效并释放,即buffers2系统释放所有未使用的slabbuffer内存。即cached3系统释放所有pagebuffer和slabbuffer内存。生产中使用:1.运行syncecho3>/proc/sys/vm/drop_cachesi/oIO子系统一般是linux系统中最慢的部分。一个原因是它与CPU的距离,另一个原因是它的物理结构。所以尽量减少磁盘IO。磁盘调度策略:#cat/sys/block/sda/queue/schedulernoopanticipatorydeadline[cfq]目前使用的是cfq策略。cfq:完全公平的调度。在其时间片内,一个进程一次最多可以有八个请求(默认)。调度器会尝试根据历史数据来估计某个程序在不久的将来是否会发出更多的I/O,然后CFQ将闲置,等待该I/O,即使其他进程正在等待发出I/O。服务必须在截止日期前收到。noop:Nopolicyanticipatory:已经废弃,用于写多读少的场景。Linux内核以页为单位访问磁盘IO,一般为4K。查看页面:/usr/bin/time-vdateMPFlinux会将内存物理地址空间映射到虚拟内存,内核只会映射需要的内存页面。应用程序启动时,内核依次查找CPU缓存和物理内存,查找是否有对应的内存页。如果不存在,内核会发起MPF(majorpagefault)从磁盘中读取数据缓存到内存中。中间。如果在buffercache中找到对应的内存页,就会产生MnPF(minorpagefault)。/usr/bin/time-vhelloworld第一次执行会发现大部分是MPF是MnPF。FileBufferCache文件缓冲区缓存用于减少MPF和增加MnPF。它会继续增长,直到可用内存变少或内核需要为其他应用程序释放一些内存。空闲内存比较少,并不代表系统内存紧张。只是表示linux系统充分利用内存做cache。#cat/proc/meminfoMemTotal:1004772kBMemFree:79104kBBuffers:105712kB你可以用fsync()或者sync()立即回写,如果这些函数是不直接调用,pdflush会定期刷新回磁盘。iotop可以显示所有进程的IO使用情况lsof可以查看所有的调用和打开的文件其他命令:vmstatsariostattophtop等