Cours sur le thread pool en win32
Posted: Mon Jan 26, 2026 4:12 pm
# Le Thread Pool Win32
Salut aujourd’hui on va voir **un composant fondamental de Windows moderne** :
**le Thread Pool Win32**.
Le Thread Pool est partout :
* services Windows
* réseau
* I/O asynchrone
* timers
* tâches système
* composants internes de l’OS
Beaucoup de développeurs utilisent encore `CreateThread` sans comprendre **comment Windows gère réellement les threads**.
Ici on va voir **ce qu’est le Thread Pool**, comment il fonctionne, et comment l’utiliser **proprement en Win32**.
---
# 1) C’est quoi le Thread Pool Win32
Le **Thread Pool Win32** est un **mécanisme de gestion de threads géré par Windows**.
Au lieu de créer un thread à chaque tâche, Windows :
* crée un nombre optimal de threads
* les réutilise
* les planifie intelligemment
* évite la surcharge CPU
Le développeur **ne contrôle plus les threads**, mais **les tâches**.
---
# 2) Pourquoi CreateThread est une mauvaise idée
Créer un thread manuellement :
* coûte cher
* ne scale pas
* surcharge le scheduler
* provoque trop de context switch
* peut planter une application sous charge
`CreateThread` est :
* ancien
* bas niveau
* non scalable
Le Thread Pool est :
* moderne
* plus rapide
* plus sûr
* recommandé par Microsoft
---
# 3) Principe général du Thread Pool
Le fonctionnement est toujours le même :
1. Définir un callback
2. Créer un objet Thread Pool
3. Soumettre la tâche
4. Windows exécute le callback sur un thread du pool
Le développeur ne sait pas :
* quel thread sera utilisé
* quand exactement
---
# 4) Les 4 objets du Thread Pool
Le Thread Pool Win32 repose sur **4 types d’objets** :
* Work → tâche ponctuelle
* Timer → tâche différée ou périodique
* Wait → attente sur un HANDLE
* I/O → I/O asynchrone
---
# 5) Callback : le cœur du Thread Pool
Tout passe par un **callback**.
Un callback :
* est exécuté par Windows
* tourne dans un thread du pool
* doit être rapide
* ne doit pas bloquer longtemps
---
# 6) WORK — exécution d’une tâche simple
Le Work est le plus utilisé.
Il sert pour :
* calcul
* traitement mémoire
* compression
* chiffrement
* envoi réseau
---
## Callback Work
---
## Création et soumission d’un Work
---
# 7) TIMER — exécution différée ou périodique
Le Timer permet d’exécuter du code après un délai ou de manière périodique.
---
## Callback Timer
---
## Création et armement du Timer
---
# 8) WAIT — attente sur un HANDLE
Le Wait permet d’exécuter un callback lorsqu’un objet noyau est signalé.
---
## Callback Wait
---
## Exemple avec Event
---
# 9) I/O — Thread Pool et I/O asynchrone
Le Thread Pool I/O permet de gérer les opérations d’entrée sortie sans bloquer de thread.
---
## Callback I/O
---
## Création du Thread Pool I/O
---
# 10) Synchronisation dans les callbacks
À utiliser :
* InterlockedIncrement
* InterlockedExchange
* CRITICAL_SECTION
* SRWLOCK
À éviter :
* Sleep
* attente bloquante longue
* deadlocks
---
# 11) Fermeture correcte
Chaque objet Thread Pool doit être fermé explicitement.
Sinon des fuites de ressources apparaissent.
---
# À retenir
Le Thread Pool est géré par Windows.
On ne gère plus des threads mais des tâches.
C’est le modèle moderne recommandé en Win32.
Comprendre le Thread Pool, c’est comprendre comment Windows exécute le code en parallèle.
Salut aujourd’hui on va voir **un composant fondamental de Windows moderne** :
**le Thread Pool Win32**.
Le Thread Pool est partout :
* services Windows
* réseau
* I/O asynchrone
* timers
* tâches système
* composants internes de l’OS
Beaucoup de développeurs utilisent encore `CreateThread` sans comprendre **comment Windows gère réellement les threads**.
Ici on va voir **ce qu’est le Thread Pool**, comment il fonctionne, et comment l’utiliser **proprement en Win32**.
---
# 1) C’est quoi le Thread Pool Win32
Le **Thread Pool Win32** est un **mécanisme de gestion de threads géré par Windows**.
Au lieu de créer un thread à chaque tâche, Windows :
* crée un nombre optimal de threads
* les réutilise
* les planifie intelligemment
* évite la surcharge CPU
Le développeur **ne contrôle plus les threads**, mais **les tâches**.
---
# 2) Pourquoi CreateThread est une mauvaise idée
Créer un thread manuellement :
* coûte cher
* ne scale pas
* surcharge le scheduler
* provoque trop de context switch
* peut planter une application sous charge
`CreateThread` est :
* ancien
* bas niveau
* non scalable
Le Thread Pool est :
* moderne
* plus rapide
* plus sûr
* recommandé par Microsoft
---
# 3) Principe général du Thread Pool
Le fonctionnement est toujours le même :
1. Définir un callback
2. Créer un objet Thread Pool
3. Soumettre la tâche
4. Windows exécute le callback sur un thread du pool
Le développeur ne sait pas :
* quel thread sera utilisé
* quand exactement
---
# 4) Les 4 objets du Thread Pool
Le Thread Pool Win32 repose sur **4 types d’objets** :
* Work → tâche ponctuelle
* Timer → tâche différée ou périodique
* Wait → attente sur un HANDLE
* I/O → I/O asynchrone
---
# 5) Callback : le cœur du Thread Pool
Tout passe par un **callback**.
Un callback :
* est exécuté par Windows
* tourne dans un thread du pool
* doit être rapide
* ne doit pas bloquer longtemps
---
# 6) WORK — exécution d’une tâche simple
Le Work est le plus utilisé.
Il sert pour :
* calcul
* traitement mémoire
* compression
* chiffrement
* envoi réseau
---
## Callback Work
Code: Select all
VOID CALLBACK WorkCallback(
PTP_CALLBACK_INSTANCE Instance,
PVOID Context,
PTP_WORK Work
)
{
int value = *(int*)Context;
printf("Work exécuté : %d\n", value);
}
## Création et soumission d’un Work
Code: Select all
int main()
{
int data = 42;
```
PTP_WORK work = CreateThreadpoolWork(
WorkCallback,
&data,
NULL
);
SubmitThreadpoolWork(work);
Sleep(1000);
CloseThreadpoolWork(work);
```
}
# 7) TIMER — exécution différée ou périodique
Le Timer permet d’exécuter du code après un délai ou de manière périodique.
---
## Callback Timer
Code: Select all
VOID CALLBACK TimerCallback(
PTP_CALLBACK_INSTANCE Instance,
PVOID Context,
PTP_TIMER Timer
)
{
printf("Timer déclenché\n");
}
## Création et armement du Timer
Code: Select all
int main()
{
PTP_TIMER timer = CreateThreadpoolTimer(
TimerCallback,
NULL,
NULL
);
```
FILETIME ft;
ULONGLONG delay = (ULONGLONG)-50000000;
ft.dwLowDateTime = (DWORD)delay;
ft.dwHighDateTime = (DWORD)(delay >> 32);
SetThreadpoolTimer(timer, &ft, 0, 0);
Sleep(7000);
CloseThreadpoolTimer(timer);
```
}
# 8) WAIT — attente sur un HANDLE
Le Wait permet d’exécuter un callback lorsqu’un objet noyau est signalé.
---
## Callback Wait
Code: Select all
VOID CALLBACK WaitCallback(
PTP_CALLBACK_INSTANCE Instance,
PVOID Context,
PTP_WAIT Wait,
TP_WAIT_RESULT Result
)
{
printf("Objet signalé\n");
}
## Exemple avec Event
Code: Select all
int main()
{
HANDLE hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
```
PTP_WAIT wait = CreateThreadpoolWait(
WaitCallback,
NULL,
NULL
);
SetThreadpoolWait(wait, hEvent, NULL);
Sleep(2000);
SetEvent(hEvent);
Sleep(1000);
CloseThreadpoolWait(wait);
CloseHandle(hEvent);
```
}
# 9) I/O — Thread Pool et I/O asynchrone
Le Thread Pool I/O permet de gérer les opérations d’entrée sortie sans bloquer de thread.
---
## Callback I/O
Code: Select all
VOID CALLBACK IoCallback(
PTP_CALLBACK_INSTANCE Instance,
PVOID Context,
PVOID Overlapped,
ULONG IoResult,
ULONG_PTR BytesTransferred,
PTP_IO Io
)
{
printf("I/O terminé : %llu bytes\n", BytesTransferred);
}
## Création du Thread Pool I/O
Code: Select all
HANDLE file = CreateFileW(
L"test.txt",
GENERIC_READ,
FILE_SHARE_READ,
NULL,
OPEN_EXISTING,
FILE_FLAG_OVERLAPPED,
NULL
);
PTP_IO io = CreateThreadpoolIo(
file,
IoCallback,
NULL,
NULL
);
# 10) Synchronisation dans les callbacks
À utiliser :
* InterlockedIncrement
* InterlockedExchange
* CRITICAL_SECTION
* SRWLOCK
À éviter :
* Sleep
* attente bloquante longue
* deadlocks
---
# 11) Fermeture correcte
Chaque objet Thread Pool doit être fermé explicitement.
Sinon des fuites de ressources apparaissent.
---
# À retenir
Le Thread Pool est géré par Windows.
On ne gère plus des threads mais des tâches.
C’est le modèle moderne recommandé en Win32.
Comprendre le Thread Pool, c’est comprendre comment Windows exécute le code en parallèle.