a) Crear un programa que reciba por línea de comandos una serie de archivos. El programa principal debe ejecutar un thread por cada archivo recibido, y pasarle el nombre de ese archivo como parámetro. Luego cada thread debe crear una copia del archivo recibido pasando todas las letras a mayúsculas. Se debe escribir un mensaje en pantalla al entrar al thread, y si hubo algún error. El main debe imprimir un mensaje con el id del thread cada vez que se cierra.
El thread debe devolver cero si se cerró bien, y 1 si tuvo algún error.
Además se debe crear un contador de archivos, el cual cada thread debe incrementar cada vez que terminó de procesar correctamente cada archivo recibido. Cuando el programa finalice, debe mostrar la cantidad de archivos correctamente procesados. Este recurso debe estar correctamente manejado con mutex.
b) Realizar una versión del programa con threads detach, sincronizando el final del programa con un contador de threads finalizados. Este recurso debe estar correctamente manejado con mutex.
c) Realizar un nuevo programa igual al del punto a) pero en lugar de usar threads, usar funciones comunes. Medir el tiempo de ejecución de los 2 programas y comparar. Puede utilizarse la siguiente funcion:
double what_time_is_it() { struct timespec now; clock_gettime(CLOCK_REALTIME, &now); return now.tv_sec + now.tv_nsec*1e-9; }
int main () { double inicio, fin, dif; inicio = what_time_is_it(); // programa fin = what_time_is_it(); dif = fin - inicio; printf("tiempo empleado: %lf\n", dif); return 0; }