¿Cómo liberar el uso de Inode?


276

Tengo una unidad de disco donde el uso del inodo es 100% (usando el df -icomando). Sin embargo, después de eliminar archivos sustancialmente, el uso sigue siendo del 100%.

¿Cuál es la forma correcta de hacerlo entonces?

¿Cómo es posible que una unidad de disco con menos uso de espacio en disco pueda tener un mayor uso de Inode que una unidad de disco con mayor uso de espacio en disco?

¿Es posible si comprimo muchos archivos que reducirían el recuento de inodos utilizados?


44
Quiero darte 50 puntos por esta pregunta. ¡Como lo puedo hacer! :)
Sophy

@Sophy No hagas eso. te prohibirán automáticamente
Steven Lu

1
@StevenLu ¡Gracias por tu información! Quiero darle crédito porque pasé unos días para resolver mi problema. Pero este problema me puede ayudar. Gracias de nuevo,
Sophy

1
@Sophy: ¿por qué otorgar algo fuera de tema para SO? :) Definitivamente no es una pregunta de programación, no importa cuántos votos positivos obtenga.
tink

Los directorios vacíos también consumen inodes. Eliminarlos puede liberar algunos inodes. El número puede ser significativo en algunos casos de uso. Puede eliminar directorios vacíos con: find. -type d -empty -delete
Ruchit Patel

Respuestas:


171

Es bastante fácil para un disco tener una gran cantidad de inodos utilizados incluso si el disco no está muy lleno.

Se asigna un inodo a un archivo, por lo que, si tiene miles de millones de archivos, todos de 1 byte cada uno, se quedará sin inodos mucho antes de quedarse sin disco.

También es posible que eliminar archivos no reduzca el recuento de inodos si los archivos tienen múltiples enlaces duros. Como dije, los inodes pertenecen al archivo, no a la entrada del directorio. Si un archivo tiene dos entradas de directorio vinculadas, eliminar una no liberará el inodo.

Además, puede eliminar una entrada de directorio pero, si un proceso en ejecución todavía tiene el archivo abierto, el inodo no se liberará.

Mi consejo inicial sería eliminar todos los archivos que pueda, luego reiniciar el cuadro para asegurarse de que no quedan procesos que mantengan los archivos abiertos.

Si hace eso y aún tiene un problema, infórmenos.

Por cierto, si está buscando los directorios que contienen muchos archivos, este script puede ayudarlo:

#!/bin/bash
# count_em - count files in all subdirectories under current directory.
echo 'echo $(ls -a "$1" | wc -l) $1' >/tmp/count_em_$$
chmod 700 /tmp/count_em_$$
find . -mount -type d -print0 | xargs -0 -n1 /tmp/count_em_$$ | sort -n
rm -f /tmp/count_em_$$

12
Por supuesto, >/tmp/count_em_$$solo funcionará si tiene espacio para ello ... si ese es el caso, vea la respuesta de @ Simon.
alxndr

1
@alxndr, es por eso que a menudo es una buena idea mantener sus sistemas de archivos separados; de esa manera, llenar algo así /tmpno afectará a sus otros sistemas de archivos.
paxdiablo

Su respuesta es perfectamente adecuada para "el sistema no seguirá utilizando el archivo después de reiniciar si se eliminó". Pero la pregunta que se hizo es "¿cómo recuperar o reutilizar los inodes después de que se elimine el puntero de inodo?". Básicamente, el kernel de Linux crea un nuevo inodo en un archivo cada vez que se crea, y también no reclama automáticamente el inodo cada vez que borra un archivo.
Mohanraj

1
@AshishKarpe, supongo que estás hablando de tu propia situación ya que el OP no mencionó los servidores de producción. Si no puede reiniciar inmediatamente, hay dos posibilidades. Primero, espero que los procesos en vuelo eventualmente cierren los archivos actuales para que los recursos del disco puedan liberarse. En segundo lugar, incluso los servidores de producción deben tener margen para reiniciarse en algún momento: simplemente programe un tiempo de inactividad planificado o espere a que aparezca la siguiente ventana de tiempo de inactividad.
paxdiablo

2
Supongo que quieres en ls -Alugar de ls -a. ¿Por qué querrías contar? y ..?
jarno

205

Si tiene mala suerte, ha utilizado aproximadamente el 100% de todos los inodos y no puede crear el scipt. Puedes verificar esto con df -ih.

Entonces este comando bash puede ayudarte:

sudo find . -xdev -type f | cut -d "/" -f 2 | sort | uniq -c | sort -n

Y sí, esto llevará tiempo, pero puede ubicar el directorio con la mayoría de los archivos.


8
eso hace el truco. mi problema era tener una cantidad increíble de sesiones en el directorio / lib / php / sessions. tal vez alguien tiene el mismo problema
SteMa

2
¡Alguien debería reescribir este hallazgo, cortar, ordenar uniq en un solo comando awk!
mogsie

55
@alxndr awkpodría mantener un hash del directorio y el recuento de archivos sin unificar y ordenar millones de líneas. Dicho esto, tal vez aquí hay una mejora: find . -maxdepth 1 -type d | grep -v '^\.$' | xargs -n 1 -i{} find {} -xdev -type f | cut -d "/" -f 2 | uniq -c | sort -nesto solo ordena la última lista.
mogsie

12
Si no puede crear ningún archivo, incluso eso puede fallar porque sortpuede no mantener todo en la memoria y tratará de volver automáticamente a escribir un archivo temporal. Un proceso que obviamente fallaría ...
Mikko Rantalainen

10
sortme falló, pero pude dar lo --buffer-size=10Gque funcionó.
Frederick Nord el

69

Mi situación era que me había quedado sin inodes y ya había eliminado todo lo que podía.

$ df -i
Filesystem     Inodes  IUsed  IFree IUse% Mounted on
/dev/sda1      942080 507361     11  100% /

Estoy en un Ubuntu 12.04LTS y no pude eliminar los viejos núcleos de Linux que ocupaban alrededor de 400,000 inodes porque apt estaba roto debido a la falta de un paquete. Y no pude instalar el nuevo paquete porque no tenía inodos, así que estaba atascado.

Terminé eliminando algunos viejos núcleos de Linux a mano para liberar alrededor de 10,000 inodes

$ sudo rm -rf /usr/src/linux-headers-3.2.0-2*

Esto fue suficiente para luego permitirme instalar el paquete que falta y arreglar mi apt

$ sudo apt-get install linux-headers-3.2.0-76-generic-pae

y luego elimine el resto de los viejos núcleos de Linux con apt

$ sudo apt-get autoremove

Las cosas están mucho mejor ahora

$ df -i
Filesystem     Inodes  IUsed  IFree IUse% Mounted on
/dev/sda1      942080 507361 434719   54% /

3
Esto fue lo más cercano a mi propio enfoque en una situación similar. Vale la pena señalar que un enfoque más cauteloso está bien documentado en help.ubuntu.com/community/Lubuntu/Documentation/…
beldaz

¡Mi caso exactamente! Pero tuve que usar "sudo apt-get autoremove -f" para progresar
Tony Sepia

¿Es seguro hacer esto: sudo rm -rf /usr/src/linux-headers-3.2.0-2*si estoy seguro de que no estoy usando ese núcleo?
Mars Lee

@MarsLee Puede verificar qué núcleo se está ejecutando actualmente con "uname -a"
Dominique Eav

Llamar $ sudo apt-get autoremovesolo, hizo el truco para mí.
Morten Grum

49

Mi solución:

Intenta encontrar si este es un problema de inodes con:

df -ih

Trate de encontrar carpetas raíz con gran cantidad de inodos:

for i in /*; do echo $i; find $i |wc -l; done

Intenta encontrar carpetas específicas:

for i in /src/*; do echo $i; find $i |wc -l; done

Si se trata de encabezados de Linux, intente eliminar el más antiguo con:

sudo apt-get autoremove linux-headers-3.13.0-24

Personalmente los moví a una carpeta montada (porque para mí el último comando falló) e instalé el último con:

sudo apt-get autoremove -f

Esto resolvió mi problema.


1
En mi caso el problema fue SpamAssasin-Temp. find /var/spool/MailScanner/incoming/SpamAssassin-Temp -mtime +1 -print | xargs rm -fhizo el trabajo :) Gracias!
joystick

44
Para mí, esto estaba tomando horas. Sin embargo, hay una solución simple: cuando el segundo comando se cuelga en un directorio en particular, elimine el comando actual y reinicie cambiando / * al directorio en el que estaba colgado. Pude profundizar hasta el culpable <minuto.
Michael Terry

Utilicé esta variante de su comando para imprimir los números en la misma línea: for i in /usr/src/*; do echo -en "$i\t"; find $i 2>/dev/null |wc -l; done
cscracker

for i in /src/*; do echo "$i, `find $i |wc -l`"; done|sort -nrk 2|head -10mostrar el directorio más grande del top 10
Mark Simon

12

Tuve el mismo problema, lo solucioné eliminando las sesiones de directorio de php

rm -rf /var/lib/php/sessions/

Puede estar debajo /var/lib/php5si está utilizando una versión anterior de php.

Recreala con el siguiente permiso

mkdir /var/lib/php/sessions/ && chmod 1733 /var/lib/php/sessions/

Permiso por defecto para el directorio en Debian mostró drwx-wx-wt(1733)


1
¿Alguna idea de por qué sucede esto?
Sibidharan

1
@Sibidharan en mi caso fue porque el trabajo cron de PHP para borrar las viejas sesiones PHP no funcionaba.
sombrío

3
rm -rf /var/lib/php/sessions/*probablemente sería un comando mejor: no eliminará el directorio de la sesión, solo su contenido ... Entonces no tendrá que preocuparse por
Shadow

No tuve sesión de php pero sí un problema de sesión de magento, similar a esto. Gracias por la direccion.
Mohit

las sesiones de php no deben borrarse

2

Experimentamos esto en una cuenta de HostGator (que establece límites de inodo en todo su alojamiento) después de un ataque de spam. Dejó un gran número de registros de cola en /root/.cpanel/comet. Si esto sucede y encuentra que no tiene inodos libres, puede ejecutar esta utilidad cpanel a través de shell:

/usr/local/cpanel/bin/purge_dead_comet_files

2

Puede usar RSYNC para ELIMINAR la gran cantidad de archivos

rsync -a --delete blanktest/ test/

Cree una carpeta en blanco con 0 archivos y el comando sincronizará sus carpetas de prueba con una gran cantidad de archivos (he eliminado casi 5 millones de archivos con este método).

Gracias a http://www.slashroot.in/which-is-the-fastest-method-to-delete-files-in-linux


Por lo que puedo decir del artículo / comentarios, esto es más rápido que rm *para muchos archivos, debido a la expansión del comodín y pasando / procesando cada argumento, pero rm test/está bien para eliminar una test/carpeta que contiene muchos archivos.
mwfearnley

Atención, esto funciona bien, ¡pero asegúrese de configurar los permisos correctamente en el directorio en blanco! No hice esto y sin querer cambié los permisos en mi directorio de sesiones PHP. Tomó dos horas para descubrir lo que arruiné.
Ascender

1

eaccelerator podría estar causando el problema ya que compila PHP en bloques ... He tenido este problema con un servidor Amazon AWS en un sitio con una gran carga. Libere Inodes eliminando la memoria caché del acelerador en / var / cache / eaccelerator si continúa teniendo problemas.

rm -rf /var/cache/eaccelerator/*

(o cualquiera que sea su directorio de caché)


1

Enfrentamos un problema similar recientemente, en caso de que un proceso se refiera a un archivo eliminado, el Inode no se lanzará, por lo que debe verificar lsof /, y matar / reiniciar el proceso liberará los inodos.

Corrígeme si me equivoco aquí.


1

Como se dijo anteriormente, el sistema de archivos puede quedarse sin inodos, si hay muchos archivos pequeños. He proporcionado algunos medios para encontrar directorios que contienen la mayoría de los archivos aquí .


0

Respuesta tardía: en mi caso, fueron mis archivos de sesión bajo

/var/lib/php/sessions

que usaban Inodes.
Incluso no pude abrir mi crontab o hacer un nuevo directorio y mucho menos activar la operación de eliminación. Como uso PHP, tenemos esta guía donde copié el código del ejemplo 1 y configuré un cronjob para ejecutar esa parte del código.

<?php
// Note: This script should be executed by the same user of web server 
process.

// Need active session to initialize session data storage access.
session_start();

// Executes GC immediately
session_gc();

// Clean up session ID created by session_gc()
session_destroy();
?>

Si se pregunta cómo logré abrir mi crontab, bueno, eliminé algunas sesiones manualmente a través de la CLI.

¡Espero que esto ayude!


0

podías ver esta información

for i in /var/run/*;do echo -n "$i "; find $i| wc -l;done | column -t

-2

Muchas respuestas a esta hasta ahora y todas las anteriores parecen concretas. Creo que estará seguro al usarlo a statmedida que avanza, pero dependiendo del sistema operativo, es posible que se produzcan algunos errores de inodo. Por lo tanto, implementar su propia statfuncionalidad de llamada 64bitpara evitar cualquier problema de desbordamiento parece bastante compatible.


nos encantan los ejemplos aquí;)
Bohne

-3

Si usa docker, elimine todas las imágenes. Usaron mucho espacio ...

Pare todos los contenedores

docker stop $(docker ps -a -q)

Eliminar todos los contenedores

docker rm $(docker ps -a -q)

Eliminar todas las imágenes

docker rmi $(docker images -q)

Trabaja para mi


Esto no ayuda a detectar si el problema son "demasiados inodes".
Mark Stosberg

Esto no tiene nada que ver con Docker.
Urda
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.