@@ -525,6 +525,7 @@ NTSTATUS SarCreateEndpoint(
525
525
NTSTATUS status = STATUS_SUCCESS;
526
526
PKSDEVICE ksDevice = KsGetDeviceForDeviceObject (device);
527
527
BOOLEAN deviceNameAllocated = FALSE , deviceIdAllocated = FALSE ;
528
+ RTL_OSVERSIONINFOW versionInfo = {};
528
529
SarEndpoint *endpoint;
529
530
530
531
if (request->type != SAR_ENDPOINT_TYPE_RECORDING &&
@@ -679,18 +680,43 @@ NTSTATUS SarCreateEndpoint(
679
680
request->name [MAX_ENDPOINT_NAME_LENGTH] = ' \0 ' ;
680
681
request->id [MAX_ENDPOINT_NAME_LENGTH] = ' \0 ' ;
681
682
RtlInitUnicodeString (&endpoint->deviceName , request->name );
682
- RtlInitUnicodeString (&endpoint-> deviceId , request-> id );
683
- status = SarStringDuplicate ( &endpoint->deviceName , &endpoint->deviceName );
683
+ status = SarStringDuplicate (
684
+ &endpoint->deviceName , &endpoint->deviceName );
684
685
685
686
if (!NT_SUCCESS (status)) {
686
687
goto err_out;
687
688
}
688
689
689
690
deviceNameAllocated = TRUE ;
690
- status = SarStringDuplicate (&endpoint->deviceId , &endpoint->deviceId );
691
691
692
- if (!NT_SUCCESS (status)) {
693
- goto err_out;
692
+ // Windows 10 introduces a 'format cache' which at this time appears to
693
+ // not fully invalidate itself when KSEVENT_PINCAPS_FORMATCHANGE is
694
+ // sent. Work around this by encoding information about the sample rate,
695
+ // channel count and sample resolution into the endpoint ID. This means
696
+ // that WASAPI endpoints won't be stable across changes to these
697
+ // parameters on Windows 10 and e.g. applications that store them as
698
+ // configuration may lose track of them, but that seems better than "it
699
+ // fully stops working until you reinstall the driver".
700
+ RtlGetVersion (&versionInfo);
701
+
702
+ if (versionInfo.dwMajorVersion >= 10 ) {
703
+ DECLARE_UNICODE_STRING_SIZE (deviceIdBuffer, 256 );
704
+
705
+ RtlUnicodeStringPrintf (&deviceIdBuffer,
706
+ L" %ws_%d_%d_%d" , request->id , request->channelCount ,
707
+ controlContext->sampleRate , controlContext->sampleSize );
708
+ status = SarStringDuplicate (&endpoint->deviceId , &deviceIdBuffer);
709
+
710
+ if (!NT_SUCCESS (status)) {
711
+ goto err_out;
712
+ }
713
+ } else {
714
+ RtlInitUnicodeString (&endpoint->deviceId , request->id );
715
+ status = SarStringDuplicate (&endpoint->deviceId , &endpoint->deviceId );
716
+
717
+ if (!NT_SUCCESS (status)) {
718
+ goto err_out;
719
+ }
694
720
}
695
721
696
722
deviceIdAllocated = TRUE ;
0 commit comments