1#![doc = include_str!("../readme.md")]
2#![cfg(windows)]
3#![no_std]
4#![expect(
5 dead_code,
6 non_snake_case,
7 non_camel_case_types,
8 clippy::upper_case_acronyms
9)]
10
11#[macro_use]
12extern crate alloc;
13
14use alloc::{string::String, vec::Vec};
15use core::ops::Deref;
16use core::ptr::{null, null_mut};
17
18mod bindings;
19use bindings::*;
20
21mod open_options;
22pub use open_options::OpenOptions;
23
24mod key;
25pub use key::Key;
26
27mod transaction;
28pub use transaction::Transaction;
29
30mod value;
31pub use value::Value;
32
33mod data;
34use data::Data;
35
36mod pcwstr;
37use pcwstr::*;
38
39mod key_iterator;
40pub use key_iterator::KeyIterator;
41
42mod value_iterator;
43pub use value_iterator::ValueIterator;
44
45mod r#type;
46pub use r#type::Type;
47
48pub use windows_result::Result;
49use windows_result::*;
50
51pub use windows_strings::HSTRING;
52use windows_strings::{PCWSTR, *};
53
54pub const CLASSES_ROOT: &Key = &Key(HKEY_CLASSES_ROOT);
56
57pub const CURRENT_CONFIG: &Key = &Key(HKEY_CURRENT_CONFIG);
59
60pub const CURRENT_USER: &Key = &Key(HKEY_CURRENT_USER);
62
63pub const LOCAL_MACHINE: &Key = &Key(HKEY_LOCAL_MACHINE);
65
66pub const USERS: &Key = &Key(HKEY_USERS);
68
69fn win32_error(result: u32) -> Result<()> {
70 if result == 0 {
71 Ok(())
72 } else {
73 Err(Error::from_hresult(HRESULT::from_win32(result)))
74 }
75}
76
77fn invalid_data() -> Error {
78 Error::from_hresult(HRESULT::from_win32(ERROR_INVALID_DATA))
79}
80
81fn from_le_bytes(ty: Type, from: &[u8]) -> Result<u64> {
82 match ty {
83 Type::U32 if from.len() == 4 => Ok(u32::from_le_bytes(from.try_into().unwrap()).into()),
84 Type::U64 if from.len() == 8 => Ok(u64::from_le_bytes(from.try_into().unwrap())),
85 _ => Err(invalid_data()),
86 }
87}
88
89fn as_bytes(value: &HSTRING) -> &[u8] {
91 unsafe { core::slice::from_raw_parts(value.as_ptr() as *const _, (value.len() + 1) * 2) }
92}