meta: cleanup and use new AppResult type
This commit is contained in:
@@ -0,0 +1,45 @@
|
|||||||
|
use serde::Serialize;
|
||||||
|
//use salvo::http::{StatusCode, StatusError};
|
||||||
|
use salvo::oapi::{self, EndpointOutRegister, ToSchema};
|
||||||
|
use salvo::prelude::*;
|
||||||
|
|
||||||
|
#[derive(Debug, Serialize, ToSchema)]
|
||||||
|
struct ApiError {
|
||||||
|
pub description: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub struct AppError {
|
||||||
|
pub status_code: StatusCode,
|
||||||
|
pub description: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
pub type AppResult<T> = anyhow::Result<T, AppError>;
|
||||||
|
|
||||||
|
#[async_trait]
|
||||||
|
impl Writer for AppError {
|
||||||
|
async fn write(self, _: &mut Request, _depot: &mut Depot, res: &mut Response) {
|
||||||
|
res.status_code = Some(self.status_code);
|
||||||
|
Json(ApiError {
|
||||||
|
description: self.description,
|
||||||
|
})
|
||||||
|
.render(res)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl EndpointOutRegister for AppError {
|
||||||
|
fn register(components: &mut oapi::Components, operation: &mut oapi::Operation) {
|
||||||
|
let errors = vec![
|
||||||
|
StatusError::not_found(),
|
||||||
|
StatusError::request_timeout(),
|
||||||
|
StatusError::internal_server_error(),
|
||||||
|
];
|
||||||
|
for StatusError { code, brief, .. } in errors {
|
||||||
|
operation.responses.insert(
|
||||||
|
code.as_str(),
|
||||||
|
oapi::Response::new(brief)
|
||||||
|
.add_content("application/json", ApiError::to_schema(components)),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -3,13 +3,14 @@ use std::ffi::CString;
|
|||||||
|
|
||||||
use moonlight_common_c_sys::{
|
use moonlight_common_c_sys::{
|
||||||
_SERVER_INFORMATION, _STREAM_CONFIGURATION, COLOR_RANGE_LIMITED, COLORSPACE_REC_601,
|
_SERVER_INFORMATION, _STREAM_CONFIGURATION, COLOR_RANGE_LIMITED, COLORSPACE_REC_601,
|
||||||
CONNECTION_LISTENER_CALLBACKS, ENCFLG_NONE, PCONNECTION_LISTENER_CALLBACKS, SCM_H264,
|
CONNECTION_LISTENER_CALLBACKS, ENCFLG_NONE, SCM_H264, STREAM_CFG_LOCAL, VIDEO_FORMAT_H264,
|
||||||
STREAM_CFG_LOCAL, VIDEO_FORMAT_H264,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
mod certs;
|
mod certs;
|
||||||
|
mod common;
|
||||||
mod pair;
|
mod pair;
|
||||||
|
|
||||||
|
#[allow(unused)]
|
||||||
fn get_server_info() -> _SERVER_INFORMATION {
|
fn get_server_info() -> _SERVER_INFORMATION {
|
||||||
_SERVER_INFORMATION {
|
_SERVER_INFORMATION {
|
||||||
// TODO: these all leak
|
// TODO: these all leak
|
||||||
@@ -23,6 +24,7 @@ fn get_server_info() -> _SERVER_INFORMATION {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(unused)]
|
||||||
fn get_stream_config() -> _STREAM_CONFIGURATION {
|
fn get_stream_config() -> _STREAM_CONFIGURATION {
|
||||||
let mut remote_input_aes_key_u8: [u8; 16] = [0; 16];
|
let mut remote_input_aes_key_u8: [u8; 16] = [0; 16];
|
||||||
let remote_input_aes_iv: [i8; 16] = [0; 16];
|
let remote_input_aes_iv: [i8; 16] = [0; 16];
|
||||||
@@ -52,9 +54,11 @@ fn get_stream_config() -> _STREAM_CONFIGURATION {
|
|||||||
}
|
}
|
||||||
|
|
||||||
unsafe extern "C" {
|
unsafe extern "C" {
|
||||||
fn printf(format: *const i8, ...) -> ();
|
#[allow(unused)]
|
||||||
|
fn printf(format: *const i8, ...);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(unused)]
|
||||||
fn get_listener_callbacks() -> CONNECTION_LISTENER_CALLBACKS {
|
fn get_listener_callbacks() -> CONNECTION_LISTENER_CALLBACKS {
|
||||||
CONNECTION_LISTENER_CALLBACKS {
|
CONNECTION_LISTENER_CALLBACKS {
|
||||||
stageStarting: None,
|
stageStarting: None,
|
||||||
@@ -73,36 +77,38 @@ fn get_listener_callbacks() -> CONNECTION_LISTENER_CALLBACKS {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn barmain() {
|
//fn barmain() {
|
||||||
//let server_info = moonlight_common_c_sys::LiInitializeServerInformation();
|
// //let server_info = moonlight_common_c_sys::LiInitializeServerInformation();
|
||||||
let mut server_info = get_server_info();
|
// let mut server_info = get_server_info();
|
||||||
let mut stream_config = get_stream_config();
|
// let mut stream_config = get_stream_config();
|
||||||
let mut listener_callbacks = get_listener_callbacks();
|
// let mut listener_callbacks = get_listener_callbacks();
|
||||||
let mut ret = 0;
|
// let ret;
|
||||||
unsafe {
|
// unsafe {
|
||||||
ret = moonlight_common_c_sys::LiStartConnection(
|
// ret = moonlight_common_c_sys::LiStartConnection(
|
||||||
&mut server_info,
|
// &mut server_info,
|
||||||
&mut stream_config,
|
// &mut stream_config,
|
||||||
&mut listener_callbacks,
|
// &mut listener_callbacks,
|
||||||
std::ptr::null_mut(),
|
// std::ptr::null_mut(),
|
||||||
std::ptr::null_mut(),
|
// std::ptr::null_mut(),
|
||||||
std::ptr::null_mut(),
|
// std::ptr::null_mut(),
|
||||||
0,
|
// 0,
|
||||||
std::ptr::null_mut(),
|
// std::ptr::null_mut(),
|
||||||
0,
|
// 0,
|
||||||
);
|
// );
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
println!("{ret}");
|
// println!("{ret}");
|
||||||
|
//
|
||||||
loop {}
|
// loop {}
|
||||||
|
//
|
||||||
//println!("Hello, world!");
|
// //println!("Hello, world!");
|
||||||
}
|
//}
|
||||||
|
|
||||||
#[tokio::main]
|
#[tokio::main]
|
||||||
async fn main() {
|
async fn main() {
|
||||||
let mut router = Router::new().push(Router::with_path("pair").post(pair::post_pair));
|
let router = Router::new()
|
||||||
|
.push(Router::with_path("pair").post(pair::post_pair))
|
||||||
|
.push(Router::with_path("apps").get(apps::get_apps));
|
||||||
let doc = OpenApi::new("test api", "0.0.1").merge_router(&router);
|
let doc = OpenApi::new("test api", "0.0.1").merge_router(&router);
|
||||||
let router = router
|
let router = router
|
||||||
.unshift(doc.into_router("/api-doc/openapi.json"))
|
.unshift(doc.into_router("/api-doc/openapi.json"))
|
||||||
|
|||||||
@@ -6,10 +6,13 @@ use rand::Rng;
|
|||||||
use salvo::prelude::*;
|
use salvo::prelude::*;
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
|
use crate::common::{AppError, AppResult};
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, ToSchema)]
|
#[derive(Debug, Deserialize, ToSchema)]
|
||||||
struct PostPairParams {
|
struct PostPairParams {
|
||||||
host: String,
|
host: String,
|
||||||
port: u16,
|
port: u16,
|
||||||
|
#[allow(unused)]
|
||||||
pair_endpoint: Option<String>,
|
pair_endpoint: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -20,6 +23,7 @@ struct PostPairReturn {
|
|||||||
|
|
||||||
#[derive(Debug, Deserialize)]
|
#[derive(Debug, Deserialize)]
|
||||||
struct ServerCertResponse {
|
struct ServerCertResponse {
|
||||||
|
#[allow(unused)]
|
||||||
paired: i32,
|
paired: i32,
|
||||||
plaincert: String,
|
plaincert: String,
|
||||||
}
|
}
|
||||||
@@ -31,6 +35,7 @@ struct ClientChallengeResponse {
|
|||||||
|
|
||||||
#[derive(Debug, Deserialize)]
|
#[derive(Debug, Deserialize)]
|
||||||
struct ServerChallengeResponseResponse {
|
struct ServerChallengeResponseResponse {
|
||||||
|
#[allow(unused)]
|
||||||
paired: i32,
|
paired: i32,
|
||||||
pairingsecret: String,
|
pairingsecret: String,
|
||||||
}
|
}
|
||||||
@@ -146,7 +151,7 @@ fn generate_challenge_response(
|
|||||||
)?;
|
)?;
|
||||||
cipher_ctx.cipher_final(&mut client_challenge_response_data)?;
|
cipher_ctx.cipher_final(&mut client_challenge_response_data)?;
|
||||||
|
|
||||||
let client_challenge_response_data_hex = hex::encode(&client_challenge_response_data);
|
//let client_challenge_response_data_hex = hex::encode(&client_challenge_response_data);
|
||||||
//println!("client_challenge_response_data_hex: {client_challenge_response_data_hex}");
|
//println!("client_challenge_response_data_hex: {client_challenge_response_data_hex}");
|
||||||
|
|
||||||
// Extract ASN.1 signature from certificate
|
// Extract ASN.1 signature from certificate
|
||||||
@@ -161,7 +166,7 @@ fn generate_challenge_response(
|
|||||||
challenge_response.extend_from_slice(signature_data);
|
challenge_response.extend_from_slice(signature_data);
|
||||||
challenge_response.extend_from_slice(client_secret_data);
|
challenge_response.extend_from_slice(client_secret_data);
|
||||||
|
|
||||||
let challenge_response_hex = hex::encode(&challenge_response);
|
//let challenge_response_hex = hex::encode(&challenge_response);
|
||||||
//println!("challenge_response_hex: {challenge_response_hex}");
|
//println!("challenge_response_hex: {challenge_response_hex}");
|
||||||
|
|
||||||
let mut hasher = Sha256::new();
|
let mut hasher = Sha256::new();
|
||||||
@@ -213,7 +218,7 @@ async fn do_challenge(
|
|||||||
cert: &X509,
|
cert: &X509,
|
||||||
) -> Result<ServerPairingSecret> {
|
) -> Result<ServerPairingSecret> {
|
||||||
let aes_key = generate_aes_key(salt, pin);
|
let aes_key = generate_aes_key(salt, pin);
|
||||||
let aes_hex = hex::encode(&aes_key);
|
//let aes_hex = hex::encode(&aes_key);
|
||||||
//println!("aes_hex: {aes_hex}");
|
//println!("aes_hex: {aes_hex}");
|
||||||
|
|
||||||
let client_challenge_response = get_server_challenge(base_url.clone(), &aes_key).await?;
|
let client_challenge_response = get_server_challenge(base_url.clone(), &aes_key).await?;
|
||||||
@@ -323,15 +328,18 @@ fn get_unique_id() -> Result<String> {
|
|||||||
Ok(hex::encode(bytes))
|
Ok(hex::encode(bytes))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[salvo::oapi::endpoint]
|
#[salvo::oapi::endpoint(status_codes(StatusCode::OK, StatusCode::INTERNAL_SERVER_ERROR))]
|
||||||
pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) -> StatusCode {
|
pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) -> AppResult<()> {
|
||||||
let params = body.into_inner();
|
let params = body.into_inner();
|
||||||
|
|
||||||
let unique_id = match get_unique_id() {
|
let unique_id = match get_unique_id() {
|
||||||
Ok(u) => u,
|
Ok(u) => u,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Could not generate unique id: {e}");
|
println!("Could not generate unique id: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -342,7 +350,10 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
let mut client_secret_data = [0u8; 16];
|
let mut client_secret_data = [0u8; 16];
|
||||||
if let Err(e) = openssl::rand::rand_bytes(&mut client_secret_data) {
|
if let Err(e) = openssl::rand::rand_bytes(&mut client_secret_data) {
|
||||||
println!("Could not generate client secret data: {e}");
|
println!("Could not generate client secret data: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get or generate cert / private key
|
// Get or generate cert / private key
|
||||||
@@ -350,7 +361,10 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
Ok(v) => v,
|
Ok(v) => v,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Could not generate certs: {e}");
|
println!("Could not generate certs: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -370,7 +384,10 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
Ok(s) => s,
|
Ok(s) => s,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Could not get server cert: {e}");
|
println!("Could not get server cert: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
//println!("{server_cert:?}");
|
//println!("{server_cert:?}");
|
||||||
@@ -382,7 +399,10 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
Ok(s) => s,
|
Ok(s) => s,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Could not do challenge: {e}");
|
println!("Could not do challenge: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
//println!("{server_pairing_secret:?}");
|
//println!("{server_pairing_secret:?}");
|
||||||
@@ -394,7 +414,10 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
server_cert.cert,
|
server_cert.cert,
|
||||||
) {
|
) {
|
||||||
println!("Could not verify signature: {e}");
|
println!("Could not verify signature: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let client_pairing_secret_response =
|
let client_pairing_secret_response =
|
||||||
@@ -403,18 +426,24 @@ pub async fn post_pair(body: salvo::oapi::extract::JsonBody<PostPairParams>) ->
|
|||||||
Ok(p) => p,
|
Ok(p) => p,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Could not send client pairing secret: {e}");
|
println!("Could not send client pairing secret: {e}");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
if client_pairing_secret_response.paired != 1 {
|
if client_pairing_secret_response.paired != 1 {
|
||||||
println!("Failed to pair with server");
|
println!("Failed to pair with server");
|
||||||
return StatusCode::INTERNAL_SERVER_ERROR;
|
return Err(AppError {
|
||||||
|
status_code: StatusCode::INTERNAL_SERVER_ERROR,
|
||||||
|
description: "Pairing failed".to_string(),
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
let host = ¶ms.host;
|
let host = ¶ms.host;
|
||||||
let port = params.port;
|
let port = params.port;
|
||||||
println!("Paired with server {host}:{port} successfully!");
|
println!("Paired with server {host}:{port} successfully!");
|
||||||
}
|
}
|
||||||
|
|
||||||
StatusCode::OK
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user