- Files, lsited in this gist are generated (except generation script itself)
- Tested only partially
- GCC compiller from Xtensa toolchain is required to make this code work.
- Or instead you can generate static library with the GCC once and link it to the rust code
Last active
December 25, 2019 13:43
-
-
Save pacmancoder/70788fc112b582f71f885e2c3104c0ab to your computer and use it in GitHub Desktop.
Rust-Xtensa atomics support workarround
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// THIS FILE IS GENERATED; PLEASE DO NOT CHANGE! | |
#include <stdint.h> | |
int8_t rust_xtensa__sync_fetch_and_add_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_add_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_fetch_and_sub_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_sub_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_fetch_and_or_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_or_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_fetch_and_and_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_and_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_fetch_and_xor_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_xor_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_fetch_and_nand_1(int8_t* ptr, int8_t arg) { | |
return __sync_fetch_and_nand_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_add_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_add_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_sub_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_sub_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_or_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_or_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_and_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_and_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_xor_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_xor_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_nand_and_fetch_1(int8_t* ptr, int8_t arg) { | |
return __sync_nand_and_fetch_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_lock_test_and_set_1(int8_t* ptr, int8_t arg) { | |
return __sync_lock_test_and_set_1(ptr, arg); | |
} | |
int8_t rust_xtensa__sync_val_compare_and_swap_1(int8_t* ptr, int8_t old, int8_t new) { | |
return __sync_val_compare_and_swap_1(ptr, old, new); | |
} | |
_Bool rust_xtensa__sync_bool_compare_and_swap_1(int8_t* ptr, int8_t old, int8_t new) { | |
return __sync_bool_compare_and_swap_1(ptr, old, new); | |
} | |
int16_t rust_xtensa__sync_fetch_and_add_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_add_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_fetch_and_sub_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_sub_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_fetch_and_or_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_or_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_fetch_and_and_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_and_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_fetch_and_xor_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_xor_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_fetch_and_nand_2(int16_t* ptr, int16_t arg) { | |
return __sync_fetch_and_nand_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_add_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_add_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_sub_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_sub_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_or_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_or_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_and_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_and_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_xor_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_xor_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_nand_and_fetch_2(int16_t* ptr, int16_t arg) { | |
return __sync_nand_and_fetch_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_lock_test_and_set_2(int16_t* ptr, int16_t arg) { | |
return __sync_lock_test_and_set_2(ptr, arg); | |
} | |
int16_t rust_xtensa__sync_val_compare_and_swap_2(int16_t* ptr, int16_t old, int16_t new) { | |
return __sync_val_compare_and_swap_2(ptr, old, new); | |
} | |
_Bool rust_xtensa__sync_bool_compare_and_swap_2(int16_t* ptr, int16_t old, int16_t new) { | |
return __sync_bool_compare_and_swap_2(ptr, old, new); | |
} | |
int32_t rust_xtensa__sync_fetch_and_add_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_add_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_fetch_and_sub_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_sub_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_fetch_and_or_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_or_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_fetch_and_and_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_and_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_fetch_and_xor_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_xor_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_fetch_and_nand_4(int32_t* ptr, int32_t arg) { | |
return __sync_fetch_and_nand_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_add_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_add_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_sub_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_sub_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_or_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_or_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_and_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_and_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_xor_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_xor_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_nand_and_fetch_4(int32_t* ptr, int32_t arg) { | |
return __sync_nand_and_fetch_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_lock_test_and_set_4(int32_t* ptr, int32_t arg) { | |
return __sync_lock_test_and_set_4(ptr, arg); | |
} | |
int32_t rust_xtensa__sync_val_compare_and_swap_4(int32_t* ptr, int32_t old, int32_t new) { | |
return __sync_val_compare_and_swap_4(ptr, old, new); | |
} | |
_Bool rust_xtensa__sync_bool_compare_and_swap_4(int32_t* ptr, int32_t old, int32_t new) { | |
return __sync_bool_compare_and_swap_4(ptr, old, new); | |
} | |
int64_t rust_xtensa__sync_fetch_and_add_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_add_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_fetch_and_sub_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_sub_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_fetch_and_or_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_or_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_fetch_and_and_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_and_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_fetch_and_xor_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_xor_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_fetch_and_nand_8(int64_t* ptr, int64_t arg) { | |
return __sync_fetch_and_nand_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_add_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_add_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_sub_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_sub_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_or_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_or_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_and_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_and_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_xor_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_xor_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_nand_and_fetch_8(int64_t* ptr, int64_t arg) { | |
return __sync_nand_and_fetch_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_lock_test_and_set_8(int64_t* ptr, int64_t arg) { | |
return __sync_lock_test_and_set_8(ptr, arg); | |
} | |
int64_t rust_xtensa__sync_val_compare_and_swap_8(int64_t* ptr, int64_t old, int64_t new) { | |
return __sync_val_compare_and_swap_8(ptr, old, new); | |
} | |
_Bool rust_xtensa__sync_bool_compare_and_swap_8(int64_t* ptr, int64_t old, int64_t new) { | |
return __sync_bool_compare_and_swap_8(ptr, old, new); | |
} | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// THIS FILE IS GENERATED; PLEASE DO NOT CHANGE! | |
#![allow(non_snake_case)] | |
extern "C" { fn rust_xtensa__sync_fetch_and_add_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_add_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_add_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_sub_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_sub_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_sub_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_or_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_or_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_or_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_and_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_and_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_and_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_xor_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_xor_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_xor_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_nand_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_nand_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_fetch_and_nand_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_add_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_add_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_add_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_sub_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_sub_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_sub_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_or_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_or_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_or_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_and_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_and_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_and_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_xor_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_xor_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_xor_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_nand_and_fetch_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_nand_and_fetch_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_nand_and_fetch_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_lock_test_and_set_1(ptr: *mut i8, arg: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_lock_test_and_set_1(ptr: *mut i8, arg: i8) -> i8 { | |
rust_xtensa__sync_lock_test_and_set_1(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_val_compare_and_swap_1(ptr: *mut i8, old: i8, new: i8) -> i8; } | |
#[no_mangle] | |
unsafe fn __sync_val_compare_and_swap_1(ptr: *mut i8, old: i8, new: i8) -> i8 { | |
rust_xtensa__sync_val_compare_and_swap_1(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_bool_compare_and_swap_1(ptr: *mut i8, old: i8, new: i8) -> bool; } | |
#[no_mangle] | |
unsafe fn __sync_bool_compare_and_swap_1(ptr: *mut i8, old: i8, new: i8) -> bool { | |
rust_xtensa__sync_bool_compare_and_swap_1(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_add_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_add_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_add_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_sub_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_sub_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_sub_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_or_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_or_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_or_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_and_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_and_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_and_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_xor_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_xor_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_xor_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_nand_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_nand_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_fetch_and_nand_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_add_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_add_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_add_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_sub_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_sub_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_sub_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_or_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_or_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_or_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_and_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_and_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_and_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_xor_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_xor_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_xor_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_nand_and_fetch_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_nand_and_fetch_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_nand_and_fetch_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_lock_test_and_set_2(ptr: *mut i16, arg: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_lock_test_and_set_2(ptr: *mut i16, arg: i16) -> i16 { | |
rust_xtensa__sync_lock_test_and_set_2(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_val_compare_and_swap_2(ptr: *mut i16, old: i16, new: i16) -> i16; } | |
#[no_mangle] | |
unsafe fn __sync_val_compare_and_swap_2(ptr: *mut i16, old: i16, new: i16) -> i16 { | |
rust_xtensa__sync_val_compare_and_swap_2(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_bool_compare_and_swap_2(ptr: *mut i16, old: i16, new: i16) -> bool; } | |
#[no_mangle] | |
unsafe fn __sync_bool_compare_and_swap_2(ptr: *mut i16, old: i16, new: i16) -> bool { | |
rust_xtensa__sync_bool_compare_and_swap_2(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_add_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_add_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_add_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_sub_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_sub_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_sub_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_or_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_or_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_or_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_and_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_and_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_and_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_xor_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_xor_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_xor_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_nand_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_nand_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_fetch_and_nand_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_add_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_add_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_add_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_sub_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_sub_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_sub_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_or_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_or_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_or_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_and_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_and_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_and_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_xor_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_xor_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_xor_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_nand_and_fetch_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_nand_and_fetch_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_nand_and_fetch_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_lock_test_and_set_4(ptr: *mut i32, arg: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_lock_test_and_set_4(ptr: *mut i32, arg: i32) -> i32 { | |
rust_xtensa__sync_lock_test_and_set_4(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_val_compare_and_swap_4(ptr: *mut i32, old: i32, new: i32) -> i32; } | |
#[no_mangle] | |
unsafe fn __sync_val_compare_and_swap_4(ptr: *mut i32, old: i32, new: i32) -> i32 { | |
rust_xtensa__sync_val_compare_and_swap_4(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_bool_compare_and_swap_4(ptr: *mut i32, old: i32, new: i32) -> bool; } | |
#[no_mangle] | |
unsafe fn __sync_bool_compare_and_swap_4(ptr: *mut i32, old: i32, new: i32) -> bool { | |
rust_xtensa__sync_bool_compare_and_swap_4(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_add_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_add_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_add_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_sub_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_sub_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_sub_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_or_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_or_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_or_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_and_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_and_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_and_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_xor_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_xor_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_xor_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_fetch_and_nand_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_fetch_and_nand_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_fetch_and_nand_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_add_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_add_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_add_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_sub_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_sub_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_sub_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_or_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_or_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_or_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_and_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_and_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_and_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_xor_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_xor_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_xor_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_nand_and_fetch_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_nand_and_fetch_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_nand_and_fetch_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_lock_test_and_set_8(ptr: *mut i64, arg: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_lock_test_and_set_8(ptr: *mut i64, arg: i64) -> i64 { | |
rust_xtensa__sync_lock_test_and_set_8(ptr, arg) | |
} | |
extern "C" { fn rust_xtensa__sync_val_compare_and_swap_8(ptr: *mut i64, old: i64, new: i64) -> i64; } | |
#[no_mangle] | |
unsafe fn __sync_val_compare_and_swap_8(ptr: *mut i64, old: i64, new: i64) -> i64 { | |
rust_xtensa__sync_val_compare_and_swap_8(ptr, old, new) | |
} | |
extern "C" { fn rust_xtensa__sync_bool_compare_and_swap_8(ptr: *mut i64, old: i64, new: i64) -> bool; } | |
#[no_mangle] | |
unsafe fn __sync_bool_compare_and_swap_8(ptr: *mut i64, old: i64, new: i64) -> bool { | |
rust_xtensa__sync_bool_compare_and_swap_8(ptr, old, new) | |
} | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# How to use this script: | |
# 1) `$ python3 generate_atomic.shim.py` | |
# - Generate with default params: | |
# - Generated C file Path: atomic_shim.c | |
# - Generated Rust file Path: atomic_shim.rs | |
# - Proxy functions prefix: rust_xtensa | |
# 2) `$ python3 generate_atomic.shim.py <C file path> <Rust file path>` | |
# 3) `$ python3 generate_atomic.shim.py <C file path> <Rust file path> <Proxy functions prefix>` | |
import sys | |
DEFAULT_C_FILE_PATH = "atomic_shim.c" | |
DEFAULT_RUST_FILE_PATH = "atomic_shim.rs" | |
DEFAULT_FN_PREFIX = "rust_xtensa" | |
HEADER_COMMENT = "// THIS FILE IS GENERATED; PLEASE DO NOT CHANGE!\n" | |
OPERATION_FETCH_FUNCTIONS = [ | |
"__sync_fetch_and_add", | |
"__sync_fetch_and_sub", | |
"__sync_fetch_and_or", | |
"__sync_fetch_and_and", | |
"__sync_fetch_and_xor", | |
"__sync_fetch_and_nand", | |
"__sync_add_and_fetch", | |
"__sync_sub_and_fetch", | |
"__sync_or_and_fetch", | |
"__sync_and_and_fetch", | |
"__sync_xor_and_fetch", | |
"__sync_nand_and_fetch", | |
# Does not hold any operation, but signature is same | |
"__sync_lock_test_and_set", | |
] | |
class SyncType: | |
def __init__(self, size, c_type, rust_type): | |
self.size = size | |
self.c_type = c_type | |
self.rust_type = rust_type | |
SYNC_TYPES = [ | |
SyncType(1, "int8_t", "i8"), | |
SyncType(2, "int16_t", "i16"), | |
SyncType(4, "int32_t", "i32"), | |
SyncType(8, "int64_t", "i64") | |
] | |
class AtomicShimGenerator: | |
def __init__(self, c_file_path, rust_file_path, fn_prefix): | |
self.c_data = "" | |
self.rust_data = "" | |
self.c_file_path = c_file_path | |
self.rust_file_path = rust_file_path | |
self.fn_prefix = fn_prefix | |
def __generate_c_header(self): | |
self.c_data += HEADER_COMMENT + "#include <stdint.h>\n\n" | |
def __generate_rust_header(self): | |
self.rust_data += HEADER_COMMENT + "#![allow(non_snake_case)]\n\n" | |
def __save(self): | |
with open(self.c_file_path, 'w') as f: | |
f.write(self.c_data) | |
with open(self.rust_file_path, 'w') as f: | |
f.write(self.rust_data) | |
def generate(self): | |
self.__generate_c_header() | |
self.__generate_rust_header() | |
for sync_type in SYNC_TYPES: | |
for func in OPERATION_FETCH_FUNCTIONS: | |
self.__c_generate_fetch_operation(func, sync_type.c_type, sync_type.size) | |
self.__rust_generate_fetch_operation(func, sync_type.rust_type, sync_type.size) | |
self.__c_generate_val_compare_and_swap(sync_type.c_type, sync_type.size) | |
self.__rust_generate_val_compare_and_swap(sync_type.rust_type, sync_type.size) | |
self.__c_generate_bool_compare_and_swap(sync_type.c_type, sync_type.size) | |
self.__rust_generate_bool_compare_and_swap(sync_type.rust_type, sync_type.size) | |
self.__save() | |
def __rust_add_extern(self, value): | |
self.rust_data += "extern \"C\" { " + value + " }\n\n" | |
def __rust_add_builtin_surrogate(self, value): | |
self.rust_data += "#[no_mangle]\n" + value + "\n\n" | |
def __rust_generate_val_compare_and_swap(self, sync_type, suffix): | |
FN_NAME = "__sync_val_compare_and_swap" | |
extern_entry = "fn {3}{0}_{2}(ptr: *mut {1}, old: {1}, new: {1}) -> {1};"\ | |
.format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_extern(extern_entry) | |
builtin_surrogate = ("unsafe fn {0}_{2}(ptr: *mut {1}, old: {1}, new: {1}) -> {1} {{\n" | |
+ " {3}{0}_{2}(ptr, old, new)\n" | |
+ "}}").format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_builtin_surrogate(builtin_surrogate) | |
def __rust_generate_bool_compare_and_swap(self, sync_type, suffix): | |
FN_NAME = "__sync_bool_compare_and_swap" | |
extern_entry = "fn {3}{0}_{2}(ptr: *mut {1}, old: {1}, new: {1}) -> bool;"\ | |
.format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_extern(extern_entry) | |
builtin_surrogate = ("unsafe fn {0}_{2}(ptr: *mut {1}, old: {1}, new: {1}) -> bool {{\n" | |
+ " {3}{0}_{2}(ptr, old, new)\n" | |
+ "}}").format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_builtin_surrogate(builtin_surrogate) | |
def __rust_generate_fetch_operation(self, func, sync_type, suffix): | |
extern_entry = "fn {3}{0}_{2}(ptr: *mut {1}, arg: {1}) -> {1};"\ | |
.format(func, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_extern(extern_entry) | |
builtin_surrogate = ("unsafe fn {0}_{2}(ptr: *mut {1}, arg: {1}) -> {1} {{\n" | |
+ " {3}{0}_{2}(ptr, arg)\n" | |
+ "}}").format(func, sync_type, suffix, self.fn_prefix) | |
self.__rust_add_builtin_surrogate(builtin_surrogate) | |
def __c_add_builtin_proxy(self, value): | |
self.c_data += value + "\n\n" | |
def __c_generate_fetch_operation(self, func, sync_type, suffix): | |
builtin_proxy = ("{1} {3}{0}_{2}({1}* ptr, {1} arg) {{\n" | |
+ " return {0}_{2}(ptr, arg);\n" | |
+ "}}").format(func, sync_type, suffix, self.fn_prefix) | |
self.__c_add_builtin_proxy(builtin_proxy) | |
def __c_generate_val_compare_and_swap(self, sync_type, suffix): | |
FN_NAME = "__sync_val_compare_and_swap" | |
builtin_proxy = ("{1} {3}{0}_{2}({1}* ptr, {1} old, {1} new) {{\n" | |
+ " return {0}_{2}(ptr, old, new);\n" | |
+ "}}").format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__c_add_builtin_proxy(builtin_proxy) | |
def __c_generate_bool_compare_and_swap(self, sync_type, suffix): | |
FN_NAME = "__sync_bool_compare_and_swap" | |
builtin_proxy = ("_Bool {3}{0}_{2}({1}* ptr, {1} old, {1} new) {{\n" | |
+ " return {0}_{2}(ptr, old, new);\n" | |
+ "}}").format(FN_NAME, sync_type, suffix, self.fn_prefix) | |
self.__c_add_builtin_proxy(builtin_proxy) | |
def main(): | |
c_file_path = DEFAULT_C_FILE_PATH | |
rust_file_path = DEFAULT_RUST_FILE_PATH | |
fn_prefix = DEFAULT_FN_PREFIX | |
if len(sys.argv) >= 3: | |
c_file_path = sys.argv[1] | |
rust_file_path = sys.argv[2] | |
if len(sys.argv) >= 4: | |
fn_prefix = sys.argv[3] | |
AtomicShimGenerator(c_file_path, rust_file_path, fn_prefix).generate() | |
main() |
@pacmancoder, is the Rust wrapper strictly needed for some reason? I just removed the rust_xtensa
prefix from all the functions, statically compiled it and linked it directly, which is working fine.
@reitermarkus, nope, I just selected arbitrary prefix which looked fine to me. Just make sure that new function names don't create any name collisions.
@reitermarkus I just have tested shim functions without prefixes and rust shim code. Can confirm now that this works correctly 👍 . Thank you, I will try to find time to update the gist code this week.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
UPD: Performed generation script refactoring