1use std::fs;
8use std::io::BufReader;
9use std::net::TcpListener;
10use std::sync::Arc;
11
12use rustls::ServerConfig as TlsServerConfig;
13use rustls::pki_types::CertificateDer;
14
15use crate::auth::RateLimiter;
16use crate::config::ServerConfig;
17use crate::handler::{self, HandlerContext};
18use crate::storage::ProjectStorage;
19
20fn build_tls_config(config: &ServerConfig) -> Result<TlsServerConfig, String> {
22 let cert_file = fs::File::open(&config.tls_cert_path)
23 .map_err(|e| format!("Cannot open TLS cert {}: {}", config.tls_cert_path.display(), e))?;
24 let mut cert_reader = BufReader::new(cert_file);
25 let certs: Vec<CertificateDer> = rustls_pemfile::certs(&mut cert_reader)
26 .collect::<Result<Vec<_>, _>>()
27 .map_err(|e| format!("Cannot parse TLS cert: {}", e))?;
28
29 if certs.is_empty() {
30 return Err("No certificates found in cert file".into());
31 }
32
33 let key_file = fs::File::open(&config.tls_key_path)
34 .map_err(|e| format!("Cannot open TLS key {}: {}", config.tls_key_path.display(), e))?;
35 let mut key_reader = BufReader::new(key_file);
36 let key = rustls_pemfile::private_key(&mut key_reader)
37 .map_err(|e| format!("Cannot parse TLS key: {}", e))?
38 .ok_or_else(|| "No private key found in key file".to_string())?;
39
40 let tls_config = TlsServerConfig::builder()
41 .with_no_client_auth()
42 .with_single_cert(certs, key)
43 .map_err(|e| format!("Cannot build TLS config: {}", e))?;
44
45 Ok(tls_config)
46}
47
48pub fn run(config: ServerConfig) -> Result<(), String> {
53 let psk = pwr_core::crypto::psk_from_hex(&config.auth_token)
54 .map_err(|e| format!("Invalid auth token: {}", e))?;
55
56 let storage = ProjectStorage::new(config.clone())?;
57 let storage = Arc::new(std::sync::RwLock::new(storage));
58 let rate_limiter = Arc::new(std::sync::Mutex::new(RateLimiter::new()));
59
60 let tls_config = Arc::new(build_tls_config(&config)?);
61
62 let bind_addr = config.bind_addr();
63 let listener = TcpListener::bind(&bind_addr)
64 .map_err(|e| format!("Cannot bind to {}: {}", bind_addr, e))?;
65
66 log::info!("pwr-server listening on {} (TLS 1.3)", bind_addr);
67 log::info!("Storage: {}", config.storage_base_path.display());
68
69 for stream_result in listener.incoming() {
71 let stream = stream_result.map_err(|e| format!("Accept error: {}", e))?;
72 let peer_addr = stream
73 .peer_addr()
74 .unwrap_or_else(|_| "unknown".parse().unwrap());
75
76 let psk = psk;
77 let storage = storage.clone();
78 let rate_limiter = rate_limiter.clone();
79 let tls_config = tls_config.clone();
80
81 std::thread::spawn(move || {
83 log::debug!("Connection from {}", peer_addr);
84
85 let conn = match rustls::ServerConnection::new(tls_config.clone()) {
87 Ok(c) => c,
88 Err(e) => {
89 log::error!("Cannot create TLS connection: {}", e);
90 return;
91 }
92 };
93 let mut tls_stream = rustls::StreamOwned::new(conn, stream);
94
95 let ctx = HandlerContext {
96 storage: storage.clone(),
97 rate_limiter: rate_limiter.clone(),
98 psk,
99 peer_addr,
100 connected_at: std::time::Instant::now(),
101 };
102
103 if let Err(e) = handler::handle_connection(&mut tls_stream, ctx) {
104 log::error!("Handler error for {}: {}", peer_addr, e);
105 }
106 });
107 }
108
109 Ok(())
110}