Add callback codegen

This commit is contained in:
Mats committed 2022-02-18 17:47:59 +01:00
1 parent 776595cc3a
commit bb068e94de
10 files changed
+236 -11

No files matched your search

Generated
+91 -1
View File
@@ -156,6 +156,25 @@ dependencies = [
"nix",
]
[[package]]
name = "cbindgen"
version = "0.20.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "51e3973b165dc0f435831a9e426de67e894de532754ff7a3f307c03ee5dec7dc"
dependencies = [
"clap 2.34.0",
"heck 0.3.3",
"indexmap",
"log",
"proc-macro2",
"quote",
"serde",
"serde_json",
"syn",
"tempfile",
"toml",
]
[[package]]
name = "cc"
version = "1.0.72"
@@ -241,7 +260,7 @@ version = "3.0.12"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0fd2078197a22f338bd4fbf7d6387eb6f0d6a3c69e6cbc09f5c93e97321fd92a"
dependencies = [
"heck",
"heck 0.4.0",
"proc-macro-error",
"proc-macro2",
"quote",
@@ -578,6 +597,15 @@ dependencies = [
"serde",
]
[[package]]
name = "fastrand"
version = "1.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c3fcf0cee53519c866c09b5de1f6c56ff9d647101f81c1964fa632e148896cdf"
dependencies = [
"instant",
]
[[package]]
name = "fnv"
version = "1.0.7"
@@ -603,6 +631,7 @@ checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b"
name = "generate_headers"
version = "0.1.0"
dependencies = [
"cbindgen",
"mist",
]
@@ -724,6 +753,15 @@ version = "0.11.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e"
[[package]]
name = "heck"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6d621efb26863f0e9924c6ac577e8275e5e6b77455db64ffa6c65c904e9e132c"
dependencies = [
"unicode-segmentation",
]
[[package]]
name = "heck"
version = "0.4.0"
@@ -773,6 +811,12 @@ dependencies = [
"web-sys",
]
[[package]]
name = "itoa"
version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1aab8fc367588b89dcee83ab0fd66b72b50b72fa1904d7095045ace2b0c81c35"
[[package]]
name = "jni-sys"
version = "0.3.0"
@@ -1242,6 +1286,15 @@ version = "0.6.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f497285884f3fcff424ffc933e56d7cbca511def0c9831a7f9b5f6153e3cc89b"
[[package]]
name = "remove_dir_all"
version = "0.5.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7"
dependencies = [
"winapi",
]
[[package]]
name = "ron"
version = "0.7.0"
@@ -1259,6 +1312,12 @@ version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2"
[[package]]
name = "ryu"
version = "1.0.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "73b4b750c782965c211b42f022f59af1fbceabdd026623714f104152f1ec149f"
[[package]]
name = "scoped-tls"
version = "1.0.0"
@@ -1314,6 +1373,17 @@ dependencies = [
"syn",
]
[[package]]
name = "serde_json"
version = "1.0.79"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8e8d9fa5c3b304765ce1fd9c4c8a3de2c8db365a5b91be52f186efc675681d95"
dependencies = [
"itoa",
"ryu",
"serde",
]
[[package]]
name = "shared_library"
version = "0.1.9"
@@ -1404,6 +1474,20 @@ dependencies = [
"unicode-xid",
]
[[package]]
name = "tempfile"
version = "3.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5cdb1ef4eaeeaddc8fbd371e5017057064af0911902ef36b39801f67cc6d79e4"
dependencies = [
"cfg-if 1.0.0",
"fastrand",
"libc",
"redox_syscall",
"remove_dir_all",
"winapi",
]
[[package]]
name = "termcolor"
version = "1.1.2"
@@ -1463,6 +1547,12 @@ version = "0.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4ccbe8381883510b6a2d8f1e32905bddd178c11caef8083086d0c0c9ab0ac281"
[[package]]
name = "unicode-segmentation"
version = "1.9.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7e8820f5d777f6224dc4be3632222971ac30164d4a258d595640799554ebfd99"
[[package]]
name = "unicode-width"
version = "0.1.9"
+8 -2
View File
@@ -9,8 +9,14 @@ after_includes = """
#define MIST_IS_SUCCESS(result) (MIST_RESULT_CODE(result) == MistResult_Success)
#define MIST_IS_ERROR(result) (!MIST_IS_SUCCESS(result))"""
header = """/* Autogenerated file, do not edit by hand. */
#ifndef mist_h
#define mist_h"""
include_guard = "mist_h"
trailer = """
#include "mist_callbacks.h"
#endif /* mist_h */
"""
includes = ["mist_results.h"]
+3
View File
@@ -1,3 +1,4 @@
/* Autogenerated file, do not edit by hand. */
#ifndef mist_h
#define mist_h
@@ -250,4 +251,6 @@ MistResult mist_remote_storage_end_file_write_batch(void);
*/
MistResult mist_utils_get_appid(AppId *app_id);
#include "mist_callbacks.h"
#endif /* mist_h */
+12
View File
@@ -0,0 +1,12 @@
typedef struct MistCallbackDlcInstalled {
AppId app_id;
} MistCallbackDlcInstalled;
typedef struct MistCallbackRemoteStorageLocalFileChange {
} MistCallbackRemoteStorageLocalFileChange;
enum {
MistCallback_DlcInstalled = 1005,
MistCallback_RemoteStorageLocalFileChange = 1333,
};
+1
View File
@@ -12,6 +12,7 @@ serde_derive = "1.0"
steamworks-sys = { path = "../steamworks-sys", optional = true } # Only include steamworks for the binary
[features]
codegen = ["steamworks"]
steamworks = ["steamworks-sys"]
[lib]
+29 -3
View File
@@ -365,6 +365,7 @@ macro_rules! mist_errors {
// This will get LTO'd on normal builds so it should be fine
// Called from generate headers tool
#[allow(dead_code)]
#[cfg(feature = "codegen")]
pub fn generate_header() -> String {
let mut out: String = "enum {\n\tMistResult_Success = 0".into();
@@ -413,12 +414,16 @@ macro_rules! mist_callbacks {
$(
#[derive(Serialize, Deserialize, PartialEq)]
#[repr(C)]
pub struct [<MistCallback $module $callback_ident>] {
pub struct [<MistCallback $callback_ident>] {
$($callback_field_ident: $callback_var_ty),*
}
)*
)*
pub mod callbacks {
pub use super::{$($([<MistCallback $callback_ident>]),*),*};
}
#[derive(Serialize, Deserialize, PartialEq)]
pub struct MistCallback {
pub user: SteamUser,
@@ -429,7 +434,7 @@ macro_rules! mist_callbacks {
#[derive(Serialize, Deserialize, PartialEq)]
pub enum MistCallbacks {
$($(
[<$module $callback_ident>] ([<MistCallback $module $callback_ident>])
[<$module $callback_ident>] ([<MistCallback $callback_ident>])
),*),*
}
@@ -449,7 +454,7 @@ macro_rules! mist_callbacks {
Some(MistCallback {
user,
callback: callback_id,
data: MistCallbacks::[<$module $callback_ident>] ([<MistCallback $module $callback_ident>] {
data: MistCallbacks::[<$module $callback_ident>] ([<MistCallback $callback_ident>] {
$($callback_field_ident: data.$callback_var_ident),*
})
})
@@ -459,6 +464,27 @@ macro_rules! mist_callbacks {
_ => None
}
}
#[allow(dead_code)]
#[cfg(feature = "codegen")]
pub fn get_struct_callback(s: &str) -> u32 {
match s {
$($(stringify!([<MistCallback $callback_ident>]) => steamworks_sys::[<$callback_ident _t_k_iCallback>],)*)*
_ => unreachable!()
}
}
#[allow(dead_code)]
#[cfg(feature = "codegen")]
pub fn get_struct_idents() -> Vec<String> {
let mut out = Vec::new();
$($(
out.push(stringify!([<MistCallback $callback_ident>]).into());
)*)*
out
}
}
}
}
+2 -2
View File
@@ -1,6 +1,6 @@
#[macro_use]
mod codegen;
mod callbacks;
pub mod callbacks;
mod consts;
pub mod result;
mod service;
@@ -8,7 +8,7 @@ mod service;
mod lib_subprocess;
mod types;
pub use callbacks::MistCallbackMsg;
use callbacks::MistCallbackMsg;
use result::{Error, MistError, MistResult, Success};
macro_rules! unwrap_client_result {
+1 -1
View File
@@ -1,4 +1,4 @@
#!/bin/bash
cargo run --bin generate_headers -- "$(dirname $0)/../include/"
cargo run --bin generate_headers -- "$(dirname $0)/../"
(cd $(dirname $0)/../ && cbindgen --config cbindgen.toml --crate mist --output "$(dirname $0)/../include/mist.h")
+2 -1
View File
@@ -4,4 +4,5 @@ version = "0.1.0"
edition = "2021"
[dependencies]
mist = { path = "../../mist" }
cbindgen = "0.20"
mist = { path = "../../mist", features = ["codegen"] }
+87 -1
View File
@@ -1,4 +1,90 @@
fn main() {
let path = std::path::PathBuf::from(std::env::args().nth(1).expect("include path"));
std::fs::write(path.join("mist_results.h"), mist::result::generate_header()).unwrap();
let include_path = path.join("include");
std::fs::write(
include_path.join("mist_results.h"),
mist::result::generate_header(),
)
.unwrap();
// Callback codegen requires macro expansion
std::env::set_var("RUSTC_BOOTSTRAP", "1");
let bindings = cbindgen::Builder::new()
.with_config(cbindgen::Config {
no_includes: true,
language: cbindgen::Language::C,
export: cbindgen::ExportConfig {
include: mist::callbacks::MistCallback::get_struct_idents(),
item_types: vec![cbindgen::ItemType::Structs],
..Default::default()
},
parse: cbindgen::ParseConfig {
expand: cbindgen::ParseExpandConfig {
crates: vec!["mist".into()],
all_features: true,
..Default::default()
},
..Default::default()
},
..Default::default()
})
.with_crate_and_name(&path, "mist")
.generate()
.unwrap();
let mut out = Vec::new();
bindings.write(&mut out);
let header = String::from_utf8_lossy(&out).to_string();
let mut callback_struct_idents = std::collections::HashSet::new();
for i in mist::callbacks::MistCallback::get_struct_idents() {
callback_struct_idents.insert(i);
}
let mut callbacks_out = String::new();
let mut pos = 0;
let mut start = None;
let mut callbacks = Vec::new();
// Filter out headers we do not want
for line in header.lines() {
if line.starts_with("typedef struct ") {
let end = line.find("{").unwrap() - 1;
let ident: &str = &line["typedef struct ".len()..end];
if callback_struct_idents.contains(ident) {
start = Some(pos);
}
}
pos += line.len() + 1;
if line.starts_with("} ") {
let end = line.find(";").unwrap();
let ident = &line[2..end];
if callback_struct_idents.contains(ident) {
let text = header[start.unwrap()..pos].to_string();
let callback_id = mist::callbacks::MistCallback::get_struct_callback(ident);
callbacks.push((ident, callback_id));
callbacks_out.push_str(&text);
callbacks_out.push_str("\n");
start = None;
}
}
}
callbacks_out.push_str("enum {\n");
for (ident, value) in callbacks {
let mut ident = ident.to_string();
ident.insert("MistCallback".len(), '_');
callbacks_out.push_str(&format!(" {} = {},\n", ident, value));
}
callbacks_out.push_str("};\n");
std::fs::write(include_path.join("mist_callbacks.h"), callbacks_out).unwrap();
}