194 votes

Errno n’est thread-safe ?

En , cette variable est déclarée comme donc ma question est, est-ce sécuritaire vérifier `` valeur après quelques appels ou utiliser perror() dans du code multi-threadé. Est-ce une variable de thread sécurisé ? Si non, alors quel est l’alternative ?

J’utilise linux avec gcc sous x86 architecture.

195voto

Charles Salvia Points 28661

Oui, c'est thread-safe. Sur Linux, le global variable errno est de thread spécifique. POSIX exige que errno être thread-safe.

Voir http://www.unix.org/whitepapers/reentrant.html

Dans POSIX.1, errno est définie comme une externe variable globale. Mais ce la définition est inacceptable dans un environnement multithread, parce que ses utilisation peut entraîner la non-déterministes résultats. Le problème est que deux ou plusieurs threads peuvent rencontrer des erreurs, tous les à l'origine du même errno à définir. Dans ces circonstances, un thread pourriez vérifier errno après il a déjà été mis à jour par un autre fil de discussion.

Pour contourner le résultant non-déterminisme, POSIX.1c redéfinit errno comme un service qui peut accéder à l' par thread numéro d'erreur comme suit (ISO/IEC 9945:1-1996, §2.4):

Certaines fonctions peuvent fournir le numéro de l'erreur dans une variable accessible à travers le symbole de errno. Le symbole errno est définie par y compris le l'en-tête , comme spécifié par le C Standard ... Pour chaque thread d'un processus, la valeur de errno est pas être affectée par des appels de fonctions ou de les affectations à errno par d'autres threads.

Voir aussi http://linux.die.net/man/3/errno

errno est thread-local; le réglage dans un thread n'affecte pas sa valeur dans toute autre thread.

61voto

DigitalRoss Points 80400
<h2>Oui<hr><p>Errno n’est pas une simple variable plus, c’est quelque chose de complexe dans les coulisses, plus précisément pour qu’elle soit thread-safe.</p><p>Voir <code></code> :</p><pre><code></code></pre><hr><p>Nous pouvons vérifier une deuxième fois :</p><pre><code></code></pre></h2>

15voto

Bastien Léonard Points 18404

Dans errno.h, cette variable est déclarée comme extern int errno;

Voici ce que la norme C dit:

La macro errno n'ont pas besoin d'être l'identifiant d'un objet. Il pourrait développer une modifiables lvalue résultant d'un appel de fonction (par exemple, *errno()).

Généralement, errno est une macro qui appelle une fonction retournant l'adresse du numéro d'erreur pour le thread en cours, puis déréférence.

Voici ce que j'ai sur Linux dans /usr/include/bits/errno.h:

/* Function to get address of global `errno' variable.  */
extern int *__errno_location (void) __THROW __attribute__ ((__const__));

#  if !defined _LIBC || defined _LIBC_REENTRANT
/* When using threads, errno is a per-thread value.  */
#   define errno (*__errno_location ())
#  endif

En fin de compte, il génère ce genre de code:

> cat essai.c
#include <errno.h>

int
main(void)
{
    errno = 0;

    return 0;
}
> gcc -c -Wall -Wextra -pedantic essai.c
> objdump -d -M intel essai.o

essai.o:     file format elf32-i386


Disassembly of section .text:

00000000 <main>:
   0: 55                    push   ebp
   1: 89 e5                 mov    ebp,esp
   3: 83 e4 f0              and    esp,0xfffffff0
   6: e8 fc ff ff ff        call   7 <main+0x7>  ; get address of errno in EAX
   b: c7 00 00 00 00 00     mov    DWORD PTR [eax],0x0  ; store 0 in errno
  11: b8 00 00 00 00        mov    eax,0x0
  16: 89 ec                 mov    esp,ebp
  18: 5d                    pop    ebp
  19: c3                    ret

10voto

Jonathan Leffler Points 299946

Sur de nombreux systèmes Unix, compilation avec veille à ce que est thread-safe.

Par exemple :

7voto

Timo Geusch Points 16952

Je pense que la réponse est « ça dépend ». Bibliothèques d’exécution de threads C implémentent généralement errno comme un appel de fonction (macro expansion à une fonction) si vous construisez le code multithread avec les drapeaux correctes.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X