Fix/preserve deleted printer (#16500)

* fix(windows): preserve manually deleted printers

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(windows): distinguish printer detection failures

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(windows): skip printer detection when disabled

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(flutter): load printer status asynchronously

Signed-off-by: fufesou <linlong1266@gmail.com>

* refactor(flutter): remove printer status mounted checks

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(msi): preserve deleted printers in direct upgrades

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(windows): preserve deleted printers in silent EXE installs

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(windows): skip printer installation when detection fails

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(installer): default printer off when detection fails

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(printer): limit checked enumeration to presence queries

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(installer): allow cancellation during printer detection

Inline MSI update command construction without changing its arguments.

Signed-off-by: fufesou <linlong1266@gmail.com>

* fix(flutter): time out installer printer detection

Signed-off-by: fufesou <linlong1266@gmail.com>

* chore

Signed-off-by: fufesou <linlong1266@gmail.com>

* test(windows): cover multilingual install app names

Signed-off-by: fufesou <linlong1266@gmail.com>

---------

Signed-off-by: fufesou <linlong1266@gmail.com>
This commit is contained in:
fufesou authored and GitHub committed 2026-10-10 00:21:17 +08:00
1 parent 0bc2473ffe
commit 001b0e9617
6 files changed
+186 -22

No files matched your search

+44 -15
View File
@@ -5,7 +5,7 @@ use winapi::{
shared::{
minwindef::{BOOL, DWORD, FALSE, LPBYTE, LPDWORD},
ntdef::HANDLE,
winerror::ERROR_INVALID_PRINTER_NAME,
winerror::{ERROR_INSUFFICIENT_BUFFER, ERROR_INVALID_PRINTER_NAME},
},
um::winspool::{
AddPrinterW, ClosePrinter, DeletePrinter, EnumPrintersW, OpenPrinterW, SetPrinterW,
@@ -42,20 +42,49 @@ fn enum_local_printer(
#[inline]
pub fn is_printer_added(name: &PCWSTR) -> ResultType<bool> {
let r = common_enum(
"EnumPrintersW",
enum_local_printer,
1,
|info: &PRINTER_INFO_1W| {
if is_name_equal(name, info.pName) {
Some(true)
} else {
None
}
},
|| None,
)?;
Ok(r.unwrap_or(false))
const PRINTER_INFO_LEVEL: DWORD = 1;
let mut needed = 0;
let mut returned = 0;
if enum_local_printer(
PRINTER_INFO_LEVEL,
null_mut(),
0,
&mut needed,
&mut returned,
) == FALSE
{
let error = io::Error::last_os_error();
if error.raw_os_error() != Some(ERROR_INSUFFICIENT_BUFFER as i32) || needed == 0 {
bail!("Failed to query EnumPrintersW buffer size: {error}");
}
}
if needed == 0 {
return Ok(false);
}
let mut buffer = vec![0u8; needed as usize];
if enum_local_printer(
PRINTER_INFO_LEVEL,
buffer.as_mut_ptr(),
needed,
&mut needed,
&mut returned,
) == FALSE
{
bail!(
"Failed to call EnumPrintersW, error: {}",
io::Error::last_os_error()
);
}
let printers = buffer.as_ptr() as *const PRINTER_INFO_1W;
for index in 0..returned {
let printer = unsafe { &*printers.add(index as usize) };
if is_name_equal(name, printer.pName) {
return Ok(true);
}
}
Ok(false)
}
// Only return the first matched printer