Está en la página 1de 55

Lenguaje C

Para Administradores de
Red

Fernando I. Díaz Sánchez


Lenguaje C

El Administrador de Red debe ser una de esas personas que, durante el


trabajo, mientras menos lo vean las cosas estarán mejor. Nada mas imagínese a uno
de ellos corriendo como pollo sin cabeza por toda la oficina o aun peor, que de
pronto lo llame a Ud. y le diga que apague su PC porque va a restaurar en el servidor
todos sus emails que han sido borrados.

Ser Administrador de Red no es fácil, y menos si todos piensan que no hacen nada. La
verdad es que si uno de ellos está tranquilo y concentrado es porque algo bueno
viene creando en su mente, está optimizando, aprendiendo, ordenando, ellos no
están contentos si algo se puede hacer mejor y mas rápido.

Al aprender el lenguaje C las cosas para un Administrador de Red pueden salir mucho
mejor y más rápido, deja de estar atado a programas que usa para crear los que
realmente quiere y necesita. Conociendo el Lenguaje C las posibilidades de hacer
cosas asombrosas son muchas. Es cierto, también pueden salir mal, sobre todo si no
prestan atención a los detalles.

Este contenido es un pequeño intento por mejorar el aprendizaje de un Lenguaje que


ha hecho posible que tengamos un digno trabajo.
>>Fids
Lenguaje C

MAXIMA: «Domina las


variables, y dominaras el
sistema…»
Lenguaje C

SCRIPT I

Variables en C
Lenguaje C

Script I – Variables en C

>> Variables
>> Direcciones de Memoria
>> Tamaño
>> Unidad Básica de Almacenamiento
>> Tipos de Datos Básicos en C
>> Tamaño de los tipos de datos básicos en C
>> Limites de los tipos de datos básicos en C
>> Cualificadores de los tipos de datos básicos en C
>> Cualificadores de Tamaño
>> Cualificadores de Valor
>> Resumen de Tipos de Datos
>> Tipos de Datos Especiales
>> Prueba de Concepto - Detrás de las Variables
>> Bonus Track - División de bytes & Protocolo IP
>> Bonus Track – Endianness & Lilliput
>> Tarea para la Casa
>> Anexos
>> Bibliografía
Lenguaje C

int edad = 10;


Lenguaje C

VARIABLES
Las variables almacenan datos, eso no tiene
ninguna novedad.
int
El problema es que en C, debemos conocer
QUE ES REALMENTE una variable y DE QUE
ESTA COMPUESTA

Aquí podemos ver una representación de la


10 edad
línea: int edad = 10;

Pero hay algo que no pusimos en el código…

Y QUE EXISTE REALMENTE 0xf0113b1


Lenguaje C

DIRECCIONES DE MEMORIA
int
Las variables almacenan datos, PERO nadie
se pregunto en donde se guardan esos
datos…

Por esa razón, tus programas no funcionan 10 edad


Las variables se guardan en la MEMORIA del
computador, y la única manera de
encontrarlas entre tanta memoria es
mediante su DIRECCION 0xf0113b1
El 2do problema en el lenguaje C es que las
direcciones de memoria están identificadas
con números HEXADECIMALES…
Y eso no es todo, le antepone las letras 0x
Lenguaje C

TAMAÑO
int
Las variables almacenan datos en
memoria, PERO nadie se pregunto hasta
ahora que tamaño ocupan en memoria 32 bits

Por esa razón, tus programas son lentos 10 edad


El tamaño depende de que cosa quiero
guardar en memoria. ¿Un Número?, ¿Una
Letra?, ¿Una Fecha?, ¿Una Imagen?, etc.

Cuando hacemos programas, en realidad no


0xf0113b1
decimos «que cosa quiero guardar», sino
que «tipo de dato» voy a guardar

Y los tipos de datos tienen ya un tamaño


predefinido en bits
Lenguaje C

TAMAÑO
int
Las variables almacenan datos en memoria
que ocupan espacio según su tipo de dato y
son identificadas a través de su dirección de 32 bits
memoria. PERO se olvidaron de preguntar
cual el tamaño mínimo que podemos 10 edad
guardar

Por esa razón, tus programas son pesados

En las computadoras, el tamaño mínimo


que puede ser identificado (mediante su
0xf0113b1
dirección de memoria) es de 8 bits

Y 8 bits forman 1 byte…


Lenguaje C

UNIDAD BASICA DE ALMACENAMIENTO


1 byte ¿Y que puedo guardar en 1 miserable byte?

8 bits, y cada bit solo puede representar 2


posibles valores (cero o uno, encendido o
0 0 0 0 0 0 0 0 apagado, blanco o negro, sonido o
silencio, etc., etc., etc.)

8 bits El mas conocido mundialmente es el de


ceros y unos…

1 1 1 1 1 1 1 1 Así nació el uso mundial del Sistema Binario

0x0361a71
Lenguaje C

UNIDAD BASICA DE ALMACENAMIENTO


1 byte ¿Por qué 8 y no 4, 5 ó 6?

Eso lo decidieron nuestros padres, que le


vamos a hacer…
0 0 0 0 0 0 0 0
Ellos pensaron que la combinación de 8 bits
da como resultado un buen balance para
8 bits interpretar información y ahorrar
complejidad en el seguimiento de las
direcciones de memoria.
1 1 1 1 1 1 1 1
Después de todo, 255 valores diferentes no

0x0361a71 esta nada mal para representar algo


Lenguaje C

UNIDAD BASICA DE ALMACENAMIENTO


1 byte ¿255 valores? Y eso de donde salió

No has prestado atención…

0 0 0 0 0 0 0 0 Cada bit solo puede tomar uno de 2 posibles


valores. El valor CERO o UNO. Por lo tanto, si
juntamos 8 combinaciones de ceros y
8 bits unos, tenemos:

0000 0000 =0
1 1 1 1 1 1 1 1 0000 0001 =1
0000 0010 =2

0x0361a71 0000 0011


….
=3

1111 1111 = 255


Lenguaje C

UNIDAD BASICA DE ALMACENAMIENTO


1 byte ¿Y como se guardan las letras del teclado?

Las letras o caracteres, son en realidad


números que el sistema operativo interpreta.
0 0 0 0 0 0 0 0
Por ejemplo, la letra ‘A’ en realidad
corresponde con el número 65. La tecla
8 bits ENTER corresponde con el número 13, etc.

Esa correspondencia (número -> carácter)


1 1 1 1 1 1 1 1 obedece a estándares internacionales
diseñados hace muchos años.

0x0361a71 Un estándar conocido es el formato ASCII


Lenguaje C

UNIDAD BASICA DE ALMACENAMIENTO


1 byte Si 8 bits me permiten combinar 255 valores
diferentes, y pueden servir para representar
caracteres…

0 0 0 0 0 0 0 0 ¿Cómo sabemos que el valor 65 hace


referencia al número 65 y no a la letra ‘A’?

8 bits …Eso lo sabemos según el TIPO DE DATO que


hemos utilizado

1 1 1 1 1 1 1 1 El 3er problema en C es la confusión entre


los tipos de datos y el desconocimiento de

0x0361a71 como se almacenan en memoria


Lenguaje C

TIPOS DE DATOS BASICOS EN C


¿Y no que todo era binario…?

char Sí, todo lo que guardamos es binario, pero el


Lenguaje C nos permite «CLASIFICAR» lo que

int guardamos en binario…

Los tipos de dato nos permiten darle un


float «sentido» a la información que guardamos

Técnicamente los tipos de dato se reducen a


double números de diferentes tamaños y formas

Es decir, el lenguaje C bailará con números…


Lenguaje C

TIPOS DE DATOS BASICOS EN C

char Caracteres (visibles e invisibles)

int Números Enteros

float Números de simple precisión

double Números de doble precisión


Lenguaje C

TAMAÑO DE LOS TIPOS DE DATOS BASICOS EN C

char
8 bits

int
32 bits

float
32 bits

double
64 bits
Lenguaje C

LIMITES DE TIPOS DE DATOS BASICOS EN C

char 0 a 255

int -2147483648 a 2147483647

float Números de simple precisión

double Números de doble precisión


Lenguaje C

CUALIFICADORES DE TIPOS DE DATOS BASICOS EN C


¿Cuali… qué?

short Ahora sabemos bien el tamaño que ocupan


los tipos de datos, pero uno llega a
long preguntarse:

long long ¿Y si quiero guardar el valor 256, porque


desperdiciar 16 bits que no usare con el int?
signed ¿Y que pasa con los valores negativos?

unsigned ¿Hay alguna manera de ajustar los tamaños


de los tipos de datos para hacerlos mas
flexibles?
Lenguaje C

CUALIFICADORES DE TIPOS DE DATOS BASICOS EN C


¿Qué son los cualificadores?

short Son mecanismos en C que permiten


«ajustar» los tamaños o límites de los tipos
long de datos básicos, ya sea a modo de
expansión o de reducción en los bits que
long long ocupan o en su representación numérica

signed De todos ellos, el cualificador signed es el


cualificador por defecto.

unsigned Es decir, todas las variables que se declaren


en un programa en C tendrán el cualificador
signed a menos que se indique lo contrario
Lenguaje C

CUALIFICADORES DE TAMAÑO

short int
16 bits

int
32 bits

long int
64 bits
Lenguaje C

CUALIFICADORES DE TAMAÑO

¿Y nuestro
querido char
char porque no
8 bits

tiene
cualificadores
de tamaño?
Lenguaje C

CUALIFICADORES DE VALOR

unsigned char
8 bits

unsigned int
32 bits

unsigned short
16 bits

unsigned
64 bits long
Lenguaje C

RESUMEN DE TIPOS DE DATOS


Tipo de dato signed / Limite signed Limite unsigned
unsigned
char 8 bits -128 a 127 0 a 255

short [int] 16 bits -32768 a 32767 0 a 65535

int 32 bits -2147483648 a 2147483647 0 a 4294967295

long [int] 64 bits -9223372036854775808 to 0 to 18446744073709551615


9223372036854775807
long long [int] 64 bits -9223372036854775808 to 0 a 9223372036854775807
9223372036854775807
float 32 bits 1.17549e-38 to 3.40282e+38 No existe

double 64 bits 2.22507e-308 to 1.79769e+308 No existe

long double 128 bits 2.22507e-308 to 1.79769e+308 No existe

Nota: Los tipos de datos float, double y long double no usan cualificadores de valor (signed o unsigned)
Lenguaje C

RESUMEN DE TIPOS DE DATOS

Nota: Los tipos de datos mostrados son de un servidor Red Hat 6.2 64 bits , es posible que los valores difieran en otros SO
Lenguaje C

TIPOS DE DATOS ESPECIALES


¿Qué tienen de especial?

bool El tipo dato bool solo permite registrar los


valores enteros CERO y UNO
void Internamente, el tipo de datos bool ocupa 1
byte (al igual que char), pero no se permite
guardar números diferentes de cero o uno.
Si el valor asignado es diferente de CERO, la
variable de tipo bool tomara el valor UNO.

Este comportamiento nos permite


representar los valores VERDADERO (true,1)
o FALSO (false,0). Para poder usar bool
debemos incluir la librería stdbool.h
Lenguaje C

TIPOS DE DATOS ESPECIALES

bool
Nótese que usamos el header
stdbool.h para poder usar el
tipo de dato bool

Nota: Una confusión común es no tener claro si 1 es FALSO o VERDADERO. Una forma
sencilla de recordarlo es preguntarse cuanto vale un billete FALSO 
Lenguaje C

TIPOS DE DATOS ESPECIALES


¿Qué tienen de especial?

bool El tipo dato void permite guardar cualquier


información para luego ser recuperada según
void el tipo de dato que nos interese

El tipo de datos void ocupa 8 bytes debido a


que lo que guarda en realidad son
direcciones de memoria

Para poder usar una variable del tipo


void, deben usarse en forma de punteros
(void *), de lo contrario ocurrirá un error de
compilación
Lenguaje C

int edad = 10;


Lenguaje C

DETRAS DE LAS VARIABLES


int
0000 0000 0000 0000 0000 0000 0000 1010
edad
8 bits 8 bits 8 bits 8 bits

10
0x7ffffc127f27 0x7ffffc127f26 0x7ffffc127f25 0x7ffffc127f24

32 bits
Lenguaje C

DETRAS DE LAS VARIABLES

Ir a siguiente dirección de memoria

???
Ir a siguiente dirección de memoria

Ir a siguiente dirección de memoria

Se puede apreciar que la variable edad


abarca 4 bytes de memoria porque es
de tipo int.

En cambio los valores de tipo char solo


abarcan 1 byte
Lenguaje C

DETRAS DE LAS VARIABLES – PRUEBA DE CONCEPTO

DEMOSTRADO !

El lenguaje C solamente maneja bits con sus


posiciones de memoria; Es el programador
quien decide como quiere interpretar los
bits valiéndose de los tipos de datos
proporcionados por el lenguaje

Nota: EL orden de los caracteres se debe a que se la arquitectura trabaja con LittleEndian del cual trataremos ma adelante
Lenguaje C

DETRAS DE LAS VARIABLES – PRUEBA DE CONCEPTO

DEMOSTRADO !

El tipo de dato void permite ubicarse


en cualquier posición de memoria de
cualquier variable del programa
¿Cuándo USAR VOID?

El uso del tipo de dato void suele utilizarse en programas complejos que requieren alta
velocidad y flexibilidad en la manipulación de datos. Su desventaja es lo peligroso que puede
llegar a ser y lo engorroso en su sintaxis
Lenguaje C

DETRAS DE LAS VARIABLES

 Las variables son estructuras del lenguaje C que permiten almacenar


información que es accedida mediante una dirección de memoria y que
ocupan un tamaño según sea el tipo de dato y cualificador con las que
fueron declaradas.
 El sistema operativo es el responsable de separar el espacio necesario por
cada variable a utilizar
 El programador es el responsable de darle la adecuada interpretación a
los datos así como su adecuada manipulación.
 Las variables guardan información binaria agrupada en bloques de 8 bits
 Dependiendo de la arquitectura del equipo donde se ejecuta un
programa en C, las variables pueden ser almacenadas ya sea en formato
Big Endian o Little Endian
 Conociendo el funcionamiento de las variables podremos optimizar
nuestros programas y hackear el sistema!
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

Si bien la unidad básica de almacenamiento


es 1 byte, sus 8 bits que lo componen
0 0 0 0 0 0 0 0 pueden ser referenciados mediante variables

Por ejemplo, podemos crear 2 variables cada


una de 4 bits o inclusive podemos crear 8
4 bits 4 bits variables de 1 bit cada una

1 1 1 1 1 1 1 1 Esto es particularmente útil cuando


diseñamos protocolos de comunicación para
8 bits redes de computadoras

0x0361a71
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

Es importante recordar que si bien podemos


fragmentar los bytes, no podemos reducir su
0 0 0 0 0 0 0 0 tamaño de almacenamiento.

Imaginemos que necesitamos guardar los


días de la semana (que son 7) e
3 bits 5 bits ingenuamente pensamos que podremos
optimizar espacio en disco si declaramos una
1 1 1 1 1 1 1 1 variable de 3 bits de longitud

8 bits La sorpresa será que la variable de 3 bits

0x0361a71 declarada sigue teniendo un tamaño de 1


byte
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

¿Entonces de que me sirve?

0 0 0 0 0 0 0 0 Nos sirve de mucho si queremos ahorrar


espacio al máximo, siempre y cuando
tengamos mas de 1 variable que podamos
incluir en 1 byte
3 bits 5 bits
Ejemplo:
1 1 1 1 1 1 1 1 Necesitamos 2 variables para almacenar el
día de la semana y el día del mes
8 bits

0x0361a71
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

¿Entonces de que me sirve?

0 0 0 0 0 0 0 0 El programador común hará algo similar a


esto:

int dia_semana = 7;
3 bits 5 bits int dia_mes = 31;

1 1 1 1 1 1 1 1 Estas variables consumen 64 bits (cada int


ocupa 32 bits)
8 bits

0x0361a71
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

¿Entonces de que me sirve?

0 0 0 0 0 0 0 0 El programador obsesionado con el tamaño


de sus variables hará esto:

struct fecha{
3 bits 5 bits unsigned char dia_semana:3;
unsigned char dia_mes:5;
1 1 1 1 1 1 1 1 };

8 bits Estas variables juntas consumen solo 8 bits

0x0361a71
Lenguaje C

BONUS TRACK
1 byte Dividiendo los bytes

Wow !

0 0 0 0 0 0 0 0 64 bits vs 8 bits es una diferencia bastante


grande cuando se trata de redes y
comunicaciones.
3 bits 5 bits Es por eso que los protocolos aprovechan
esta característica del lenguaje C para hacer
1 1 1 1 1 1 1 1 de las suyas y llevar al limite el envío de
información en pocos bits
8 bits

0x0361a71
Lenguaje C

BONUS TRACK
Prueba de
Concepto

Demostrado !

Se puede reducir
significativamente
el tamaño de las
variables
agrupándolas en
estructuras y
dividiendo sus
bytes.
Lenguaje C

BONUS TRACK – PROTOCOLO IP


Prueba de Concepto

Demostrado !

Se puede apreciar una implementación


(barata por supuesto) del protocolo IP el
cual aplica el concepto de división de bytes

Un paquete IP normal ocupa 20 bytes


gracias a este mecanismo.

De esta manera se ahorra espacio al enviar


trafico por la red
Lenguaje C

BONUS TRACK - ENDIANNESS


int
0000 0000 0000 0000 0000 0000 0000 1010
edad
8 bits 8 bits 8 bits 8 bits

10
0x7ffffc127f27 0x7ffffc127f26 0x7ffffc127f25 0x7ffffc127f24

¿En que orden se almacenan los bits?

Uno de los aspectos mas confusos cuando se aprende el lenguaje C a fondo es la


forma en la que se almacenan físicamente los datos.
Lenguaje C

BONUS TRACK - ENDIANNESS

Despedazando el Byte MSB LSB

La forma en la que se numera un byte es de


derecha a izquierda. Esto a veces no es simple de
entenderlo. Pondremos un ejemplo sencillo
7 6 5 4 3 2 1 0
Imaginemos que pudiéramos guardar números
decimales dentro de un byte. ¿Cuál sería la
manera correcta de numerar el 765?

¿00000765 o 76500000 ?
10
0 0 0 0 1 0 1 0
A algunos le resulta razonable la 2da forma hasta
que se encuentran con el problema de numerar
7650 o 76500
0x0361a71
Lenguaje C

BONUS TRACK - ENDIANNESS

Despedazando el Byte MSB LSB

Eso no es todo. Cada byte contiene 2 partes bien


diferenciadas a tener en cuenta.

La posición 0 (cero) que se encuentra mas a la


7 6 5 4 3 2 1 0
derecha se le conoce como LSB (Less Significant
Bit) o Bit menos significativo

La posición 7 que se encuentra mas a la


izquierda, se le conoce como MSB (Most
10
0 0 0 0 1 0 1 0
Significant Bit) o Bit Mas significativo

Son utilizados para realizar operaciones con bits 0x0361a71


Lenguaje C

BONUS TRACK - ENDIANNESS


Prueba de Concepto

Demostrado !

Los datos son almacenados en


bits agrupados en 8 formando
1 byte. Se almacenan siguiendo
la numeración tradicional (de
derecha a izquierda)
Lenguaje C

BONUS TRACK - ENDIANNESS


¿Y cuál es el problema?

No hay ningún problema para almacenar 1 byte. El problema viene cuando queremos
almacenar información multibyte (tipos de dato diferentes de char)

¿Por qué es un problema? 32 bits ( 4 bytes)

Porque todos los equipos con un 0 0 0 10 Little Endian


formato Little Endian leerán de forma
byte 4 byte 3 byte 2 byte 1
incorrecta la información proveniente
de los equipos con formato Big Endian y 32 bits ( 4 bytes)
viceversa
10 0 0 0 Big Endian
En nuestro ejemplo, el byte 1 es distinto
en ambos formatos. Babilonia otra vez! byte 4 byte 3 byte 2 byte 1
Lenguaje C

BONUS TRACK - ENDIANNESS


¿De donde provienen los nombres Little Endian y Big Endian?

Los nombres fueron extraídos de la novela «Los viajes de Gulliver» que relata la
disputa en Lilliput por la forma de comer los huevos cocidos. Unos exigían que debía
ser por la parte pequeña (Little Endian) y otros por la parte grande (Big Endian)
32 bits ( 4 bytes)

El formato Little Endian es el mas


común, sin embargo algunas 0 0 0 10 Little Endian
arquitecturas trabajan con Big Endian. byte 3 byte 1
byte 4 byte 2

Big Endian también es muy utilizado en 32 bits ( 4 bytes)


la transmisión de datos de red, por lo
tanto la mayoría de protocolos lo 10 0 0 0 Big Endian
implementa con este formato
byte 4 byte 3 byte 2 byte 1
Lenguaje C

BONUS TRACK - ENDIANNESS

Prueba de Concepto

Demostrado !

El formato Little Endian


empieza su numeración desde
el extremo izquierdo
Lenguaje C

TAREA PARA LA CASA


¿No hay cuando acabar con estos tipos?

clock_t El lenguaje C no solo tiene tipos de datos


básicos, también tiene otros tipos de datos
time_t que permiten manipular información mas
compleja (como el tiempo)
wchar_t Incluso, el lenguaje C permite ‘crear’
wint_t nuestros propios tipos de datos mediante
estructuras y uniones para representar
entidades mas complejas que un tipo de
dato básico no basta para completarlo

Investiga que otros tipos de datos no básicos


podemos usar en C
Lenguaje C

TAREA PARA LA CASA


¿No hay cuando acabar con estos tipos?
int8_t El lenguaje C es muy popular en el mundo y
uint32_t ha tenido varios estándares mundiales que
rigen su buen uso y mejoras en el tiempo.

intptr_t Entre los estándares mas conocidos tenemos


al estándar C99 (1999) y C11 (2011) cuyas
intmax_t reglas han sido agregadas en los diferentes
compiladores de C.
size_t En estos estándares se recomienda usar
… etc tipos de datos enteros basados en su
tamaño. Investiga cuales son y para que
sirven
Lenguaje C

Anexos
¿Qué necesito para programar en C bajo Linux? Nota: La extensión .exe es
solo para referencia
gcc, gdb, vim sencilla de que se trata
de un ejecutable, no es
¿Cómo compilar un programa C en Linux? necesario por lo tanto
agregarle dicha extensión
gcc mi-programa.c -g -o mi-programa.exe en realidad

¿Cómo depurar un programa C en Linux? Nota: Si se desea


programar con el
gdb mi-programa.exe estándar C11 se deberá
obtener una copia del
¿Qué necesito para programar en C bajo Windows? compilador gcc 4.8.1.

Visual C++ ó Borland C ó C Builder, etc


Lenguaje C

Bibliografia
The C Programming Language, 2nd Edition, B. Kernighan, Dennis Ritchie.

The Art and Science of C, Eric S. Roberts.

Programming in C, 3rd Edition, Stephen G. Kochan

Programación en C, Metodología, algoritmos y estructura de datos. Luis Joyanes


Aguilar

C Programming A Modern Approach. Second Edition. K.K.King

Essential C. Standford CS Education Library. Nick Parlante


Lenguaje C

Bibliografia
Bit Numbering (http://en.wikipedia.org/wiki/Bit_numbering)

Endianness (http://en.wikipedia.org/wiki/Endianness)

White Paper: Endianness or Where is Byte 0?. Bertrand Blanc, Bob Maaraoui

Understanding Big and Little Endian Byte Order | Better Explained


(http://betterexplained.com/articles/understanding-big-and-little-endian-byte-order)

Writing endian-independent code in C. Harsha S. Adiga


(http://www.ibm.com/developerworks/aix/library/au-endianc/index.html?ca=drs-)

ISO/IEC 9899:TC2 (C99)

También podría gustarte