From emhn at telcel.net.ve Fri Feb 21 12:09:34 2003 From: emhn at telcel.net.ve (Ernesto Hernandez-Novich) Date: Wed Aug 4 23:59:34 2004 Subject: [l-linux] Proceso comiendo CPU? Como examino al culpable? In-Reply-To: Message-ID: On Tue, 18 Feb 2003, Jean Hendrickx wrote: > Hola amigos, tengo una aplicaci??n cliente-servido corriendo en un > Compaq Proliant ML370 con SuSE 8.0 (y el ProvideX server), los clientes > son m??quinas Windows 98SE, ME con el software cliente del lenguaje > (ProvideX). Estoy usando los puertos 10050 (programas) y 11000 (odbc), > y todo funciona -aparentemente- bien. El problema es que en la ??ltima > semana el equipo (con solo 3 usuarios) ha disminuido su velocidad hasta > hacerse casi imposible trabajar con el (un ls tarda hasta 10 segs, > mostrar el prompt de login [telnet] hasta 15 segs). > > Haciendo un top, veo que casi el 100% de actividad del cpu est?? > compartido entre el n??mero de usuarios ProvideX (1=(aprox)=99.%, > 2=(aprox)=50% c/u, 3=(aprox)=32% c/u) ... los valores obtenidos con > el top son (en una medici??n de varios minutos durante el proceso de > "robo de tiempo de procesador"): El tiempo de CPU tiene tres "calidades": - Tiempo en espacio usuario. Es el tiempo invertido en operaciones "?tiles" para la aplicaci?n (aritm?tica, comparaci?n de cadenas, etc.) - Tiempo en espacio de sistema. Es el tiempo invertido en operaciones necesarias para la aplicaci?n pero que involucran acceso a recursos del sistema (reservar memoria, leer/escribir del disco, esperar por la red). Un consumo de CPU de 100% en espacio usuario indica "el proceso es CPU-bound, si quieres que vaya m?s r?pido, compra un CPU m?s r?pido". Un consumo de CPU de 100% en espacio sistema indica "el proceso es I/O-bound, si quieres que vaya m?s r?pido, optimiza el acceso a la red/disco/memoria o reprograma tu aplicaci?n para que no sea tan salvaje". Necesitas saber cual es la distribuci?n user/sys; en aplicaciones normales escritas por personas que no se secan la baba del ment?n, la proporci?n habitual es 85/15 como _mucho_. > %CPU: Desde 28% a 99.9% > SHARE: 348-500 > RSS: 70-170 > SIZE: 310-700M ?Cu?nta memoria RAM tiene la m?quina? ?Cu?nta memoria ocupan _exactamente_ los procesos? El proceso para calcular la cantidad de memoria exacta consiste en sumar: a. El producto del tama?o del texto del ejecutable y el n?mero de procesos simult?neos. Lo determinas con el comando size. b. Tama?o compartido entre los procesos una sola vez (es compartido). Lo determinas usando ps y convirtiendo de p?ginas a Kb. c. Tama?o del espacio privado (stack, DATA + BSS) de cada proceso. Lo determinas con ps y convirtiendo de p?ginas a Kb. d. Tama?o de los segmentos de memoria compartida entre los procesos (si aplica). Lo determinas con ipcs. Si la sumatoria de ?stas medidas [1] cabe en la memoria libre, perfecto, porque en caso contrario... > hay otro proceso llamado kswapd que llega a tener hasta 29%, este > proceso no pertenece al ProvideX, para que se usa este programa? ...vas a estar paginando (y posiblemente swappeando) como un salvaje, haciendo que el CPU se dedique solamente a intercambiar p?ginas entre RAM y swap en lugar de hacer cosas constructivas, llegando al tristemente conocido s?ndrome de thrashing. ?Trataste de escribir free en el apogeo de la crisis? >Simplemente matando los procesos y re-conectando se resuelve todo, Porque liberas la memoria. > Ahora mi pregunta: Adicionalmente al top y ps, existen otros comandos > (a l?? Unix) como sar o cpu_usage que me permitan monitorear m??s > cercanamente mi servidor? ps es suficiente utilizando las opciones adicionales para an?lisis de consumo de memoria y CPU. > Que podr??a estar disparando estos eventos (uhmm... se que muchos no > conocen ProvideX, pero podr??an tener sugerencias o experiencias con > problemas parecidos). Programas/consultas mal escritos que consumen mucha memoria. [1] Hace a?os escrib? un script que hac?a ?sto para procesos en general, aunque en particular lo hice para la basura que es Oracle. Es bastante simple de modificar para cualquier otro servidor. No hay ninguna garant?a impl?cita ni expl?cita, soporte, ni nada remotamente relacionado con "necesito algunos cambios". Si lo ejecuto como el usuario oracle en mi servidor principal tengo algo como /opt/oracle> ./mem.pl Found shared segment of 927997952 bytes. Correct (y/N) y Shared Memory 927997952 bytes Binary TEXT 22276376 bytes Processes 129 (112 shared servers) Total SZ 123385786368 bytes TOTAL RAM 1750672384 bytes 1669.571 Mb Tot ziens. Mak ik een bierje? Shared Memory y el TEXT son fijos (el primero es un par?metro del manejador y el segundo es un tama?o constante). Sin embargo Processes var?a y definitivamente sus SZ tambi?n. En mi caso, todos los procesos ocupan 1669.571Mb de RAM que caben perfectamente en 2Gb de RAM libres. Y la ?ltima l?nea es un chiste privado que qued? en el c?digo. #!/usr/bin/perl # Calcula la memoria consumida por Oracle en Linux # Ernesto Hern?ndez-Novich # 0.3 - No funcionaba en 2.4. Cambi? el formato de ipcs. Enero, 2002 # 0.2 - No funcionaba en 2.2. Cambiaron los flags de ps y no tomaba # el comando correcto. Junio 2000 # 0.1 - Version inicial. Junio 1999 # (I hope you dutch bastards stop bothering me for a change, # start translating van spaans naar neederlander a.u.b :-) # # n = Numero de procesos en la instancia # SZ = Paginas de memoria ocupadas por el proceso # text = Bytes ocupados por el binario Oracle # shm = Bytes ocupados en memoria compartida # # entonces # n # total = (1 - n) * (text + shm) + sum [ SZ(p) en bytes ] # p=1 my $instance = $ENV{'ORACLE_SID'}; my $oraexec = $ENV{'ORACLE_HOME'} . "/bin/oracle"; # Usamos ps para determinar cuantos procesos hay en la instancia y # sumamos sus SZ. my $ps = q{/bin/ps -e -o 'pid vsz cmd'}; my $units = 1024; my $size = q{/usr/bin/size}; my $ipcs = q{/usr/bin/ipcs -m}; my $n = 0; my $shsrv = 0; my $sumsz = 0; my @pids = (); open(PS,"$ps |") || die "Can't ps :-P"; while () { chomp; ($pid,$vsz,$command) = split; if ($command =~ /$instance$/) { $n++; $shsrv++ if ($command =~ /_s\d\d\d_/); $sumsz += $vsz * $units; push(@pids,$pid); } } close(PS); @pids = sort { $a <=> $b } @pids; # Determinamos los bytes ocupados por el texto del binario. open(SB,"$size $oraexec |") || die "Can't size $oraexec :-b"; while () { chomp; ($text) = split; last if $text =~ /^\d+$/; } close(SB); # Determinamos los bytes ocupados por la memoria compartida my $shm = 0; my $correct = "n"; open(IPCS,"$ipcs |") || die "Can't ipcs :-/"; while () { next unless /^0x/; chomp; (undef,undef,$owner,undef,$size) = split; next unless $owner = 'oracle'; print "Found shared segment of $size bytes. Correct (y/N) "; $correct = <>; last if ($correct =~ /^y/i); } close(IPCS); $shm = $size if ($correct =~ /^y/i); $total = ( 1 - $n ) * ( $text + $shm ) + $sumsz; write; print "Tot ziens. Mak ik een bierje?\n" format = Shared Memory @########## bytes $shm Binary TEXT @########## bytes $text Processes @## (@## shared servers) $n,$shsrv Total SZ @############ bytes $sumsz TOTAL RAM @########## bytes ~ @###.### Mb $total,($total/1024/1024) . -- Ernesto Hern?ndez-Novich - Running Linux 2.4.19 i686 - Unix: Live free or die! Geek by nature, Linux by choice, Debian of course. If you can't apt-get it, it isn't useful or doesn't exist. GPG Key Fingerprint = 438C 49A2 A8C7 E7D7 1500 C507 96D6 A3D6 2F4C 85E3 ------------------------------------------------------------------------ Enviar e-mail a colocando en el cuerpo: "UNSUBSCRIBE caracas-pm-list" para desuscribirse. "INFO caracas-pm-list" para conocer las reglas de etiqueta. ------------------------------------------------------------------------