Ok, je courais POV-Ray sur toutes les démos, mais POV est toujours mono-thread et n'utiliserait pas plus d'un core. J'ai donc commencé à penser à une solution dans BASH.Programmation BASH multi-threadée - méthode généralisée?
J'ai écrit une fonction générale qui prend une liste de commandes et les exécute dans le nombre désigné de sous-shells. Cela fonctionne en fait, mais je n'aime pas la façon dont il gère l'accès à la commande suivante de manière thread-safe
multi-processus:
- Il faut, comme un argument, un fichier avec les commandes (1 par ligne),
- Pour obtenir la commande "next", chaque processus ("thread") sera:
- Waits jusqu'à ce qu'il puisse créer un fichier de verrouillage, avec: en $ CMDFILE $ LockFile
- Lisez la commande pour m le fichier,
- Modifie $ CMDFILE en supprimant la première ligne,
- Supprime le $ LOCKFILE.
Est-il possible de faire plus propre cela? Je ne pouvais pas obtenir les sous-shells pour lire une seule ligne d'une FIFO correctement. Par ailleurs, le but de ceci est d'améliorer ce que je peux faire sur une ligne de commande BASH, et de ne pas trouver de solutions non-bash. J'ai tendance à effectuer beaucoup de tâches compliquées à partir de la ligne de commande et je veux un autre outil dans la boîte à outils.
En attendant, voici la fonction qui gère l'obtention de la ligne suivante à partir du fichier. Comme vous pouvez le voir, il modifie un fichier sur disque chaque fois qu'il lit/supprime une ligne. C'est ce qui semble hackish, mais je ne trouve rien de mieux, puisque FIFO n'a pas fonctionné sans setvbuf() dans bash.
#
# Get/remove the first line from FILE, using LOCK as a semaphore (with
# short sleep for collisions). Returns the text on standard output,
# returns zero on success, non-zero when file is empty.
#
parallel__nextLine()
{
local line rest file=$1 lock=$2
# Wait for lock...
until ln "${file}" "${lock}" 2>/dev/null
do sleep 1
[ -s "${file}" ] || return $?
done
# Open, read one "line" save "rest" back to the file:
exec 3<"$file"
read line <&3 ; rest=$(cat<&3)
exec 3<&-
# After last line, make sure file is empty:
([ -z "$rest" ] || echo "$rest") > "${file}"
# Remove lock and 'return' the line read:
rm -f "${lock}"
[ -n "$line" ] && echo "$line"
}
Postez votre code! –
Jetez un oeil à 'lockfile-progs (1)' pour voir si cela aide. Le problème avec le FIFO peut avoir à voir avec la mise en mémoire tampon. Certains utilitaires ont un mode sans tampon. –