diff --git a/Cargo.lock b/Cargo.lock index 7e8a115..8063ceb 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -40,6 +40,35 @@ dependencies = [ "generic-array", ] +[[package]] +name = "bumpalo" +version = "3.19.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5dd9dc738b7a8311c7ade152424974d8115f2cdad61e8dab8dac9f2362298510" + +[[package]] +name = "bytecheck" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0caa33a2c0edca0419d15ac723dff03f1956f7978329b1e3b5fdaaaed9d3ca8b" +dependencies = [ + "bytecheck_derive", + "ptr_meta", + "rancor", + "simdutf8", +] + +[[package]] +name = "bytecheck_derive" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89385e82b5d1821d2219e0b095efa2cc1f246cbf99080f3be46a1a85c0d392d9" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "bytes" version = "1.11.0" @@ -156,6 +185,12 @@ dependencies = [ "crypto-common 0.2.0-rc.9", ] +[[package]] +name = "equivalent" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f" + [[package]] name = "generic-array" version = "0.14.7" @@ -166,6 +201,12 @@ dependencies = [ "version_check", ] +[[package]] +name = "hashbrown" +version = "0.16.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "841d1cc9bed7f9236f321df977030373f4a4163ae1a7dbfe1a51a2c1a51d9100" + [[package]] name = "hex" version = "0.4.3" @@ -181,6 +222,26 @@ dependencies = [ "typenum", ] +[[package]] +name = "indexmap" +version = "2.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ad4bb2b565bca0645f4d68c5c9af97fba094e9791da685bf83cb5f3ce74acf2" +dependencies = [ + "equivalent", + "hashbrown", +] + +[[package]] +name = "js-sys" +version = "0.3.83" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "464a3709c7f55f1f721e5389aa6ea4e3bc6aba669353300af094b29ffbdde1d8" +dependencies = [ + "once_cell", + "wasm-bindgen", +] + [[package]] name = "libc" version = "0.2.179" @@ -193,6 +254,26 @@ version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f9fbbcab51052fe104eb5e5d351cf728d30a5be1fe14d9be8a3b097481fb97de" +[[package]] +name = "munge" +version = "0.4.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5e17401f259eba956ca16491461b6e8f72913a0a114e39736ce404410f915a0c" +dependencies = [ + "munge_macro", +] + +[[package]] +name = "munge_macro" +version = "0.4.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4568f25ccbd45ab5d5603dc34318c1ec56b117531781260002151b8530a9f931" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "num-traits" version = "0.2.19" @@ -202,6 +283,12 @@ dependencies = [ "autocfg", ] +[[package]] +name = "once_cell" +version = "1.21.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42f5e15c9953c5e4ccceeb2e7382a716482c34515315f7b03532b8b4e8393d2d" + [[package]] name = "pem-rfc7468" version = "1.0.0" @@ -246,12 +333,34 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "ptr_meta" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b9a0cf95a1196af61d4f1cbdab967179516d9a4a4312af1f31948f8f6224a79" +dependencies = [ + "ptr_meta_derive", +] + +[[package]] +name = "ptr_meta_derive" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7347867d0a7e1208d93b46767be83e2b8f978c3dad35f775ac8d8847551d6fe1" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "pyroxene" version = "0.1.0" dependencies = [ + "rkyv", "rsa", "sha256", + "socket2", ] [[package]] @@ -263,12 +372,60 @@ dependencies = [ "proc-macro2", ] +[[package]] +name = "rancor" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a063ea72381527c2a0561da9c80000ef822bdd7c3241b1cc1b12100e3df081ee" +dependencies = [ + "ptr_meta", +] + [[package]] name = "rand_core" version = "0.10.0-rc-3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f66ee92bc15280519ef199a274fe0cafff4245d31bc39aaa31c011ad56cb1f05" +[[package]] +name = "rend" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cadadef317c2f20755a64d7fdc48f9e7178ee6b0e1f7fce33fa60f1d68a276e6" +dependencies = [ + "bytecheck", +] + +[[package]] +name = "rkyv" +version = "0.8.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b2e88acca7157d83d789836a3987dafc12bc3d88a050e54b8fe9ea4aaa29d20" +dependencies = [ + "bytecheck", + "bytes", + "hashbrown", + "indexmap", + "munge", + "ptr_meta", + "rancor", + "rend", + "rkyv_derive", + "tinyvec", + "uuid", +] + +[[package]] +name = "rkyv_derive" +version = "0.8.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f6dffea3c91fa91a3c0fc8a061b0e27fef25c6304728038a6d6bcb1c58ba9bd" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "rsa" version = "0.10.0-rc.11" @@ -287,6 +444,12 @@ dependencies = [ "zeroize", ] +[[package]] +name = "rustversion" +version = "1.0.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b39cdef0fa800fc44525c84ccb54a029961a8215f9619753635a9c0d2538d46d" + [[package]] name = "serde" version = "1.0.228" @@ -360,6 +523,22 @@ dependencies = [ "rand_core", ] +[[package]] +name = "simdutf8" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3a9fe34e3e7a50316060351f37187a3f546bce95496156754b601a5fa71b76e" + +[[package]] +name = "socket2" +version = "0.5.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e22376abed350d73dd1cd119b57ffccad95b4e585a7cda43e286245ce23c0678" +dependencies = [ + "libc", + "windows-sys", +] + [[package]] name = "spki" version = "0.8.0-rc.4" @@ -381,6 +560,21 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "tinyvec" +version = "1.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa5fdc3bce6191a1dbc8c02d5c8bffcf557bafa17c124c5264a458f1b0613fa" +dependencies = [ + "tinyvec_macros", +] + +[[package]] +name = "tinyvec_macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" + [[package]] name = "tokio" version = "1.49.0" @@ -403,12 +597,140 @@ version = "1.0.22" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9312f7c4f6ff9069b165498234ce8be658059c6728633667c526e27dc2cf1df5" +[[package]] +name = "uuid" +version = "1.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2e054861b4bd027cd373e18e8d8d8e6548085000e41290d95ce0c373a654b4a" +dependencies = [ + "js-sys", + "wasm-bindgen", +] + [[package]] name = "version_check" version = "0.9.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" +[[package]] +name = "wasm-bindgen" +version = "0.2.106" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0d759f433fa64a2d763d1340820e46e111a7a5ab75f993d1852d70b03dbb80fd" +dependencies = [ + "cfg-if", + "once_cell", + "rustversion", + "wasm-bindgen-macro", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-macro" +version = "0.2.106" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "48cb0d2638f8baedbc542ed444afc0644a29166f1595371af4fecf8ce1e7eeb3" +dependencies = [ + "quote", + "wasm-bindgen-macro-support", +] + +[[package]] +name = "wasm-bindgen-macro-support" +version = "0.2.106" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cefb59d5cd5f92d9dcf80e4683949f15ca4b511f4ac0a6e14d4e1ac60c6ecd40" +dependencies = [ + "bumpalo", + "proc-macro2", + "quote", + "syn", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-shared" +version = "0.2.106" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cbc538057e648b67f72a982e708d485b2efa771e1ac05fec311f9f63e5800db4" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "windows-sys" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" +dependencies = [ + "windows-targets", +] + +[[package]] +name = "windows-targets" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973" +dependencies = [ + "windows_aarch64_gnullvm", + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_gnullvm", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" + +[[package]] +name = "windows_i686_gnu" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b" + +[[package]] +name = "windows_i686_gnullvm" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" + +[[package]] +name = "windows_i686_msvc" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" + [[package]] name = "zeroize" version = "1.8.2" diff --git a/Cargo.toml b/Cargo.toml index 0b857c5..b34c9a7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -5,5 +5,7 @@ edition = "2024" [dependencies] rsa = "0.10.0-rc.11" -sha2 = "0.11.0-rc.3" -rand = "0.10.0-rc.6" \ No newline at end of file +sha2 = "0.10.9" +socket2 = "0.5" +rkyv = "0.8.13" +rand = "0.10.0-rc.6" diff --git a/src/block/block.rs b/src/block/block.rs new file mode 100644 index 0000000..f282e9f --- /dev/null +++ b/src/block/block.rs @@ -0,0 +1,11 @@ +use crate::block::transaction::Transaction; + +pub struct BlockHeader { + prev_hash: [u8; 32], + nonce: u64, + merkle_root: [u8; 32] +} +pub struct Block{ + block_header: BlockHeader, + txs: Vec +} \ No newline at end of file diff --git a/src/block/mod.rs b/src/block/mod.rs new file mode 100644 index 0000000..b87e751 --- /dev/null +++ b/src/block/mod.rs @@ -0,0 +1,6 @@ +pub mod block; +pub mod transaction{ + pub struct Transaction{ + + } +} \ No newline at end of file diff --git a/src/block.rs b/src/block/transaction.rs similarity index 100% rename from src/block.rs rename to src/block/transaction.rs diff --git a/src/network.rs b/src/network.rs deleted file mode 100644 index e69de29..0000000 diff --git a/src/network/mod.rs b/src/network/mod.rs new file mode 100644 index 0000000..a8f5fec --- /dev/null +++ b/src/network/mod.rs @@ -0,0 +1,78 @@ +use socket2::{Domain, Protocol, Socket, Type}; +use std::io::Result; +use std::net::{SocketAddr, SocketAddrV4, UdpSocket}; + +mod protocol; + +pub const PORT: u16 = 1200; + +pub struct UdpBroadcast { + socket: UdpSocket, + target: SocketAddr, +} + +impl UdpBroadcast { + pub fn new() -> Result { + Self::with_port(PORT, PORT) + } + + pub fn with_port(send: u16, receive: u16) -> Result { + let socket = Socket::new(Domain::IPV4, Type::DGRAM, Some(Protocol::UDP))?; + socket.set_broadcast(true)?; + socket.set_reuse_address(true)?; + + let addr: SocketAddr = ([0, 0, 0, 0], receive).into(); // 0.0.0.0 != 192.168.x.x.. 미래의 나, 해결해라! + socket.bind(&addr.into())?; + + let socket: UdpSocket = socket.into(); + + Ok(Self { + socket, + target: ([255, 255, 255, 255], send).into(), // 브로드캐스트 주소 바꿀 것 + }) + } + + pub fn send(&self, data: &[u8]) -> Result { + self.socket.send_to(data, self.target) + } + + pub fn recv(&self, buf: &mut [u8]) -> Result<(usize, SocketAddr)> { + self.socket.recv_from(buf) + } + + pub fn is_self(&self, addr: SocketAddr) -> bool { + addr == self.target + } +} + +#[cfg(test)] +mod tests { + use std::thread; + use std::time::Duration; + use crate::network::UdpBroadcast; + + #[test] + fn test_broadcast() { + let node1 = UdpBroadcast::new().unwrap(); + let node2 = UdpBroadcast::new().unwrap(); + let data: [u8; 4] = [0x43, 0x55, 0x54, 0x45]; + let mut receive_buffer = [0u8; 4]; + + let receiver = thread::scope(|scope| { + let result = scope.spawn(|| { + thread::sleep(Duration::from_secs(1)); + node2.recv(&mut receive_buffer).unwrap() + }); + scope.spawn(|| { + node1.send(&data).unwrap(); + }); + result.join().unwrap() + }); + let (receive_count, sender_address) = receiver; + + assert_eq!(receive_count, data.len()); + assert_eq!(receive_buffer, data); + + } + +} \ No newline at end of file diff --git a/src/network/protocol.rs b/src/network/protocol.rs new file mode 100644 index 0000000..d092c38 --- /dev/null +++ b/src/network/protocol.rs @@ -0,0 +1,87 @@ + +use rkyv::{Archive, Deserialize, Serialize}; +use std::net::Ipv4Addr; + +#[derive(Archive, Deserialize, Serialize, Debug, PartialEq, Clone)] +#[rkyv( + compare(PartialEq), + derive(Debug), +)] +pub struct Packet { + pub sender_ip: [u8; 4], +} + +impl Packet { + pub fn new(sender: Ipv4Addr) -> Self { + Self { + sender_ip: sender.octets(), + } + } + + pub fn sender(&self) -> Ipv4Addr { + Ipv4Addr::from(self.sender_ip) + } +} + +impl ArchivedPacket { + pub fn sender(&self) -> Ipv4Addr { + Ipv4Addr::new( + self.sender_ip[0], + self.sender_ip[1], + self.sender_ip[2], + self.sender_ip[3], + ) + } +} + +#[cfg(test)] +mod tests { + use super::*; + use crate::network::UdpBroadcast; + use std::net::Ipv4Addr; + use std::thread; + use std::time::Duration; + + #[test] + fn test_packet_broadcast() { + let node1 = UdpBroadcast::with_port(1201, 1201).unwrap(); + let node2 = UdpBroadcast::with_port(1201, 1201).unwrap(); + + // 보낼 패킷 + let packet = Packet::new(Ipv4Addr::new(192, 168, 0, 100)); + + let serialized = rkyv::to_bytes::(&packet).unwrap(); + + let mut receive_buffer = [0u8; 1024]; // 1KB 버퍼 재사용 + + let receiver = thread::scope(|scope| { + let result = scope.spawn(|| { + thread::sleep(Duration::from_millis(100)); + let (size, addr) = node2.recv(&mut receive_buffer).unwrap(); + (size, addr) + }); + + scope.spawn(|| { + thread::sleep(Duration::from_millis(50)); + node1.send(&serialized).unwrap(); + }); + + result.join().unwrap() + }); + + let (received_size, _sender_addr) = receiver; + + + let valid_data = &receive_buffer[..received_size]; + + + let archived = rkyv::access::(valid_data).unwrap(); + + assert_eq!(archived.sender(), packet.sender()); + assert_eq!(archived.sender(), Ipv4Addr::new(192, 168, 0, 100)); + + // 역직렬화 + let deserialized: Packet = rkyv::deserialize::(archived).unwrap(); + assert_eq!(deserialized, packet); + } +} \ No newline at end of file