subproceso

Específicos de Microsoft

El thread modificador de clase de almacenamiento extendida se usa para declarar una variable local de subproceso. Para el equivalente portátil en C++11 y versiones posteriores, use el especificador thread_local clase de almacenamiento para el código portátil. En Windows thread_local se implementa con __declspec(thread) .

Sintaxis

__declspec(thread)__declspec(thread)

Comentarios

El almacenamiento local para el subproceso (TLS) es el mecanismo por el que cada subproceso de un proceso con varios subproceso asigna almacenamiento para los datos específicos de ese subproceso. En los programas multiproceso estándar, los datos se comparten entre todos los subproceso de un proceso dado, mientras que el almacenamiento local para el subproceso es el mecanismo para asignar datos por subproceso. Para obtener una explicación completa de los subprocesos, vea Multithreading.

Las declaraciones de variables locales de subproceso deben usar la sintaxis de atributo extendida y la palabra clave con la palabra clave thread . Por ejemplo, el código siguiente declara una variable local de subproceso de entero y la inicializa con un valor:

__declspec( thread ) int tls_i = 1;

Al usar variables locales de subprocesos en bibliotecas cargadas dinámicamente, debe tener en cuenta los factores que pueden hacer que una variable local de subproceso no se inicialice correctamente:

  1. Si la variable se inicializa con una llamada de función (incluidos constructores), solo se llamará a esta función para el subproceso que hizo que el archivo binario o DLL se cargara en el proceso y para los subprocesos que se iniciaron después de cargar el archivo binario o DLL. No se llama a las funciones de inicialización para ningún otro subproceso que ya se estaba ejecutando cuando se cargó el archivo DLL. La inicialización dinámica se produce en la llamada a DllMain para DLL_THREAD_ATTACH, pero el archivo DLL nunca obtiene ese mensaje si el archivo DLL no está en el proceso cuando se inicia el subproceso.

  2. Las variables locales de subproceso que se inicializan estáticamente con valores constantes se inicializan normalmente correctamente en todos los subprocesos. Sin embargo, a partir de diciembre de 2017 hay un problema de conformidad conocido en el compilador de Microsoft C++ por el que las variables reciben inicialización dinámica en lugar constexpr de estática.

    Nota: Se espera que ambos problemas se corrigirán en futuras actualizaciones del compilador.

Además, debe observar estas directrices al declarar variables y objetos locales de subprocesos:

  • El atributo solo se puede aplicar a definiciones y declaraciones de datos y clases; no se puede usar en declaraciones o definiciones threadthread de función.

  • Solo puede especificar el atributo thread en elementos de datos con duración de almacenamiento estática. Esto incluye objetos de datos globales (y staticextern ), objetos estáticos locales y miembros de datos estáticos de clases. No se pueden declarar objetos de datos automáticos con el thread atributo .

  • Debe usar el atributo para la declaración y la definición de un objeto local de subproceso, tanto si la declaración como la definición se producen en el mismo archivo o thread en archivos independientes.

  • No se puede usar el thread atributo como modificador de tipo.

  • Dado que se permite la declaración de objetos que usan el atributo thread , estos dos ejemplos son semánticamente equivalentes:

    // declspec_thread_2.cpp
    // compile with: /LD
    __declspec( thread ) class B {
    public:
       int data;
    } BObject;   // BObject declared thread local.
    
    class B2 {
    public:
       int data;
    };
    __declspec( thread ) B2 BObject2;   // BObject2 declared thread local.
    
  • C estándar permite la inicialización de un objeto o variable con una expresión que implica una referencia a sí misma, pero solo para objetos no estáticos. Aunque C++ normalmente permite esta inicialización dinámica de un objeto con una expresión que implica una referencia a sí mismo, este tipo de inicialización no se permite con objetos locales de subproceso. Por ejemplo:

    // declspec_thread_3.cpp
    // compile with: /LD
    #define Thread __declspec( thread )
    int j = j;   // Okay in C++; C error
    Thread int tls_i = sizeof( tls_i );   // Okay in C and C++
    

    Una expresión que incluye el objeto que se inicializa no constituye una referencia a sí misma y sizeof se permite en C y C++.

FIN de Específicos de Microsoft

Vea también

__declspec
Palabras clave
Subproceso local Storage (TLS)