|

Comandos Bash

Puedo darte una lista muy amplia y bien organizada de los comandos Bash más importantes, con explicaciones técnicas claras. Pero hay un detalle importante: no existe una “lista completa” absoluta, porque Bash puede ejecutar:

  • Comandos internos (builtins)
  • Comandos externos del sistema (GNU coreutils, utilidades POSIX, etc.)
  • Comandos instalados por paquetes adicionales
  • Alias y funciones definidas por el usuario

Aun así, puedo darte la lista más exhaustiva y útil, cubriendo:

  1. Builtins de Bash
  2. Comandos esenciales de GNU/Linux
  3. Utilidades POSIX estándar
  4. Comandos avanzados de administración del sistema

Voy a estructurarlo para que sea técnico, claro y práctico.

🧠 1. Builtins de Bash (comandos internos)

Estos comandos los ejecuta el propio intérprete Bash, sin llamar a programas externos.

🔧 Gestión del entorno y shell

ComandoExplicación técnica
cdCambia el directorio actual modificando la variable interna PWD.
pwdMuestra el directorio actual leyendo PWD o consultando el sistema de archivos.
echoImprime texto en stdout; interpreta escapes si se usa -e.
exportMarca variables para ser heredadas por procesos hijos mediante el entorno.
setConfigura flags del shell y lista variables internas.
unsetElimina variables o funciones del entorno del shell.
aliasCrea alias que se expanden antes de ejecutar el comando.
unaliasElimina alias definidos.
typeIndica si un comando es builtin, alias, función o binario.
source / .Ejecuta un script en el contexto del shell actual sin crear subshell.

🧵 Control de procesos

ComandoExplicación técnica
jobsLista procesos en background gestionados por el shell.
fgTrae un job al foreground.
bgReanuda un job en background.
killEnvía señales POSIX a procesos (SIGTERMSIGKILL, etc.).
waitEspera a que un proceso hijo termine y devuelve su exit code.

📚 Estructuras de control

ComandoExplicación técnica
ifthenelseelifEstructuras condicionales basadas en exit codes.
forwhileuntilBucles iterativos.
caseSelección múltiple basada en patrones.
functionDefine funciones internas del shell.

📁 Manipulación de archivos (interno)

ComandoExplicación técnica
test / [Evalúa expresiones lógicas y de archivos.
readLee entrada desde stdin y asigna a variables.
printfImprime texto con formato POSIX.

📦 2. Comandos esenciales del sistema (GNU coreutils)

Estos son binarios externos ubicados normalmente en /bin o /usr/bin.

📁 Gestión de archivos y directorios

ComandoExplicación técnica
lsLista entradas de un directorio leyendo inodos.
cpCopia archivos usando syscalls read() y write().
mvMueve archivos; si es en el mismo FS usa rename().
rmElimina entradas del directorio; no borra datos, solo inodos.
mkdirCrea directorios usando mkdir() syscall.
rmdirElimina directorios vacíos.
touchActualiza timestamps o crea archivos vacíos.
lnCrea enlaces duros o simbólicos.

📄 Visualización de contenido

ComandoExplicación técnica
catConcatena archivos a stdout.
lessPaginador interactivo eficiente.
headMuestra primeras líneas.
tailMuestra últimas líneas; con -f sigue cambios en tiempo real.

🔍 Búsqueda

ComandoExplicación técnica
grepFiltra texto usando expresiones regulares.
findRecorrido recursivo del FS evaluando predicados.
locateBusca en una base de datos indexada (mlocate.db).

🧮 Procesamiento de texto

ComandoExplicación técnica
awkLenguaje de procesamiento de texto basado en patrones y acciones.
sedEditor de flujo para sustituciones y transformaciones.
cutExtrae columnas por delimitador.
sortOrdena líneas usando algoritmos eficientes (merge sort).
uniqElimina duplicados consecutivos.
trTraduce o elimina caracteres.

⚙️ 3. Administración del sistema

ComandoExplicación técnica
psLista procesos leyendo /proc.
top / htopMonitor interactivo de procesos.
dfMuestra uso de discos leyendo superblocks.
duCalcula tamaño de directorios recursivamente.
freeMuestra memoria del sistema.
unameInformación del kernel.
systemctlControla servicios systemd.
journalctlLee logs binarios de systemd.

🌐 4. Red y comunicaciones

ComandoExplicación técnica
pingEnvía ICMP echo requests.
curlCliente HTTP/FTP; usa libcurl.
wgetDescarga archivos vía HTTP/HTTPS/FTP.
sshConexión remota cifrada usando OpenSSH.
scpCopia archivos sobre SSH.
netstat / ssMuestra sockets y conexiones.
ipConfigura interfaces, rutas y reglas de red.

🧩 5. Compresión y empaquetado

ComandoExplicación técnica
tarEmpaqueta archivos sin comprimir.
gzip / gunzipCompresión DEFLATE.
zip / unzipFormato ZIP.
xzCompresión LZMA2.

Versión extendida de builtins y tabla completa de coreutils

Vamos a construir la referencia más completa y útil que puedes tener en una sola pieza:

  1. Todos los builtins de Bash, con una descripción técnica clara.
  2. La tabla completa de GNU coreutils, organizada por categorías.

Todo en formato limpio, consultable y sin ruido.

🧠 1. Builtins de Bash (lista extendida y completa)

Esta es la lista oficial de builtins que Bash incorpora internamente. Incluye todos los builtins POSIX + los específicos de Bash.

🔧 Gestión del entorno y variables

BuiltinDescripción técnica
aliasDefine alias que se expanden antes del análisis sintáctico.
unaliasElimina alias del entorno del shell.
bindGestiona bindings de teclado de readline.
declare / typesetDeclara variables con atributos (integer, array, readonly…).
exportMarca variables para ser heredadas por procesos hijos.
readonlyMarca variables como inmutables.
setConfigura flags del shell y lista variables.
unsetElimina variables o funciones del entorno.
localDeclara variables locales dentro de funciones.
letEvalúa expresiones aritméticas en el contexto del shell.
printfImprime texto con formato POSIX.
evalEjecuta una cadena tras expandirla completamente.

📁 Navegación y manipulación del entorno

BuiltinDescripción técnica
cdCambia el directorio actual modificando PWD y OLDPWD.
pwdMuestra el directorio actual (interno o consultando el FS).
dirsMuestra el stack de directorios.
pushdAñade un directorio al stack y cambia a él.
popdExtrae un directorio del stack y cambia a él.

🧵 Control de procesos y jobs

BuiltinDescripción técnica
jobsLista procesos gestionados por el shell.
fgTrae un job al foreground.
bgReanuda un job en background.
killEnvía señales POSIX a procesos.
waitEspera a que un proceso hijo termine.
disownElimina un job del control del shell.
suspendSuspende el shell enviando SIGSTOP.

🧩 Ejecución y control del flujo

BuiltinDescripción técnica
. / sourceEjecuta un script en el contexto del shell actual.
execReemplaza el proceso actual por otro (sin fork).
exitTermina el shell con un exit code.
returnDevuelve un exit code desde una función.
shiftDesplaza los parámetros posicionales.
getoptsAnaliza opciones estilo POSIX.

📚 Entrada y salida

BuiltinDescripción técnica
echoImprime texto en stdout.
readLee entrada desde stdin y asigna a variables.
mapfile / readarrayLee líneas en un array.

🧮 Aritmética

BuiltinDescripción técnica
(( ))Evaluación aritmética nativa del shell.
letEvaluación aritmética tradicional.

🧱 Estructuras de control (palabras reservadas)

Estas no son builtins, pero forman parte del lenguaje Bash:

if, then, else, elif, fi, for, while, until, do, done, case, esac, select, function, time, coproc, !, {}, [[ ]].

📦 2. Tabla completa de GNU coreutils

GNU coreutils contiene 106 comandos. Los organizo por categoría para que sea realmente útil.

📁 A. Gestión de archivos y directorios

Comando
basename
chcon
chgrp
chmod
chown
cp
dd
df
dir
dircolors
install
ln
ls
mkdir
mkfifo
mknod
mktemp
mv
readlink
realpath
rm
rmdir
shred
sync
touch
truncate
vdir

📄 B. Visualización y lectura de archivos

Comando
cat
tac
nl
od
base32
base64
fmt
fold
head
tail
split
csplit
sum

🔍 C. Búsqueda y comparación

Comando
cmp
comm
diff
dircmp
md5sum
sha1sum
sha224sum
sha256sum
sha384sum
sha512sum
cksum

🧮 D. Procesamiento de texto

Comando
cut
expand
unexpand
join
paste
sort
uniq
tr
wc

🧩 E. Utilidades del sistema

Comando
arch
date
df
env
expr
factor
groups
hostid
id
logname
nice
nohup
nproc
pathchk
pinky
printenv
printf
pwd
seq
sleep
stat
stdbuf
stty
tee
test
timeout
tty
uname
uptime
users
who
whoami
yes

🔐 F. Permisos y atributos

Comando
chcon
chgrp
chmod
chown
runcon

🧱 G. Utilidades de shell

Comando
false
true
echo
printf

Comandos menos conocidos

🧩 1. Gestión de entorno y variables

🔧 1.1. bind — gestionar atajos de teclado de Readline

Bash usa Readline para leer lo que escribes en el prompt. Readline permite:

  • Atajos tipo Emacs (Ctrl+A, Ctrl+E…)
  • Atajos tipo Vi
  • Macros de teclado
  • Reasignar teclas

bind sirve para ver, modificar o crear atajos.

Ver todos los atajos actuales

Código

bind -P

Asignar un atajo nuevo

Ejemplo: que F2 inserte la palabra “hola”:

Código

bind '"\eOQ": "hola"'

Cambiar a modo vi

Código

set -o vi

🔧 1.2. declare / typeset — variables con atributos

Son equivalentes en Bash. Sirven para declarar variables con tipos o atributos especiales.

Atributos importantes

AtributoSignificado
-iVariable entera (evalúa expresiones)
-aArray indexado
-AArray asociativo
-rSolo lectura
-xExportar al entorno

Ejemplos

Variable entera

Código

declare -i x=5+3
echo $x   # 8

Array

Código

declare -a nums=(1 2 3)

Array asociativo

Código

declare -A persona=([nombre]=David [edad]=40)

Solo lectura

Código

declare -r PI=3.14159

🔧 1.3. eval — ejecutar código generado dinámicamente

eval vuelve a interpretar una cadena como código Bash.

Ejemplo básico

Código

cmd="ls -l"
eval $cmd

Ejemplo potente: variables dinámicas

Código

var="nombre"
eval $var="David"
echo $nombre

Riesgo

Si evalúas texto no controlado → inyección de comandos.

🧭 2. Navegación y manipulación del entorno

🔧 2.1. pushd y popd — pila de directorios

Bash mantiene una pila de directorios.

pushd — cambia de directorio y lo mete en la pila

Código

pushd /etc

popd — vuelve al directorio anterior

Código

popd

Ver la pila

Código

dirs -v

Esto es oro para navegar rápido entre 2–3 rutas.

🧵 3. Control de procesos y jobs

🔧 3.1. jobs — lista procesos en background

Código

sleep 100 &
jobs

🔧 3.2. fg — trae un job al foreground

Código

fg %1

🔧 3.3. bg — reanuda un job en background

Código

bg %1

🔧 3.4. kill — envía señales

Código

kill -9 1234
kill -TERM %1

🔧 3.5. wait — espera a que un proceso termine

Código

wait %1

🔧 3.6. disown — elimina un job del control del shell

Código

disown %1

El proceso sigue, pero el shell ya no lo controla.

🔧 3.7. suspend — suspende el shell

Código

suspend

⚙️ 4. Ejecución y control de flujo

🔧 4.1. exec — reemplaza el proceso actual

Ejemplo: redirigir todo el shell a un archivo:

Código

exec > salida.log

Ejemplo: reemplazar el shell por otro programa:

Código

exec ls

El shell desaparece.

🔧 4.2. shift — desplaza parámetros posicionales

Código

set -- a b c d
echo $1  # a
shift
echo $1  # b

Muy útil en scripts con argumentos.

🔧 4.3. getopts — parseo POSIX de opciones

Ejemplo:

Código

while getopts "ab:c" opt; do
  case $opt in
    a) echo "Opción -a" ;;
    b) echo "Opción -b con valor $OPTARG" ;;
    c) echo "Opción -c" ;;
  esac
done

📥 5. Entrada y salida

🔧 5.1. mapfile / readarray — leer líneas en un array

Son idénticos.

Código

mapfile arr < archivo.txt
echo "${arr[0]}"

Con numeración automática.

➗ 6. Aritmética

🔧 6.1. (( )) — aritmética nativa del shell

Código

((x = 5 + 3))
echo $x

Permite comparaciones:

Código

if (( x > 10 )); then ...

🔧 6.2. let — versión antigua

Código

let x=5+3

🔧 6.3. bc — calculadora arbitraria de precisión

Código

echo "scale=5; 10/3" | bc

Funciones, bucles, variables… Es un mini lenguaje matemático.

🧱 7. Estructuras de control

🔧 7.1. coproc — ejecutar un proceso con pipes automáticos

Ejemplo:

Código

coproc DATE { date; }
read linea <&"${DATE[0]}"
echo "La fecha es: $linea"

Crea un proceso con dos pipes listos para usar.

🔧 7.2. ! — negación lógica

Código

if ! grep -q error log.txt; then
  echo "No hay errores"
fi

Nada que ver con el history.

📁 8. Gestión de archivos y directorios

🔧 8.1. basename — extraer nombre de archivo

Código

basename /usr/local/bin/python
# python

🔧 8.2. chgrp — cambiar grupo

Código

chgrp staff archivo

🔧 8.3. chown — cambiar propietario

Código

chown david archivo
chown david:staff archivo

🔧 8.4. dd — copiar datos a bajo nivel

Código

dd if=/dev/zero of=archivo bs=1M count=10

Sirve para:

  • Crear imágenes
  • Copiar discos
  • Convertir formatos

🔧 8.5. mkfifo — crear FIFO (named pipe)

Código

mkfifo canal
echo hola > canal
cat canal

🔧 8.6. mknod — crear nodos de dispositivo

Solo para administradores avanzados.

🔧 8.7. mktemp — crear archivo temporal seguro

Código

mktemp

🔧 8.8. readlink — resolver enlaces simbólicos

Código

readlink -f /usr/bin/python

🔧 8.9. shred — sobrescribir archivo para borrado seguro

Código

shred -u archivo

🔧 8.10. truncate — cambiar tamaño de archivo

Código

truncate -s 0 archivo

🔧 8.11. vdir — como ls -l

Código

vdir

📄 9. Visualización

🔧 9.1. tac — cat al revés

Código

tac archivo

🔧 9.2. nl — numerar líneas

Código

nl archivo

🔧 9.3. od — volcado hexadecimal

Código

od -x archivo

🔧 9.4. base32 / base64

Código

echo hola | base64

🔧 9.5. fmt — formatear párrafos

Código

fmt -w 40 archivo

🔧 9.6. fold — cortar líneas largas

Código

fold -w 20 archivo

🔧 9.7. split — dividir archivos

Código

split -b 1M archivo parte_

🔧 9.8. csplit — dividir por patrones

Código

csplit archivo '/ERROR/' '{*}'

🔧 9.9. sum — checksum antiguo

Código

sum archivo

🔍 10. Búsqueda y comparación

🔧 10.1. cmp — comparar binarios

Código

cmp a.bin b.bin

🔧 10.2. comm — comparar listas ordenadas

Código

comm lista1 lista2

🔧 10.3. dircmp — comparar directorios

Código

dircmp dir1 dir2

🔧 10.4. md5sum — hash MD5

Código

md5sum archivo

🔧 10.5. cksum — checksum CRC32

Código

cksum archivo

⚙️ 11. Utilidades del sistema

arch — arquitectura

Código

arch

expr — expresiones aritméticas

Código

expr 5 + 3

factor — descomposición en factores

Código

factor 360

hostid — ID del host

Código

hostid

nice — cambiar prioridad

Código

nice -n 10 comando

nproc — núcleos disponibles

Código

nproc

pathchk — comprobar validez de rutas

Código

pathchk /ruta/larga

pinky — versión reducida de finger

Código

pinky

stdbuf — cambiar buffers de E/S

Código

stdbuf -oL comando

stty — configurar terminal

Código

stty -a

tty — mostrar terminal actual

Código

tty

yes — repetir una cadena infinitamente

Código

yes hola

🔐 12. Permisos y atributos

chcon — cambiar contexto SELinux

Código

chcon -t httpd_sys_content_t archivo

runcon — ejecutar con contexto SELinux

Código

runcon -t httpd_t comando

Procesamiento de texto: awk, sed, cut, sort, uniq y tr

Vamos a hacer la guía definitiva, técnica y profunda, de los seis comandos de procesamiento de texto más importantes en Unix: awk, sed, cut, sort, uniq y tr. Cada uno con:

  • Qué hace realmente a nivel técnico
  • Cómo funciona internamente
  • Sintaxis esencial
  • Ejemplos prácticos
  • Casos avanzados
  • Errores típicos y cómo evitarlos

Todo pensado para alguien con tu perfil técnico.

🧠 1. AWK — El lenguaje de procesamiento de texto más potente en Unix

🧩 ¿Qué es AWK realmente?

AWK no es un comando, sino un lenguaje de programación completo diseñado para:

  • Procesar texto línea a línea
  • Dividir en campos automáticamente
  • Aplicar patrones y acciones
  • Trabajar con expresiones regulares
  • Generar informes y transformaciones complejas

Internamente, AWK:

  • Lee una línea
  • La divide en campos usando el separador FS
  • Evalúa patrones
  • Ejecuta acciones { ... }
  • Imprime si procede

🧬 Sintaxis general

Código

awk 'patrón { acción }' archivo

🔧 Ejemplos esenciales

1) Imprimir la primera columna

Código

awk '{print $1}' datos.txt

2) Filtrar líneas que contengan “error”

Código

awk '/error/'

3) Sumar la tercera columna

Código

awk '{s += $3} END {print s}'

4) Cambiar separador de campos

Código

awk -F',' '{print $2}'

5) Reemplazar texto (más potente que sed)

Código

awk '{gsub("foo","bar"); print}'

🚀 Ejemplo avanzado: procesar logs

Código

awk '$9 == 404 {count[$1]++} END {for (ip in count) print ip, count[ip]}'

Cuenta cuántos errores 404 genera cada IP.

🧠 2. SED — Editor de flujo (stream editor)

🧩 ¿Qué hace realmente sed?

SED procesa texto sin cargarlo entero en memoria. Funciona línea a línea, aplicando transformaciones declarativas.

Internamente:

  • Lee una línea
  • La coloca en el pattern space
  • Aplica comandos
  • Imprime (a menos que uses -n)

🔧 Sintaxis básica

Código

sed 'comando' archivo

🔧 Ejemplos esenciales

1) Sustitución simple

Código

sed 's/foo/bar/' archivo

2) Sustitución global

Código

sed 's/foo/bar/g'

3) Eliminar líneas que coincidan

Código

sed '/error/d'

4) Reemplazar solo en líneas que cumplan un patrón

Código

sed '/^#/{s/todo/nada/}'

5) Editar un archivo en sitio

Código

sed -i 's/foo/bar/g' archivo

🚀 Ejemplo avanzado: eliminar líneas entre dos patrones

Código

sed '/BEGIN/,/END/d'

🧠 3. CUT — Extracción de columnas o rangos

🧩 ¿Qué hace realmente cut?

CUT no interpreta expresiones regulares. Es extremadamente rápido porque:

  • Trabaja por posiciones o delimitadores
  • No analiza sintaxis compleja
  • No reordena datos

🔧 Sintaxis

Código

cut -d',' -f2 archivo

🔧 Ejemplos esenciales

1) Extraer la segunda columna

Código

cut -f2

2) Usar delimitador personalizado

Código

cut -d':' -f1 /etc/passwd

3) Extraer rangos de caracteres

Código

cut -c1-10 archivo

🚀 Ejemplo avanzado: extraer múltiples columnas

Código

cut -d',' -f1,4,7 datos.csv

🧠 4. SORT — Ordenación eficiente de texto

🧩 ¿Qué hace realmente sort?

SORT usa algoritmos de ordenación externos (merge sort) optimizados para:

  • Archivos enormes
  • Ordenación por claves
  • Ordenación numérica
  • Ordenación por campos

Internamente:

  • Divide en bloques
  • Ordena cada bloque
  • Hace merge de los bloques

🔧 Sintaxis

Código

sort [opciones] archivo

🔧 Ejemplos esenciales

1) Ordenar alfabéticamente

Código

sort archivo

2) Ordenar numéricamente

Código

sort -n archivo

3) Ordenar por la tercera columna

Código

sort -k3 archivo

4) Ordenar por columna numérica

Código

sort -k2,2n archivo

🚀 Ejemplo avanzado: ordenar por fecha (ISO 8601)

Código

sort -k1,1 archivo.log

🧠 5. UNIQ — Elimina duplicados consecutivos

🧩 ¿Qué hace realmente uniq?

UNIQ no detecta duplicados globales, solo consecutivos. Por eso suele usarse con sort.

Internamente:

  • Compara línea actual con la anterior
  • Si son iguales → descarta
  • Si cambian → imprime

🔧 Sintaxis

Código

uniq archivo

🔧 Ejemplos esenciales

1) Eliminar duplicados consecutivos

Código

uniq

2) Contar ocurrencias

Código

uniq -c

3) Mostrar solo duplicados

Código

uniq -d

🚀 Ejemplo avanzado: top de palabras repetidas

Código

sort palabras.txt | uniq -c | sort -nr | head

🧠 6. TR — Traducción y eliminación de caracteres

🧩 ¿Qué hace realmente tr?

TR trabaja carácter a carácter, no por líneas. Es extremadamente rápido porque:

  • No usa expresiones regulares
  • No entiende campos
  • Solo transforma bytes

🔧 Sintaxis

Código

tr SET1 SET2

🔧 Ejemplos esenciales

1) Convertir minúsculas a mayúsculas

Código

tr 'a-z' 'A-Z'

2) Eliminar caracteres

Código

tr -d 'aeiou'

3) Comprimir repeticiones

Código

tr -s ' '

4) Sustituir separadores

Código

tr ':' '\t'

🚀 Ejemplo avanzado: normalizar texto

Código

tr -cd '[:alnum:]\n'

Elimina todo excepto letras, números y saltos de línea.

Conceptos en bash: builtins, gnu coreutils, stat, posix o estandar posix, fork

Vamos a desmenuzar estos conceptos con precisión técnica, pero de forma clara y útil para tu nivel. Son piezas fundamentales para entender cómo funciona realmente un sistema Unix/Linux por dentro.

🧩 1. Builtins (comandos internos del shell)

🔧 ¿Qué son?

Un builtin es un comando que no es un programa externo, sino una función interna del propio intérprete de comandos (Bash, Zsh, etc.).

Ejemplos: cd, echo, export, alias, read.

🧠 ¿Por qué existen?

Porque hay operaciones que no pueden ejecutarse en un proceso hijo. Ejemplo clásico:

Código

cd /tmp

Si cd fuera un programa externo:

  • El shell lanzaría un proceso hijo
  • El hijo cambiaría de directorio
  • El hijo terminaría
  • El shell seguiría en el mismo directorio de antes

Por eso cd debe ejecutarse dentro del proceso del shell.

⚙️ Características técnicas

  • Se ejecutan sin fork()
  • Son más rápidos que los binarios externos
  • Tienen acceso directo al estado interno del shell (variables, entorno, directorio actual)

📦 2. GNU coreutils

🔧 ¿Qué son?

Es un conjunto de programas esenciales para cualquier sistema GNU/Linux. Incluye comandos como:

  • ls, cp, mv, rm
  • cat, head, tail
  • sort, uniq, cut
  • chmod, chown, stat

Son binarios externos, normalmente ubicados en:

Código

/usr/bin
/bin

🧠 ¿Por qué existen?

Porque implementan las herramientas básicas del sistema operativo siguiendo estándares POSIX, pero con extensiones GNU.

⚙️ Características técnicas

  • Se ejecutan como procesos independientes
  • Requieren fork() + execve()
  • Son portables entre distribuciones Linux
  • Suelen ser más potentes que las versiones POSIX puras

📏 3. POSIX (o estándar POSIX)

🔧 ¿Qué es POSIX?

POSIX = Portable Operating System Interface Es un estándar internacional que define:

  • Cómo deben comportarse los comandos básicos
  • Cómo deben funcionar las llamadas al sistema
  • Cómo debe ser la API de procesos, señales, archivos, etc.
  • Cómo debe comportarse un shell compatible

POSIX no es software. Es un conjunto de reglas que los sistemas Unix-like deben cumplir.

🧠 ¿Por qué existe?

Para que un script o programa funcione igual en:

  • Linux
  • macOS
  • BSD
  • Solaris
  • AIX

⚙️ Ejemplo práctico

POSIX define que:

Código

ls

debe listar archivos, pero no define colores. Por eso:

  • ls en GNU tiene colores
  • ls en macOS no
  • Ambos siguen siendo POSIX

📊 4. stat (concepto general y comando)

🔧 ¿Qué es stat?

Hay dos cosas distintas:

1) La syscall stat() del kernel

Es una llamada al sistema que devuelve metadatos de un archivo, como:

  • tamaño
  • permisos
  • inodo
  • timestamps
  • propietario
  • tipo de archivo

Ejemplo en C:

c

struct stat info;
stat("archivo.txt", &info);

2) El comando stat de coreutils

Es un binario que muestra la información de la syscall stat() de forma legible.

Ejemplo:

Código

stat archivo.txt

Salida típica:

Código

Size: 2048    Blocks: 8    IO Block: 4096 regular file
Device: 803h/2051d    Inode: 1234567    Links: 1
Access: (0644/-rw-r--r--)  Uid: 1000  Gid: 1000
Access: 2024-01-01 12:00:00
Modify: 2024-01-01 12:00:00
Change: 2024-01-01 12:00:00

🧬 5. fork() — La base de la multitarea en Unix

🔧 ¿Qué es fork()?

fork() es una llamada al sistema que crea un nuevo proceso duplicando el proceso actual.

  • El proceso original = padre
  • El proceso duplicado = hijo

Ambos continúan ejecutándose desde el mismo punto del código.

🧠 ¿Por qué es tan importante?

Porque todos los comandos externos se ejecutan así:

  1. El shell llama a fork()
  2. El hijo ejecuta execve() para cargar el binario
  3. El padre espera o sigue ejecutando

Ejemplo conceptual:

Código

bash
 └── fork()
       └── execve("/usr/bin/ls")

⚙️ Características técnicas

  • Copia el espacio de memoria del proceso (copy-on-write)
  • Copia descriptores de archivo
  • Copia variables de entorno
  • El hijo tiene un PID distinto

🚀 Ejemplo en C

c

pid_t pid = fork();

if (pid == 0) {
    printf("Soy el hijo\n");
} else {
    printf("Soy el padre\n");
}

🎯 Resumen rápido

ConceptoQué esNivel
BuiltinsComandos internos del shellShell
GNU coreutilsConjunto de binarios esencialesSistema
POSIXEstándar que define cómo deben comportarse los sistemas UnixNorma
statSyscall para obtener metadatos de archivos (y comando que la muestra)Kernel / Usuario
fork()Syscall que crea procesosKernel

Este es uno de esos temas donde entender cómo funciona Unix por dentro te cambia la forma de ver cualquier shell o proceso. Te lo explico con rigor técnico, pero de forma clara.

🧩 1. ¿Por qué escribimos fork()execve()wait() con paréntesis?

Porque son funciones reales del sistema, no comandos del shell.

  • fork()
  • execve()
  • wait()
  • kill()
  • signal()

Todas ellas son llamadas al sistema (syscalls) expuestas a través de la biblioteca estándar de C (glibc en Linux).

🔧 ¿Qué significa esto?

En C, las syscalls se invocan como funciones:

c

pid_t pid = fork();
execve("/bin/ls", args, envp);
wait(&status);

Por eso se escriben con paréntesis: son funciones que reciben parámetros y devuelven valores.

🔬 ¿Qué ocurre realmente?

Aunque parecen funciones normales, en realidad:

  • La función de C prepara los argumentos
  • Ejecuta la instrucción syscall (o int 0x80 en sistemas antiguos)
  • El kernel toma el control
  • Realiza la operación
  • Devuelve al proceso

🧬 2. Cómo se relacionan fork(), execve(), wait() y signals

Este es el ciclo vital de cualquier comando externo que ejecutas en Bash, Zsh, etc.

Vamos paso a paso.

🧩 2.1 fork() — Crear un proceso hijo

fork() duplica el proceso actual:

  • El padre sigue ejecutándose
  • El hijo es una copia casi idéntica (copy-on-write)
  • Ambos continúan desde la misma línea de código

El hijo recibe pid = 0 El padre recibe pid = <PID del hijo>

🧩 2.2 execve() — Reemplazar el proceso por un programa

Después de fork(), el hijo llama a execve():

c

execve("/usr/bin/ls", args, envp);

Esto:

  • Descarta el código del proceso hijo
  • Carga el binario solicitado
  • Comienza a ejecutarlo desde su main()

El PID no cambia. Solo cambia el contenido del proceso.

🧩 2.3 wait() — El padre espera al hijo

El shell (padre) ejecuta:

c

wait(&status);

Esto:

  • Suspende al padre hasta que el hijo termine
  • Recoge el exit code
  • Evita procesos zombis

🧩 2.4 signals — Comunicación asíncrona

Las señales son interrupciones software:

  • SIGINT (Ctrl+C)
  • SIGTERM
  • SIGKILL
  • SIGCHLD (cuando un hijo termina)
  • SIGHUP

El shell usa señales para:

  • Cancelar procesos
  • Notificar terminación
  • Controlar jobs en background

🧠 Resumen visual del ciclo

Código

shell
 ├── fork() → crea hijo
 │
 ├── hijo → execve("/bin/ls")
 │
 └── padre → wait() hasta que hijo termine

🐚 3. Diferencias entre POSIX sh, Bash, Zsh, Dash y Fish

Aquí viene lo bueno. Cada shell tiene su filosofía, su velocidad y su compatibilidad.

📏 3.1 POSIX sh (Bourne Shell estándar)

✔️ Características

  • Especificado por POSIX
  • Sintaxis mínima y estable
  • Máxima portabilidad
  • Sin arrays, sin funciones avanzadas, sin extensiones

✔️ ¿Cuándo usarlo?

  • Scripts que deben funcionar en cualquier Unix
  • Entornos embebidos
  • Init scripts

❌ Limitaciones

  • Muy limitado comparado con Bash o Zsh
  • No tiene sintaxis moderna

🟦 3.2 Bash — Bourne Again Shell

✔️ Características

  • El shell más usado en Linux
  • Compatible con POSIX sh
  • Arrays, diccionarios, brace expansion, process substitution
  • Funciones avanzadas
  • [[ ]] test mejorado
  • coproc, mapfile, readarray

✔️ Ventajas

  • Potente y muy documentado
  • Ideal para scripting serio

❌ Desventajas

  • Más lento que Dash
  • No es POSIX puro (tiene extensiones)

⭐ 3.3 Zsh — El shell más avanzado para usuarios

✔️ Características

  • Autocompletado espectacular
  • Globbing avanzado
  • Arrays potentes
  • Plugins (Oh My Zsh)
  • Prompt extremadamente configurable

✔️ Ventajas

  • El mejor shell interactivo
  • Muy rápido en autocompletado

❌ Desventajas

  • No es POSIX
  • Scripts Zsh no son portables

⚡ 3.4 Dash — Debian Almquist Shell

✔️ Características

  • Implementación minimalista de POSIX sh
  • Ultra rápido
  • Usado como /bin/sh en Debian/Ubuntu

✔️ Ventajas

  • Ideal para scripts del sistema
  • Arranca muy rápido

❌ Desventajas

  • No tiene extensiones de Bash
  • No sirve para scripting avanzado

🐟 3.5 Fish — Friendly Interactive Shell

✔️ Características

  • No es POSIX
  • Sintaxis propia
  • Autocompletado inteligente
  • Colores y sugerencias tipo IDE
  • Arrays nativos
  • Configuración web

✔️ Ventajas

  • El mejor shell para principiantes
  • Interactivo, moderno, cómodo

❌ Desventajas

  • No sirve para scripting POSIX
  • Sintaxis incompatible con Bash/Zsh

🧠 Resumen comparativo

ShellPOSIXVelocidadInteractivoScriptingExtensiones
sh✔️⚡⚡⚡✔️
bash✔️ (parcial)✔️✔️✔️✔️✔️
zsh⭐⭐⭐⭐⭐✔️✔️⭐⭐⭐⭐⭐
dash✔️⚡⚡⚡⚡⚡✔️
fish⭐⭐⭐⭐⭐⭐⭐⭐⭐

Vale, ahora entramos ya en “anatomía interna de un shell”. Te lo organizo por bloques para que todo encaje mentalmente.

1. Pipelines: qué son realmente cmd1 | cmd2 | cmd3

Un pipeline no es magia, es solo procesos conectados por pipes del kernel.

1.1. Qué hace el shell al ver A | B | C

Cuando escribes:

bash

A | B | C

El shell hace, conceptualmente:

  1. Crea dos pipes:
    • pipe1: conecta AB
    • pipe2: conecta BC
  2. forkea un proceso para cada comando:
    • hijo1 para A
    • hijo2 para B
    • hijo3 para C
  3. En cada hijo:
    • Redirige stdin/stdout a los extremos correctos de los pipes
    • Cierra los extremos que no usa
    • Llama a execve() con el comando correspondiente
  4. El shell padre:
    • Cierra todos los extremos de los pipes
    • Hace wait() a los hijos (o los registra como jobs)

1.2. A nivel de descriptores de archivo

Un pipe es un par de FDs:

c

int fds[2];
pipe(fds);   // fds[0] = lectura, fds[1] = escritura

Para A | B:

  • Proceso A:
    • dup2(fds[1], STDOUT_FILENO); // su stdout va al pipe
  • Proceso B:
    • dup2(fds[0], STDIN_FILENO); // su stdin viene del pipe

Luego cierran los FDs originales y ejecutan execve().

2. File descriptors y redirecciones

2.1. Qué es un file descriptor (FD)

Un file descriptor es simplemente un entero que representa un recurso abierto:

  • 0 → stdin
  • 1 → stdout
  • 2 → stderr

El kernel mantiene una tabla de FDs por proceso.

2.2. Redirecciones típicas

Ejemplos:

bash

cmd > out.txt        # redirige stdout (1) a archivo
cmd 2> err.txt       # redirige stderr (2)
cmd > out.txt 2>&1   # stderr → stdout → archivo
cmd < in.txt         # stdin desde archivo

Internamente, el shell hace cosas como:

c

int fd = open("out.txt", O_WRONLY|O_CREAT|O_TRUNC, 0644);
dup2(fd, STDOUT_FILENO);
close(fd);
execve(...);

dup2(oldfd, newfd) hace que newfd apunte al mismo recurso que oldfd.

2.3. Combinando pipes y redirecciones

Ejemplo:

bash

A 2>err.log | B >>out.log
  • A:
    • stderr (2) → err.log
    • stdout (1) → pipe
  • B:
    • stdin (0) ← pipe
    • stdout (1) → out.log en modo append

3. Mini-shell en C con fork/exec/wait (versión conceptual)

Te hago una versión simplificada, sin pipes ni redirecciones, solo para ver el esqueleto.

3.1. Bucle principal de un shell

Pseudocódigo:

c

while (1) {
    mostrar_prompt();
    leer_linea(buf);
    parsear_linea(buf, argv);   // separar en tokens
    pid = fork();
    if (pid == 0) {
        // Hijo
        execvp(argv[0], argv);
        perror("execvp");
        exit(1);
    } else {
        // Padre
        waitpid(pid, &status, 0);
    }
}

3.2. Añadiendo redirecciones y pipes

  • Antes de execvp() en el hijo:
    • Detectas > < 2> | en los tokens
    • Configuras open(), dup2(), pipe()
    • Ajustas argv para que solo contenga el comando y sus argumentos
  • Para pipelines:
    • Creas varios hijos
    • Conectas sus FDs con pipe() y dup2()
    • El padre hace wait() a todos

La lógica real de Bash/Zsh es mucho más compleja, pero la base es esta.

4. Diferencias profundas entre [[ ]][ ] y test

Estos tres se usan para condiciones, pero no son equivalentes.

4.1. test y [ ] (POSIX)

test es un comando (builtin o externo):

bash

test "$x" = "hola"

[ ] es simplemente una forma alternativa de escribir test:

bash

[ "$x" = "hola" ]

Detalles:

  • [ es el comando
  • ] es solo el último argumento
  • Es POSIX, existe en sh, bash, zsh, dash…

Problemas típicos:

  • Expansiones vacías pueden romper la sintaxis:bash[ $x = hola ] # si x está vacío → [ = hola ] → error

Por eso siempre se recomienda:

bash

[ "$x" = "hola" ]

4.2. [[ ]] (extensión de Bash/Zsh)

[[ ]] no es un comando, es una construcción del lenguaje (keyword-like).

Ventajas:

  • No hace expansión de pathname (globbing)
  • Maneja mejor variables vacías
  • Permite operadores extra:
    • [[ $x == patrón ]]
    • [[ $x =~ regex ]]
  • No requiere comillas en muchos casos:

bash

[[ $x = hola ]]
[[ $x == *.txt ]]
[[ $x =~ ^[0-9]+$ ]]

Esto en [ ] sería peligroso o imposible sin escapes.

4.3. Resumen práctico

  • Para scripts POSIX portables: usa [ ] o test.
  • Para scripts Bash/Zsh modernos: usa [[ ]] siempre que puedas.

5. Job control y process groups

Aquí entramos en cómo el shell controla procesos en foreground/background.

5.1. Process groups

Un process group es un conjunto de procesos que el kernel trata como una unidad para señales de terminal.

Ejemplo:

bash

A | B | C

Los tres procesos suelen pertenecer al mismo process group.

¿Por qué?

  • Si pulsas Ctrl+C (SIGINT), la señal se envía al grupo, no solo a uno.
  • El shell puede parar/reanudar el grupo entero.

5.2. Foreground vs background

Cuando haces:

bash

sleep 100 &
  • El shell crea un job en background
  • No bloquea el prompt
  • El proceso (o grupo) sigue ejecutándose

Cuando haces:

bash

sleep 100
  • El job está en foreground
  • El shell hace wait() hasta que termine

5.3. Señales y job control

Señales relevantes:

  • SIGINT → Ctrl+C
  • SIGTSTP → Ctrl+Z (suspender)
  • SIGCONT → reanudar
  • SIGCHLD → el hijo ha terminado o cambiado de estado

El shell:

  • Recibe SIGCHLD cuando un hijo termina
  • Actualiza la tabla de jobs
  • Muestra mensajes tipo [1]+ Done

5.4. Comandos de job control en el shell

  • jobs → lista jobs
  • fg %1 → trae job 1 al foreground
  • bg %1 → reanuda job 1 en background
  • kill %1 → envía señal al job 1

Internamente, el shell usa:

  • setpgid() / getpgid() para gestionar grupos
  • tcsetpgrp() para asignar el terminal al grupo en foreground

6. Cómo encaja todo junto

Cuando ejecutas:

bash

A | B | C >out.txt 2>err.txt &

El shell hace algo así:

  1. Crea pipes para conectar A→B→C.
  2. Crea un process group para A, B y C.
  3. Para cada comando:
    • fork()
    • En el hijo:
      • setpgid() para unirlo al grupo
      • dup2() para redirecciones y pipes
      • execve() del binario
  4. Marca el job como background (no hace wait() bloqueante).
  5. Sigue aceptando comandos.
  6. Cuando los procesos terminan:
    • El kernel envía SIGCHLD al shell
    • El shell actualiza el estado del job

Publicaciones Similares

  • Powershell

    Para manejar PowerShell de manera básica, aquí tienes cómo se aplican los conceptos fundamentales que mencionamos antes: Para manejarte de manera básica en PowerShell, es útil conocer algunos cmdlets fundamentales. Aquí tienes una lista de los principales cmdlets que deberías aprender: Más Cmdlets Útiles Uso de Tuberías (Pipelines) Las tuberías en PowerShell permiten pasar la…

  • Lenguajes de Programacion II

    Aquí va una respuesta clara, directa y útil, David —pensada para que entiendas qué hay que dominar realmente para manejar cualquier lenguaje de programación, sin importar si es Python, JavaScript, C, Go o Rust. 🧠 1. Comprender la lógica básica de programación Esto es lo que de verdad se transfiere entre lenguajes: Si entiendes esto,…

  • |

    Optimización Recursos Sistema Linux

    Archivos de Configuración y Scripts Comunes en Bash: Aquí tienes algunos comandos y herramientas que te ayudarán a verificar el uso de recursos en tu servidor Linux: Comandos bash utiles Estos comandos te ayudarán a identificar qué procesos están consumiendo más recursos y si necesitas ajustar algo en tu servidor. Para comprobar la capacidad del…

  • Javascript para el dinamismo de la web

    1. ¿Qué es JavaScript? Es un lenguaje de programación interpretado, orientado a objetos y basado en prototipos. Su función principal en la web es crear interactividad: desde validar formularios hasta actualizar contenido sin recargar la página (AJAX/Fetch) y controlar animaciones complejas.  2. Fundamentos Esenciales A. Variables (Contenedores de datos) En el JS moderno, ya no…

  • |

    PHP

    PHP está diseñado para ser fácil de aprender y potente en su aplicación, lo que lo convierte en una opción popular para desarrolladores de todos los niveles. Aquí tienes algunos aspectos básicos: Comentarios: Puedes agregar comentarios en tu código PHP para hacerlo más legible. Los comentarios de una sola línea comienzan con //, mientras que los comentarios…

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *