PROGRAMACION
PROGRAMACION
CONCEPTOS Y DEFINICIONES
La programación a la que estamos más acostumbrados, la secuencial, estuvo en sus inicios
fuertemente influenciada por las arquitecturas de único procesador, en las cuales disponíamos como
características base:
• de un único procesador (CPU),
• de los programas y los datos que están almacenados en memoria RAM, y
• de los procesadores, que se dedican básicamente a obtener un determinado flujo de
instrucciones desde la RAM, ejecutando una instrucción por unidad de tiempo
En este sentido los programas secuenciales son totalmente ordenados, éstos nos indican en qué orden
serán ejecutadas las instrucciones.
CONCEPTOS Y DEFINICIONES
Y una particularidad importante, los programas secuenciales son deterministas:
mediante una misma secuencia de datos de entrada, se ejecutará la misma secuencia de instrucciones
y se producirá el mismo resultado (salvo errores de ejecución causados por causas externas).
Esta afirmación no es cierta para la programación concurrente.
CONCEPTOS Y DEFINICIONES
Tradicionalmente, el software es escrito para ser computado en serie.
Esto significa:
• Es ejecutado en una única computadora con una única CPU
• El problema se divide en una sucesión de instrucciones
• Las instrucciones se ejecutan una después de otra
• Solo una instrucción puede ser ejecutada en un determinado instante de tiempo
CONCEPTOS Y DEFINICIONES
Características de Programas Secuenciales
• Es el estilo de programación que corresponde al modelo conceptual de Von Newmann.
• Un programa secuencial tiene una línea simple de control de flujo.
• Las operaciones de un programa secuencial están ordenadas de acuerdo con un orden estricto.
• El comportamiento de un programa es solo función de las sentencias que lo componen y del
orden en que se ejecutan.
• El tiempo que tarda en ejecutarse cada operación no influye en el resultado de un programa
secuencial.
• La verificación de un programa secuencial es sencilla:
• Cada sentencia da la respuesta correcta.
• Las sentencias se ejecutan en el orden adecuado.
CONCEPTOS Y DEFINICIONES
La programación concurrente nos permite desarrollar aplicaciones que pueden ejecutar múltiples
actividades de forma paralela o simultánea.
La programación concurrente es necesaria por varias razones:
• Ganancia de procesamiento, ya sea en hardware multiprocesador o bien en un conjunto dado
de computadoras. Mediante la obtención de ganancias en recursos, en capacidad de cómputo,
memoria, recursos de almacenamiento, etc.
• Incremento del throughput de las aplicaciones (solapamiento E/S con cómputo).
• Incrementar la respuesta de las aplicaciones hacia el usuario, poder atender estas peticiones
frente al cómputo simultáneo. Permitiendo a los usuarios y computadores, mediante las capacidades
extras, colaborar en la solución de un problema.
• Es una estructura más apropiada para programas que controlan múltiples actividades y
gestionan múltiples eventos, con el objetivo de capturar la estructura lógica de un problema.
• Da un soporte específico a los sistemas distribuidos.
Otro punto con cierta controversia, son las diferencias entre los términos de programación
concurrente, distribuida, paralela, y multithread. Todos ellos son usados en mayor o menor medida en
la construcción de sistemas distribuidos y/o paralelos.
Usaremos programación concurrente como marco global a los diferentes tipos de programación
distribuida, paralela y multithread, tendencia que viene siendo habitual en la literatura del campo
distribuido.
Aun así, hay una serie de diferencias que hay que puntualizar:
CONCEPTOS Y DEFINICIONES
Concurrencia frente a paralelismo: en paralelismo hay procesamiento de cómputo simultáneo
físicamente, en concurrencia el cómputo es simultáneo lógicamente, ya que el paralelismo implica la
existencia de múltiples elementos de procesamiento (ya sean CPU, o computadores enteros) con
funcionamiento independiente; mientras que la concurrencia no implica necesariamente que existan
múltiples elementos de procesamiento, ya que puede ser simulada mediante las capacidades de
multiprocesamiento del SO sobre la CPU.
Un caso típico es la programación multithread, múltiples hilos de ejecución en una misma aplicación
compartiendo memoria, pudiendo ser esta ejecución paralela si se ejecuta en una máquina
multiprocesador, o concurrente, lógicamente si se ejecuta en un solo procesador. Aun existiendo estas
diferencias, en la práctica las mismas técnicas son aplicables a ambos tipos de sistemas.
CONCURRENCIA FRENTE A PARALELISMO
Concurrente: “Coincidencia, concurso simultáneo de varias circunstancias (RAE)”
• Es la capacidad de algunas de las tareas que resuelven un problema de poder ser realizadas en
paralelo.
• Está presente en la naturaleza, la vida diaria, los sistemas de cómputo, etc.
Paralelo: “A la vez, a un mismo tiempo, simultáneamente (RAE)”
• Es la condición en que dos o más tareas que resuelven un problema se realizan exactamente al
mismo tiempo.
Mientras la concurrencia es una característica de las tareas, el paralelismo se asocia a los recursos que
se disponen para poder realizar esas tareas simultáneamente.
CONCEPTOS Y DEFINICIONES: Paralelo y Distribuido
La palabra paralelismo suele asociarse con altas prestaciones en cómputo científico en una
determinada plataforma hardware, por ej. supercomputadores, aunque cada vez se desplaza más a
plataformas basadas en clusters locales (computadoras enlazadas por redes de propósito general, o
bien redes de alta velocidad optimizadas para procesamiento paralelo). Estas computadoras están
físicamente en un mismo armario o sala de cómputo.
La palabra distribuido se ha referido típicamente a aplicaciones, ejecutándose en múltiples
computadoras (normalmente se implica además heterogeneidad de recursos), que no tenían por qué
estar físicamente en un mismo espacio. Este término también relaja su significado debido a la
extensión de los modelos paralelos, a ambientes como multicluster (múltiples clusters enlazados), o
grid, que, aun siendo generalmente considerados como paralelos, se acercan más a los sistemas
distribuidos.
En general estos términos son ampliamente difundidos, y usados con significados diferentes, aunque
las distinciones tienden a desaparecer, en especial cuando se consideran cada vez sistemas más
potentes de multiprocesamiento, y la fusión de sistemas paralelos y distribuidos aumenta con entornos
como grid. Llegando en la mayoría de los casos actuales a sistemas híbridos donde se integran los tres
tipos de programación (o de sistemas).
Podemos asimismo partir de una definición de sistema distribuido de computación como:
Una colección de elementos de cómputo autónomos, ejecutándose en uno o más computadores,
enlazados por una red de interconexión, y soportados por diferentes tipos de comunicaciones que
permiten observar la colección como un sistema integrado.
Los sistemas distribuidos operan sobre redes de computadoras, pero también se puede construir uno
que tenga sus elementos funcionando en un computador simple multitarea.
Además dl cásico basado en redes, se pueden incluir los computadores paralelos, y especialmente los
servidores en cluster, y otros ambientes como las redes wireless, y las redes de sensores. Por otra
parte, la computación grid abarca coordinación de recursos que no están sujetos a control centralizado
mediante el uso de protocolos e interfaces abiertas, de propósito general, para proporcionar diferentes
servicios.
Uno de los parámetros más interesantes a la hora de enfocar la programación concurrente sobre un
determinado sistema distribuido es conocer los diferentes estilos arquitectónicos en los que se basa,
así como su modelo de interacción y organización interna de los componentes.
La Computación Paralela es el uso simultáneo de múltiples recursos de cómputo para resolver un
problema computacional. Esto es:
• Se ejecuta utilizando múltiples procesadores
• El problema es divido en partes que pueden resolverse concurrentemente
• Cada parte es dividida en una serie de instrucciones, que a su vez se ejecutan simultáneamente
en diferentes procesadores
• Debe emplearse un mecanismo de coordinación general
Procesamiento paralelo
Un programa concurrente puede ser ejecutado por:
• Multiprogramación: los procesos comparten uno o más Procesadores
• Multiprocesamiento: cada proceso corre en su propio procesador pero con memoria
compartida
• Procesamiento Distribuido: cada proceso corre en su propio procesador conectado a los otros
a través de una red
Para la concepción de sistemas concurrentes y sus paradigmas de programación, hay que tener en
cuenta que tanto en el caso distribuido, como en el paralelo los sistemas disponen de múltiples
procesadores, que son capaces de trabajar conjuntamente en una o varias tareas para resolver un
problema computacional.
Existen muchas formas diferentes de construir y clasificar en diferentes taxonomías los sistemas
distribuidos y paralelos.
Presentaremos varias clasificaciones basadas en diferentes conceptos.
Taxonomía de Flynn
Ésta es una clasificación de sistemas arquitecturales muy usada en paralelismo y en cómputo
científico, que nos sirve para identificar tipos de aplicaciones y sistemas en función de los flujos de
instrucciones (ya sean threads, procesos o tareas) y los recursos disponibles para ejecutarlos.
En función de los conjuntos de instrucciones y datos, y frente a la arquitectura secuencial que
denominaríamos SISD (single instruction single data), podemos clasificar las diferentes arquitecturas
paralelas (o distribuidas) en diferentes grupos:
• SISD (single instruction single data)
• SIMD (single instruction multiple data),
• MISD (multiple instruction single data) y,
• MIMD (multiple instruction multiple data),
• SPMD (single program multiple data).
• MIMD Shared Memory (SMP o MPP).
• UMA
• NUMA
• MIMD Distributed Memory (Paso de Mensajes y MPP).
SIMD: un solo flujo de instrucciones es aplicado a múltiples conjuntos de datos de forma concurrente.
Unos procesos homogéneos (con el mismo código) sincrónicamente ejecutan la misma instrucción
sobre sus datos, o bien la misma operación se aplica sobre unos vectores de tamaño fijo o variable. El
modelo es válido para procesamientos matriciales y vectoriales, siendo las máquinas paralelas con
procesadores vectoriales un ejemplo de esta categoría.
MISD: el mismo conjunto de datos se trata de forma diferente por los procesadores. Son útiles en
casos donde sobre el mismo conjunto de datos se deban realizar muchas operaciones diferentes. En la
práctica no se han construido máquinas de este tipo por las dificultades en su concepción.
MIMD: paralelismo funcional y/o de datos. No sólo distribuimos datos, sino también las tareas a
realizar entre los diferentes procesadores/nodos. Varios flujos (posiblemente diferentes) de ejecución
son aplicados a diferentes conjuntos de datos. Esta categoría no es muy concreta, ya que existe una
gran variedad de arquitecturas posibles con estas características, incluyendo máquinas con varios
procesadores vectoriales o sistemas de centenares de procesadores o bien con unos pocos.
SPMD (variante de MIMD):en paralelismo de datos, utilizamos mismo código con distribución de
datos. Hacemos varias instancias de las mismas tareas, cada uno ejecutando el código de forma
independiente. SPMD puede verse como una extensión de SIMD o bien una restricción del MIMD. A
veces suele tratarse más como un paradigma de programación, en el cual el mismo código es
ejecutado por todos los procesadores (u nodos) del sistema, pero en la ejecución se pueden seguir
diferentes caminos en los diferentes procesadores.
2. Sistemas MIMD con memoria distribuida (distributed memory, MIMD), o también llamados
multicomputadores: En este modelo, cada procesador ejecuta un conjunto separado de instrucciones
sobre sus propios datos locales. La memoria no centralizada está distribuida entre los procesadores (o
nodos) del sistema, cada uno con su propia memoria local, en la que poseen su propio programa y los
datos asociados. El espacio de direcciones de memoria no está compartido entre los procesadores.
Una red de interconexión conecta los procesadores (y sus memorias locales), mediante enlaces (links)
de comunicación, usados para el intercambio de mensajes entre los procesadores. Los procesadores
intercambian datos entre sus memorias cuando se pide el valor de variables remotas.
Una ultima variante MIMD con memoria físicamente distribuida y red de interconexión dedicada,
especialmente diseñada, son los sistemas MPP (massive parallel processing). En éstos, el número de
procesadores puede variar desde unos pocos a miles de ellos. Normalmente, los procesadores están
organizados formando una cierta topología (tanto física como lógica, como: anillo, árbol, malla,
hipercubo, etc.), disponiendo de un red de interconexión entre ellos de baja latencia y gran ancho de
banda.
Escalabilidad
Es la capacidad de mantener/incrementar la eficiencia del programa en proporción al tamaño del
problema (número de elementos de procesamiento).
Transparencia
Significa ocultar al usuario/programador detalles que dan funcionalidad al sistema. Puede ser con
respecto:
• a la Ubicación → no distinguir entre recursos locales o remotos.
• a la Concurrencia → El usuario no “ve” la competencia y sincronización por los recursos.
• al Paralelismo y su implementación → Partir de la especificación del problema y no detenerse
en el modo de descomponerlo en tareas o de ejecutarlo en múltiples procesadores → mayor
abstracción → muy difícil obtener alta eficiencia.
Portabilidad
• La portabilidad de código se obtiene a través de estándares que permiten que el desarrollo de
programas paralelos/distribuidos se ejecuten sobre una variedad de arquitecturas (ejemplos: OpenMP,
MPI, Java)
• La portabilidad de performance es mucho más difícil de lograr → significa que en diferentes
arquitecturas el programa logre un rendimiento o eficiencia similar.
Tolerancia a Fallos
Es la habilidad de recuperar el sistema desde fallos de sus componentes sin perder la estabilidad del
sistema.
Un problema con las comunicaciones, entre los procesadores, reinicio del sistema, etc. no debería
afectar el funcionamiento del sistema.