# How to Deploy Windows 11 **23H2** Using a Task Sequence

This bundle is 24H2-first, but every script in it is **build-aware** — you can
re-run the same pipeline against Windows 11 **23H2** (build **22631**) with one
parameter change. Two approaches are documented:

- **Approach A — Quick path** (~15 min): replace 24H2 with 23H2 on the same
  SCCM site. Use this if your org wants 23H2 only.
- **Approach B — Side-by-side** (~25 min): keep 24H2 alive AND add a parallel
  23H2 Task Sequence. Use this if you have a mixed fleet or a slow-adoption
  policy on 24H2.

> **Why still 23H2?**
> Win11 24H2 has some known enterprise blockers (a handful of app compatibility
> regressions, changed WDAC defaults). Many organizations are holding at 23H2
> until they clear internal certifications. 23H2 Enterprise/Edu is supported
> through **November 10, 2026**, so it's safe through at least one more full
> hardware-refresh cycle.

---

## Pre-facts about 23H2 vs 24H2

| Attribute | 23H2 | 24H2 |
|---|---|---|
| Marketing name | Windows 11, version 23H2 | Windows 11, version 24H2 |
| Major build | **10.0.22631** | **10.0.26100** |
| HP CMSL OS query token | `win11` with `-OsVer 22631` | `win11` with `-OsVer 26100` |
| HP driver packs | Published for every model in this bundle's scope (G7 → G11) | Published for every model |
| Win11 Supported-CPU list | Same (G7 10th-gen Intel onward qualifies) | Same |
| LCU / SSU cadence | Monthly, separate MSU catalog entry from 24H2 | Monthly |
| End-of-support (Enterprise) | Nov 10, 2026 | Nov 10, 2027 |
| Sysprep behavior | Identical | Identical |

**The scripts handle both.** What changes per-build is:

1. The **ISO** you supply (23H2 multi-edition Enterprise x64).
2. The **-OSBuild** parameter you pass (`22631`).
3. The **Updates folder** content (23H2 LCUs, not 24H2).
4. The **reference-WIM filename** (avoid overwriting the 24H2 one).

Nothing else.

---

## Approach A — Quick path (single-version site)

Use this if your whole fleet runs 23H2 and you don't need 24H2 on the same
SCCM site.

### A.1 Get the 23H2 ISO + updates
- Download **Windows 11 23H2 Enterprise x64 multi-edition ISO** from your
  Volume Licensing portal (VLSC / M365 Admin Center). File name usually
  contains `SW_DVD9_Win_Pro_11_23H2…ISO` or
  `Win11_23H2_English_x64.iso`. Verify SHA-256 against Microsoft's published
  value.
- Stage at e.g. `D:\Media\Win11_23H2_Enterprise_x64.iso`.
- Download the latest 23H2 **LCU + SSU** from
  <https://catalog.update.microsoft.com> (search: *"Cumulative Update for
  Windows 11 Version 23H2 for x64-based Systems"*). Drop MSU files into
  `\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\Updates\`.

### A.2 Run the wizard with a 23H2 override
The interactive wizard asks for the ISO path; just point it at your 23H2 ISO.
There is one extra override you need to pass to make every stage use build
`22631`:

```powershell
# Same 4-line bootstrap as the normal run:
cd C:\OSD\sccm-win11-hp-imaging\scripts
Set-ExecutionPolicy -Scope Process -ExecutionPolicy Bypass
Get-ChildItem .. -Recurse -File | Unblock-File

# Kick off the wizard normally:
.\Run-Imaging-Wizard.ps1
# ...when it prompts for "Path to Win11 ISO", give it the 23H2 ISO.
# ...when it prompts for "Path to Updates folder", give it the 23H2 Updates folder.
```

Then **immediately after** the wizard's pre-req gate passes and BEFORE it
calls stage 2 (you can hit Ctrl+C and re-run), invoke the scripts
individually in the 23H2 build context:

```powershell
# 23H2-specific runs (build 22631). Each script already accepts -OSBuild.

.\Get-HPDriverPacks.ps1 `
    -SourceRoot '\\sccm01\Sources$\OSD' `
    -OSBuild 22631 `
    -Verbose

.\New-Win11ReferenceImage.ps1 `
    -IsoPath 'D:\Media\Win11_23H2_Enterprise_x64.iso' `
    -WorkRoot '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64' `
    -UpdatesPath '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\Updates' `
    -OSBuild 22631 `
    -Verbose

.\Import-HPDriversToSCCM.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -SourceRoot '\\sccm01\Sources$\OSD' `
    -OSBuild 22631 -DPGroup 'All Production DPs'

.\New-SCCMOsdPackages.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -SourceRoot '\\sccm01\Sources$\OSD' `
    -OSImagePath '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\Captured\Win11-23H2-Ref.wim' `
    -OSBuild 22631 `
    -DPGroup 'All Production DPs'

$cred = Get-Credential CONTOSO\svc-osdjoin
.\New-Win11HPTaskSequence.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -PackageIdsJson '\\sccm01\Sources$\OSD\TaskSequence\PackageIDs.json' `
    -Domain contoso.local `
    -DomainOU 'OU=Workstations,OU=Computers,DC=contoso,DC=local' `
    -JoinAccount $cred.UserName `
    -JoinPassword $cred.GetNetworkCredential().Password `
    -ManagementPoint sccm01.contoso.local `
    -LocalAdminPassword (Read-Host -AsSecureString 'Local Admin pwd') `
    -TaskSequenceName 'Win11-HP-Baseline-23H2-TS'
```

Result: an importable TS named **`Win11-HP-Baseline-23H2-TS`** in your SCCM
console, pointing at a 23H2 reference WIM + 23H2 driver packs. PXE-boot any
HP G7–G11 and it images with 23H2.

---

## Approach B — Side-by-side 23H2 **and** 24H2 on one site

Use this if you want **both** build choices available to technicians: e.g.
the pilot collection still images 24H2 while production collections stay on
23H2, or vice versa.

### B.1 Create a 23H2 folder tree alongside 24H2
```
\\sccm01\Sources$\OSD\
├── OS\
│   ├── Win11-23H2-Enterprise-x64\        ← NEW
│   │   ├── Updates\                       ← 23H2 LCUs
│   │   └── Captured\Win11-23H2-Ref.wim   ← built by New-Win11ReferenceImage.ps1
│   └── Win11-24H2-Enterprise-x64\        ← existing
├── Drivers\
│   └── HP\
│       ├── EliteBook_840_G10\22631\      ← NEW (23H2 driver packs)
│       ├── EliteBook_840_G10\26100\      ← existing (24H2 driver packs)
│       └── ...
└── TaskSequence\
    ├── PackageIDs-22631.json             ← NEW: per-build ID maps
    └── PackageIDs-26100.json
```

`Get-HPDriverPacks.ps1` naturally stores packs under a build-suffixed folder
(`<Model>\<OSBuild>\`), so running it twice with different `-OSBuild` values
populates both 22631/ and 26100/ cleanly without conflict.

### B.2 Build the 23H2 reference WIM (keeps the 24H2 one intact)
```powershell
.\New-Win11ReferenceImage.ps1 `
    -IsoPath 'D:\Media\Win11_23H2_Enterprise_x64.iso' `
    -WorkRoot '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64' `
    -UpdatesPath '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\Updates' `
    -OSBuild 22631
```

### B.3 Acquire and import 23H2 driver packs
```powershell
.\Get-HPDriverPacks.ps1 -SourceRoot '\\sccm01\Sources$\OSD' -OSBuild 22631
.\Import-HPDriversToSCCM.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -SourceRoot '\\sccm01\Sources$\OSD' -OSBuild 22631 `
    -DPGroup 'All Production DPs'
```

SCCM creates **separate Driver Packages** per model per build, because
`Import-HPDriversToSCCM.ps1` names them `<Model> 22631 Drivers` vs.
`<Model> 26100 Drivers`. Same Categories are reused (e.g. the category
`HP_EliteBook_840_G10_22631` vs `HP_EliteBook_840_G10_26100`) — so the
23H2 TS never accidentally pulls 24H2 drivers and vice versa.

### B.4 Create a 23H2 OS Image + build-specific PackageIDs.json
```powershell
.\New-SCCMOsdPackages.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -SourceRoot '\\sccm01\Sources$\OSD' `
    -OSImagePath '\\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\Captured\Win11-23H2-Ref.wim' `
    -OSBuild 22631 `
    -OutputJson '\\sccm01\Sources$\OSD\TaskSequence\PackageIDs-22631.json' `
    -DPGroup 'All Production DPs'
```

The `-OutputJson` override keeps 23H2 IDs separate from the existing 24H2 ones.

### B.5 Build a distinct 23H2 Task Sequence
```powershell
$cred = Get-Credential CONTOSO\svc-osdjoin
.\New-Win11HPTaskSequence.ps1 `
    -SiteCode P01 -SiteServer sccm01.contoso.local `
    -PackageIdsJson '\\sccm01\Sources$\OSD\TaskSequence\PackageIDs-22631.json' `
    -Domain contoso.local `
    -DomainOU 'OU=Workstations,OU=Computers,DC=contoso,DC=local' `
    -JoinAccount $cred.UserName `
    -JoinPassword $cred.GetNetworkCredential().Password `
    -ManagementPoint sccm01.contoso.local `
    -LocalAdminPassword (Read-Host -AsSecureString 'Local Admin pwd') `
    -TaskSequenceName 'Win11-HP-Baseline-23H2-TS'
```

Now your SCCM console shows two sibling TSes:

| TS Name | Build | WIM | Driver Pkgs | Deployed to |
|---|---|---|---|---|
| `Win11-HP-Baseline-TS` | 24H2 (26100) | `Win11-24H2-Ref.wim` | `... 26100 Drivers` | Pilot |
| `Win11-HP-Baseline-23H2-TS` | 23H2 (22631) | `Win11-23H2-Ref.wim` | `... 22631 Drivers` | Production |

### B.6 Deploy each to its collection
SCCM Console → right-click each TS → **Deploy** → point at the appropriate
collection (`OSD - 23H2 Production HP Devices` vs
`OSD - 24H2 Pilot HP Devices`). Make both **Available** to
*ConfigMgr clients, media, and PXE*. The PXE boot menu will show both
choices; the tech picks the right one at F12 time.

---

## Task Sequence anatomy — what's different between 23H2 and 24H2

Short answer: almost nothing. The TSes are structurally identical because
the HP imaging pipeline is build-agnostic. The only differences are
**references**:

| TS step | 24H2 reference | 23H2 reference |
|---|---|---|
| Apply Operating System | `Win11-24H2-Ref` (index 1, build 26100) | `Win11-23H2-Ref` (index 1, build 22631) |
| Apply: HP EliteBook 840 G10 (conditional) | Driver Package `HP EliteBook 840 G10 26100 Drivers` | Driver Package `HP EliteBook 840 G10 22631 Drivers` |
| Install Software Updates | SCCM SUP auto-serves the right LCU based on client OS build | Same |
| HPIA Sweep | `HPImageAssistant.exe` against live HP catalog | Same |
| Run Set-Win11Baseline.ps1 | Unchanged | Unchanged |

Everything else — partitioning, Apply Windows Settings, Setup Windows and
ConfigMgr, domain join, HPIA sweep, baseline finalize — is identical.

---

## How to pick at PXE time

With Approach B, the PXE menu lists both TSes. The imaging tech presses F12
on the HP laptop and sees something like:

```
 +---------------------------------------+
 |  Pick a Task Sequence                 |
 |---------------------------------------|
 |  > Win11-HP-Baseline-TS        (24H2) |
 |    Win11-HP-Baseline-23H2-TS   (23H2) |
 +---------------------------------------+
```

The tech picks the right one for that device's policy. To simplify, you can:

- **Scope by collection**: deploy only one of the two TSes to any given
  collection. Devices in `OSD - 23H2 HP Devices` only see 23H2; devices
  in `OSD - 24H2 Pilot HP Devices` only see 24H2.
- **Scope by Unknown Computers**: deploy 23H2 as *Required* to
  `All Unknown Computers` so any brand-new HP that PXEs automatically
  gets 23H2 unless membership says otherwise.

---

## Validating a 23H2 deploy

Same `docs\validation-checklist.md` applies. Only the **OS build check** differs:

> Section B.1: **Build = Windows 11 23H2 Enterprise (10.0.22631.x)**.
> Verify: `winver`.

Everything else (TPM 2.0, Secure Boot, BitLocker, Device Manager,
HPIA clean, SCCM client assigned, 14 apps installed) is identical.

---

## Migrating from 23H2 to 24H2 later

Three options when you're ready:

| Scenario | Approach | Effort |
|---|---|---|
| Keep existing domain-joined 23H2 PCs, upgrade in-place | Deploy **`TS-03-InPlace-Upgrade`** against the 24H2 OS Image. Keeps apps + user data. | ~45 min per PC, 1-TS-deploy to run |
| Rebuild from scratch | Deploy `TS-02-BareMetal-Deploy` (24H2 version). Wipes and reimages. | ~45 min per PC, run `docs\Simplest-Deployment-Process.md` |
| Keep user data, new OS | Deploy `TS-04-Wipe-And-Load-USMT` (24H2). USMT preserves profiles. | ~60 min per PC |

All three TSes already exist in your SCCM site after running
`New-AllTaskSequences.ps1`.

---

## Common 23H2-specific gotchas

| Symptom | Cause | Fix |
|---|---|---|
| `Get-HPDriverPack -OSVer 22631` returns nothing for a model | HP hasn't published a combined pack for that platform on 23H2 | Script auto-falls back to `Get-SoftpaqList` (per-component) — same as 24H2 fallback |
| WIM capture fails with 0x800f0922 | Wrong LCU — you used a 24H2 LCU against 23H2 media | Download MSU specifically tagged `Version 23H2`; rename only if it literally contains `SSU` (the script detects by filename) |
| `install.wim` index doesn't have "Enterprise" | You grabbed the Home/Pro 23H2 ISO | Grab the **business editions** ISO; Enterprise is Index 3 |
| SCCM SUP offers 24H2 LCUs to a 23H2 PC | SUP syncing both product classifications — that's fine, clients only install matching builds | Leave it; clients self-filter. If you want to hide, deselect "Windows 11, version 24H2 and later" in SUP products. |
| Boot image missing NIC drivers | Same issue as 24H2 | Run `New-HPBootImage.ps1 -Auto -ReloadPxe` — it injects drivers that work for any Win11 build |

---

## Quick reference card

```
+-------------------------------------------------------------+
|  Deploy Win11 23H2 using a Task Sequence                    |
+-------------------------------------------------------------+
|  1. Get 23H2 Enterprise x64 ISO from VLSC, stage at          |
|     D:\Media\Win11_23H2_Enterprise_x64.iso                   |
|                                                             |
|  2. Drop 23H2 LCU/SSU MSUs into                              |
|     \\sccm01\Sources$\OSD\OS\Win11-23H2-Enterprise-x64\     |
|     Updates\                                                |
|                                                             |
|  3. Run:                                                    |
|     New-Win11ReferenceImage.ps1 -OSBuild 22631 ...           |
|     Get-HPDriverPacks.ps1       -OSBuild 22631 ...           |
|     Import-HPDriversToSCCM.ps1  -OSBuild 22631 ...           |
|     New-SCCMOsdPackages.ps1     -OSBuild 22631               |
|                                 -OutputJson ...-22631.json   |
|     New-Win11HPTaskSequence.ps1 -PackageIdsJson ...-22631    |
|                                 -TaskSequenceName            |
|                                    Win11-HP-Baseline-23H2-TS |
|                                                             |
|  4. SCCM Console -> Deploy the 23H2 TS to your collection.   |
|  5. PXE-boot HP -> pick Win11-HP-Baseline-23H2-TS -> done.   |
+-------------------------------------------------------------+
```

---

## Why this bundle supports both builds with no code changes

Every script in `scripts/` accepts a `-OSBuild` parameter (default `26100`).
The downstream logic:

1. **HP CMSL** (`Get-HPDriverPacks.ps1`) calls `Get-HPDriverPack -OSVer $OSBuild`
   and `Get-SoftpaqList -OSVer $OSBuild`. HP publishes driver packs for every
   recent Win11 build; the module picks whichever you ask for.
2. **Driver staging paths** (`<Share>\Drivers\HP\<Model>\<OSBuild>\`) are
   build-suffixed — 22631 and 26100 never collide.
3. **SCCM Driver Package names** are build-suffixed (`… 22631 Drivers` vs
   `… 26100 Drivers`), keeping them distinct in the console.
4. **TS cmdlets** (`New-Win11HPTaskSequence.ps1`) read the build-specific
   `PackageIDs-<OSBuild>.json` so all references in the new TS are correct.
5. **DISM offline servicing** (`New-Win11ReferenceImage.ps1`) injects whatever
   MSUs you drop in `Updates\`. Microsoft's MSU packaging is cumulative and
   self-identifying — DISM applies the right one.

That's why the only meaningful choice you make is **which ISO + which MSU
folder** to point at. Everything else flows from there.
