commit
38dd291c43
@ -0,0 +1,2 @@
|
||||
/target
|
||||
*~
|
@ -0,0 +1,603 @@
|
||||
# This file is automatically @generated by Cargo.
|
||||
# It is not intended for manual editing.
|
||||
[[package]]
|
||||
name = "arc-swap"
|
||||
version = "0.4.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4d25d88fd6b8041580a654f9d0c581a047baee2b3efee13275f2fc392fc75034"
|
||||
|
||||
[[package]]
|
||||
name = "async-trait"
|
||||
version = "0.1.40"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "687c230d85c0a52504709705fc8a53e4a692b83a2184f03dae73e38e1e93a783"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.0.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cdb031dd78e28731d87d56cc8ffef4a8f36ca26c38fe2de700543e627f8a464a"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "1.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693"
|
||||
|
||||
[[package]]
|
||||
name = "block-buffer"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4152116fd6e9dadb291ae18fc1ec3575ed6d84c29642d97890f4b4a3417297e4"
|
||||
dependencies = [
|
||||
"generic-array",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bytes"
|
||||
version = "0.5.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0e4cec68f03f32e44924783795810fa50a7035d8c8ebe78580ad7e6c703fba38"
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "0.1.10"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
|
||||
|
||||
[[package]]
|
||||
name = "chrono"
|
||||
version = "0.4.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "942f72db697d8767c22d46a598e01f2d3b475501ea43d0db4f16d90259182d0b"
|
||||
dependencies = [
|
||||
"num-integer",
|
||||
"num-traits",
|
||||
"time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cpuid-bool"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8aebca1129a03dc6dc2b127edd729435bbc4a37e1d5f4d7513165089ceb02634"
|
||||
|
||||
[[package]]
|
||||
name = "cryptohelpers"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8689d930e1c3d1cbd99014c9f7bf1a1197db8e0665ff134517b86c78233ef4fb"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"sha2",
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "digest"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066"
|
||||
dependencies = [
|
||||
"generic-array",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fnv"
|
||||
version = "1.0.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
|
||||
|
||||
[[package]]
|
||||
name = "fuchsia-zircon"
|
||||
version = "0.3.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"fuchsia-zircon-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fuchsia-zircon-sys"
|
||||
version = "0.3.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7"
|
||||
|
||||
[[package]]
|
||||
name = "futures-core"
|
||||
version = "0.3.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "59f5fff90fd5d971f936ad674802482ba441b6f09ba5e15fd8b39145582ca399"
|
||||
|
||||
[[package]]
|
||||
name = "generic-array"
|
||||
version = "0.14.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "501466ecc8a30d1d3b7fc9229b122b2ce8ed6e9d9223f1138d4babb253e51817"
|
||||
dependencies = [
|
||||
"typenum",
|
||||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "getrandom"
|
||||
version = "0.1.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7abc8dd8451921606d809ba32e95b6111925cd2906060d2dcc29c070220503eb"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"wasi 0.9.0+wasi-snapshot-preview1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hermit-abi"
|
||||
version = "0.1.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3deed196b6e7f9e44a2ae8d94225d80302d81208b1bb673fd21fe634645c85a9"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "iovec"
|
||||
version = "0.1.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "kernel32-sys"
|
||||
version = "0.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d"
|
||||
dependencies = [
|
||||
"winapi 0.2.8",
|
||||
"winapi-build",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "lazy_static"
|
||||
version = "1.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.76"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "755456fae044e6fa1ebbbd1b3e902ae19e73097ed4ed87bb79934a867c007bc3"
|
||||
|
||||
[[package]]
|
||||
name = "log"
|
||||
version = "0.4.11"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4fabed175da42fed1fa0746b0ea71f412aa9d35e76e95e59b192c64b9dc2bf8b"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "memchr"
|
||||
version = "2.3.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3728d817d99e5ac407411fa471ff9800a778d88a24685968b36824eaf4bee400"
|
||||
|
||||
[[package]]
|
||||
name = "mio"
|
||||
version = "0.6.22"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fce347092656428bc8eaf6201042cb551b8d67855af7374542a92a0fbfcac430"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"fuchsia-zircon",
|
||||
"fuchsia-zircon-sys",
|
||||
"iovec",
|
||||
"kernel32-sys",
|
||||
"libc",
|
||||
"log",
|
||||
"miow 0.2.1",
|
||||
"net2",
|
||||
"slab",
|
||||
"winapi 0.2.8",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "mio-named-pipes"
|
||||
version = "0.1.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0840c1c50fd55e521b247f949c241c9997709f23bd7f023b9762cd561e935656"
|
||||
dependencies = [
|
||||
"log",
|
||||
"mio",
|
||||
"miow 0.3.5",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "mio-uds"
|
||||
version = "0.6.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "afcb699eb26d4332647cc848492bbc15eafb26f08d0304550d5aa1f612e066f0"
|
||||
dependencies = [
|
||||
"iovec",
|
||||
"libc",
|
||||
"mio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "miow"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8c1f2f3b1cf331de6896aabf6e9d55dca90356cc9960cca7eaaf408a355ae919"
|
||||
dependencies = [
|
||||
"kernel32-sys",
|
||||
"net2",
|
||||
"winapi 0.2.8",
|
||||
"ws2_32-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "miow"
|
||||
version = "0.3.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "07b88fb9795d4d36d62a012dfbf49a8f5cf12751f36d31a9dbe66d528e58979e"
|
||||
dependencies = [
|
||||
"socket2",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "net2"
|
||||
version = "0.2.35"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3ebc3ec692ed7c9a255596c67808dee269f64655d8baf7b4f0638e51ba1d6853"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-integer"
|
||||
version = "0.1.43"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8d59457e662d541ba17869cf51cf177c0b5f0cbf476c66bdc90bf1edac4f875b"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"num-traits",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-traits"
|
||||
version = "0.2.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ac267bcc07f48ee5f8935ab0d24f316fb722d7a1292e2913f0cc196b29ffd611"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num_cpus"
|
||||
version = "1.13.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "05499f3756671c15885fee9034446956fff3f243d6077b91e5767df161f766b3"
|
||||
dependencies = [
|
||||
"hermit-abi",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "260e51e7efe62b592207e9e13a68e43692a7a279171d6ba57abd208bf23645ad"
|
||||
|
||||
[[package]]
|
||||
name = "opaque-debug"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5"
|
||||
|
||||
[[package]]
|
||||
name = "pin-project-lite"
|
||||
version = "0.1.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "282adbf10f2698a7a77f8e983a74b2d18176c19a7fd32a45446139ae7b02b715"
|
||||
|
||||
[[package]]
|
||||
name = "ppv-lite86"
|
||||
version = "0.2.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c36fa947111f5c62a733b652544dd0016a43ce89619538a8ef92724a6f501a20"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.20"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "175c513d55719db99da20232b06cda8bab6b83ec2d04e3283edf0213c37c1a29"
|
||||
dependencies = [
|
||||
"unicode-xid",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "aa563d17ecb180e500da1cfd2b028310ac758de548efdd203e18f283af693f37"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand"
|
||||
version = "0.7.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6a6b1679d49b24bbfe0c803429aa1874472f50d9b363131f0e89fc356b544d03"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
"libc",
|
||||
"rand_chacha",
|
||||
"rand_core",
|
||||
"rand_hc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_chacha"
|
||||
version = "0.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f4c8ed856279c9737206bf725bf36935d8666ead7aa69b52be55af369d193402"
|
||||
dependencies = [
|
||||
"ppv-lite86",
|
||||
"rand_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_core"
|
||||
version = "0.5.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "90bde5296fc891b0cef12a6d03ddccc162ce7b2aff54160af9338f8d40df6d19"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_hc"
|
||||
version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c"
|
||||
dependencies = [
|
||||
"rand_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "redox_syscall"
|
||||
version = "0.1.57"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce"
|
||||
|
||||
[[package]]
|
||||
name = "rustc_version"
|
||||
version = "0.2.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a"
|
||||
dependencies = [
|
||||
"semver",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "semver"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403"
|
||||
dependencies = [
|
||||
"semver-parser",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "semver-parser"
|
||||
version = "0.7.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3"
|
||||
|
||||
[[package]]
|
||||
name = "sha2"
|
||||
version = "0.9.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2933378ddfeda7ea26f48c555bdad8bb446bf8a3d17832dc83e380d444cfb8c1"
|
||||
dependencies = [
|
||||
"block-buffer",
|
||||
"cfg-if",
|
||||
"cpuid-bool",
|
||||
"digest",
|
||||
"opaque-debug",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "signal-hook-registry"
|
||||
version = "1.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a3e12110bc539e657a646068aaf5eb5b63af9d0c1f7b29c97113fad80e15f035"
|
||||
dependencies = [
|
||||
"arc-swap",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "slab"
|
||||
version = "0.4.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c111b5bd5695e56cffe5129854aa230b39c93a305372fdbb2668ca2394eea9f8"
|
||||
|
||||
[[package]]
|
||||
name = "socket2"
|
||||
version = "0.3.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "03088793f677dce356f3ccc2edb1b314ad191ab702a5de3faf49304f7e104918"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"redox_syscall",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "1.0.40"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "963f7d3cc59b59b9325165add223142bbf1df27655d07789f109896d353d8350"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-xid",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "time"
|
||||
version = "0.1.44"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6db9e6914ab8b1ae1c260a4ae7a49b6c5611b40328a735b21862567685e73255"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"wasi 0.10.0+wasi-snapshot-preview1",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio"
|
||||
version = "0.2.22"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5d34ca54d84bf2b5b4d7d31e901a8464f7b60ac145a284fba25ceb801f2ddccd"
|
||||
dependencies = [
|
||||
"bytes",
|
||||
"fnv",
|
||||
"futures-core",
|
||||
"iovec",
|
||||
"lazy_static",
|
||||
"libc",
|
||||
"memchr",
|
||||
"mio",
|
||||
"mio-named-pipes",
|
||||
"mio-uds",
|
||||
"num_cpus",
|
||||
"pin-project-lite",
|
||||
"signal-hook-registry",
|
||||
"slab",
|
||||
"tokio-macros",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-macros"
|
||||
version = "0.2.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f0c3acc6aa564495a0f2e1d59fab677cd7f81a19994cfc7f3ad0e64301560389"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "typenum"
|
||||
version = "1.12.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "373c8a200f9e67a0c95e62a4f52fbf80c23b4381c05a17845531982fa99e6b33"
|
||||
|
||||
[[package]]
|
||||
name = "unicode-xid"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f7fe0bb3479651439c9112f72b6c505038574c9fbb575ed1bf3b797fa39dd564"
|
||||
|
||||
[[package]]
|
||||
name = "uuid"
|
||||
version = "0.8.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9fde2f6a4bea1d6e007c4ad38c6839fa71cbb63b6dbf5b595aa38dc9b1093c11"
|
||||
dependencies = [
|
||||
"rand",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "version_check"
|
||||
version = "0.9.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b5a972e5669d67ba988ce3dc826706fb0a8b01471c088cb0b6110b805cc36aed"
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.9.0+wasi-snapshot-preview1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519"
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.10.0+wasi-snapshot-preview1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f"
|
||||
|
||||
[[package]]
|
||||
name = "winapi"
|
||||
version = "0.2.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a"
|
||||
|
||||
[[package]]
|
||||
name = "winapi"
|
||||
version = "0.3.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419"
|
||||
dependencies = [
|
||||
"winapi-i686-pc-windows-gnu",
|
||||
"winapi-x86_64-pc-windows-gnu",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "winapi-build"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
|
||||
|
||||
[[package]]
|
||||
name = "winapi-i686-pc-windows-gnu"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"
|
||||
|
||||
[[package]]
|
||||
name = "winapi-x86_64-pc-windows-gnu"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
|
||||
|
||||
[[package]]
|
||||
name = "ws2_32-sys"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e"
|
||||
dependencies = [
|
||||
"winapi 0.2.8",
|
||||
"winapi-build",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "yuurei"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"async-trait",
|
||||
"chrono",
|
||||
"cryptohelpers",
|
||||
"once_cell",
|
||||
"rustc_version",
|
||||
"tokio",
|
||||
"uuid",
|
||||
]
|
@ -0,0 +1,18 @@
|
||||
[package]
|
||||
name = "yuurei"
|
||||
version = "0.1.0"
|
||||
authors = ["Avril <flanchan@cumallover.me>"]
|
||||
edition = "2018"
|
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
[dependencies]
|
||||
tokio = {version = "0.2", features=["full"]}
|
||||
async-trait = "0.1.40"
|
||||
chrono = "0.4.15"
|
||||
uuid = {version = "0.8", features=["v4"]}
|
||||
once_cell = "1.4.1"
|
||||
crypto = {package= "cryptohelpers", version = "0.1", features= ["async", "sha256"]}
|
||||
|
||||
[build-dependencies]
|
||||
rustc_version = "0.2"
|
@ -0,0 +1,24 @@
|
||||
|
||||
extern crate rustc_version;
|
||||
use rustc_version::{version, version_meta, Channel};
|
||||
|
||||
fn main() {
|
||||
// Assert we haven't travelled back in time
|
||||
assert!(version().unwrap().major >= 1);
|
||||
|
||||
// Set cfg flags depending on release channel
|
||||
match version_meta().unwrap().channel {
|
||||
Channel::Stable => {
|
||||
println!("cargo:rustc-cfg=stable");
|
||||
}
|
||||
Channel::Beta => {
|
||||
println!("cargo:rustc-cfg=beta");
|
||||
}
|
||||
Channel::Nightly => {
|
||||
println!("cargo:rustc-cfg=nightly");
|
||||
}
|
||||
Channel::Dev => {
|
||||
println!("cargo:rustc-cfg=dev");
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,26 @@
|
||||
|
||||
|
||||
pub unsafe fn refer<'a, T>(src: &'a T) -> &'a [u8]
|
||||
where T: ?Sized
|
||||
{
|
||||
std::slice::from_raw_parts(src as *const T as *const u8, std::mem::size_of_val(src))
|
||||
}
|
||||
|
||||
pub unsafe fn refer_mut<'a, T>(src: &'a mut T) -> &'a mut [u8]
|
||||
where T: ?Sized
|
||||
{
|
||||
std::slice::from_raw_parts_mut(src as *mut T as *mut u8, std::mem::size_of_val(src))
|
||||
}
|
||||
|
||||
pub unsafe fn derefer<'a, T>(src: &'a [u8]) -> &'a T
|
||||
{
|
||||
assert!(src.len() >= std::mem::size_of::<T>());
|
||||
&*(&src[0] as *const u8 as *const T)
|
||||
}
|
||||
|
||||
pub unsafe fn derefer_mut<'a, T>(src: &'a mut [u8]) -> &'a mut T
|
||||
{
|
||||
assert!(src.len() >= std::mem::size_of::<T>());
|
||||
&mut *(&mut src[0] as *mut u8 as *mut T)
|
||||
}
|
||||
|
@ -0,0 +1,40 @@
|
||||
use super::*;
|
||||
|
||||
//TODO: Use tokio Watcher instead, to allow hotreloading?
|
||||
use once_cell::sync::OnceCell;
|
||||
|
||||
static INSTANCE: OnceCell<Config> = OnceCell::new();
|
||||
|
||||
/// Set the global config instance.
|
||||
/// This can only be done once for the duration of the program's runtime
|
||||
pub fn set(conf: Config)
|
||||
{
|
||||
INSTANCE.set(conf).expect("Failed to set global config state: Already set");
|
||||
}
|
||||
|
||||
/// Get the global config instance.
|
||||
/// `set()` must have been previously called or this function panics.
|
||||
pub fn get() -> &'static Config
|
||||
{
|
||||
INSTANCE.get().expect("Global config tried to be accessed before it was set")
|
||||
}
|
||||
|
||||
/// Config for this run
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
|
||||
pub struct Config
|
||||
{
|
||||
/// Name for nanashi
|
||||
pub anon_name: String,
|
||||
}
|
||||
|
||||
impl Default for Config
|
||||
{
|
||||
#[inline]
|
||||
fn default() -> Self
|
||||
{
|
||||
Self {
|
||||
anon_name: "Nanashi",
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,64 @@
|
||||
//! Handles post and user identity.
|
||||
use super::*;
|
||||
use std::{
|
||||
fmt,
|
||||
};
|
||||
use uuid::Uuid;
|
||||
|
||||
/// A globally unique post identifier.
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Hash, Ord, PartialOrd)]
|
||||
pub struct PostID(Uuid);
|
||||
|
||||
impl PostID
|
||||
{
|
||||
/// Generate a new `PostID`.
|
||||
pub fn new() -> Self
|
||||
{
|
||||
Self(Uuid::new_v4())
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for PostID
|
||||
{
|
||||
#[inline] fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result
|
||||
{
|
||||
self.0.fmt(f) //TODO: Change to use kana-hash.
|
||||
}
|
||||
}
|
||||
|
||||
/// A user's data, if set.
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default)]
|
||||
pub struct User
|
||||
{
|
||||
pub name: Option<String>,
|
||||
pub email: Option<String>,
|
||||
pub tripcode: Option<tripcode::Tripcode>,
|
||||
}
|
||||
|
||||
impl User
|
||||
{
|
||||
/// The name string of this instance, or the default name.
|
||||
pub fn name_str(&self) -> &str
|
||||
{
|
||||
self.name.as_ref().map(|x| &x[..]).unwrap_or(&config::get().anon_name[..])
|
||||
}
|
||||
|
||||
/// The email string of this instance, if it is set
|
||||
pub fn email_str(&self) -> Option<&str>
|
||||
{
|
||||
self.email.as_ref().map(|x| &x[..])
|
||||
}
|
||||
|
||||
// No str for tripcode because it's not just a string (yet)
|
||||
|
||||
/// Anon with no detials.
|
||||
pub const fn anon() -> Self
|
||||
{
|
||||
Self {
|
||||
name: None,
|
||||
email: None,
|
||||
tripcode: None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,19 @@
|
||||
#![cfg_attr(nightly, feature(option_unwrap_none))]
|
||||
#![cfg_attr(nightly, feature(never_type))]
|
||||
|
||||
#![allow(dead_code)]
|
||||
|
||||
use async_trait::async_trait;
|
||||
|
||||
mod bytes;
|
||||
mod suspend;
|
||||
|
||||
mod config;
|
||||
mod tripcode;
|
||||
mod identity;
|
||||
mod post;
|
||||
mod state;
|
||||
|
||||
fn main() {
|
||||
println!("Hello, world!");
|
||||
}
|
@ -0,0 +1,64 @@
|
||||
//! Structure for updating posts in-place
|
||||
use super::*;
|
||||
use std::{
|
||||
fmt,
|
||||
hash::{
|
||||
Hash,Hasher,
|
||||
},
|
||||
};
|
||||
use chrono::prelude::*;
|
||||
|
||||
/// Represents all valid timestamps for a post.
|
||||
///
|
||||
/// Usually in UTC, pls keep it in Utc...
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct PostTimestamp<T = Utc>
|
||||
where T: TimeZone,
|
||||
{
|
||||
pub opened: DateTime<T>,
|
||||
pub closed: Option<DateTime<T>>,
|
||||
pub last_edit: DateTime<T>,
|
||||
}
|
||||
|
||||
impl<Tz: TimeZone> Hash for PostTimestamp<Tz> {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
self.opened.hash(state);
|
||||
self.closed.hash(state);
|
||||
self.last_edit.hash(state);
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> fmt::Display for PostTimestamp<T>
|
||||
where T: TimeZone,
|
||||
T::Offset: fmt::Display
|
||||
{
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result
|
||||
{
|
||||
writeln!(f, " Opened - {}", self.opened)?;
|
||||
writeln!(f, " Edited - {}", self.last_edit)?;
|
||||
write!(f, " Closed - ")?;
|
||||
if let Some(closed) = &self.closed {
|
||||
writeln!(f, "{}", closed)?;
|
||||
} else {
|
||||
writeln!(f, "Stil open")?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
|
||||
/// A closed and finished post. The inverse of `Imouto`.
|
||||
pub struct Static
|
||||
{
|
||||
id: identity::PostID,
|
||||
|
||||
user: identity::User,
|
||||
|
||||
title: Option<String>,
|
||||
karada: String,
|
||||
|
||||
timestamp: PostTimestamp,
|
||||
|
||||
/// Hash of the rest of the post data. . . .
|
||||
hash: crypto::sha256::Sha256Hash,
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
//! Container state for all posts
|
||||
use super::*;
|
||||
|
||||
/// Contains all posts in an instance, open or closed.
|
||||
pub struct Oneesan
|
||||
{
|
||||
|
||||
}
|
@ -0,0 +1,91 @@
|
||||
//! Handles updating posts
|
||||
use super::*;
|
||||
use tokio::{
|
||||
sync::{
|
||||
RwLock,
|
||||
watch,
|
||||
},
|
||||
};
|
||||
|
||||
const MAX_SINGLE_DELTA_SIZE: usize = 16;
|
||||
|
||||
/// Information about the delta to be applied in `Delta`.
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub enum DeltaKind
|
||||
{
|
||||
/// Append to the end of body. Equivilant to `Insert` with a location at `karada.scape.len()` (the end of the buffer). Might be removed idk
|
||||
Append{
|
||||
span: [char; MAX_SINGLE_DELTA_SIZE],
|
||||
span_len: u8,
|
||||
},
|
||||
/// Insert `span_len` chars from `span` into body starting ahead of `location` and moving ahead
|
||||
Insert{
|
||||
span: [char; MAX_SINGLE_DELTA_SIZE],
|
||||
span_len: u8,
|
||||
},
|
||||
/// Remove `span_len` chars ahead of `location`. (INCLUSIVE)
|
||||
RemoveAhead{
|
||||
span_len: usize,
|
||||
},
|
||||
/// Remove `span_len` chars behind this `location`. (EXCLUSIVE)
|
||||
RemoveBehind{
|
||||
span_len: usize,
|
||||
},
|
||||
/// Remove char at `location`
|
||||
RemoveSingle,
|
||||
/// Remove entire post body
|
||||
Clear,
|
||||
}
|
||||
|
||||
/// A delta to apply to `Karada`.
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct Delta
|
||||
{
|
||||
/// Location to insert into. This is the INclusive range of: 0..=(karada.scape.len()).
|
||||
///
|
||||
/// Insertions off the end of the buffer are to be appened instead.
|
||||
location: usize,
|
||||
/// The kind of delta t oinsert
|
||||
kind: DeltaKind,
|
||||
}
|
||||
|
||||
/// Static assertion: `MAX_SINGLE_DELTA_SIZE` can fit into `u8`.
|
||||
const _: [u8;(MAX_SINGLE_DELTA_SIZE < (!0u8 as usize)) as usize] = [0];
|
||||
|
||||
/// Contains post deltas and an intermediate representation of the still-open post body.
|
||||
/// Created and modified with `Kokoro` worker instances.
|
||||
///
|
||||
/// This should not be created by itself, instead `Kokoro` should create instances of this, so that it can retain the `watch::Sender` and other such things.
|
||||
#[derive(Debug)]
|
||||
pub struct Karada
|
||||
{
|
||||
/// The post body so far as a vector of `char`s.
|
||||
scape: RwLock<Vec<char>>,
|
||||
/// All applied deltas so far. Last applied one is at the end.
|
||||
deltas: RwLock<Vec<Delta>>,
|
||||
|
||||
/// the latest render of the whole body string. Updated whenever a delta(s) are applied atomically.
|
||||
current_body: watch::Receiver<String>,
|
||||
}
|
||||
|
||||
/// Handles working on `Karada` instances.
|
||||
pub struct Kokoro
|
||||
{
|
||||
...//TODO
|
||||
}
|
||||
|
||||
/// An open, as yet unfinied post
|
||||
#[derive(Debug)]
|
||||
pub struct Imouto
|
||||
{
|
||||
id: identity::PostID,
|
||||
|
||||
user: identity::User,
|
||||
|
||||
title: Option<String>,
|
||||
karada: Karada,
|
||||
|
||||
/// Hash of the current post data
|
||||
hash: crypto::sha256::Sha256Hash,
|
||||
timestamp: post::PostTimestamp, //Note that `closed` should always be `None` in `Imouto`. We use this for post lifetimes and such
|
||||
}
|
@ -0,0 +1,15 @@
|
||||
//! Structures for handling global and local post state.
|
||||
use super::*;
|
||||
|
||||
mod global;
|
||||
pub use global::*;
|
||||
|
||||
mod local;
|
||||
pub use local::*;
|
||||
|
||||
/// An open or closed post
|
||||
pub enum Post
|
||||
{
|
||||
Open(Imouto),
|
||||
Closed(post::Static),
|
||||
}
|
@ -0,0 +1,304 @@
|
||||
//! Handles suspending and reloading posts
|
||||
use super::*;
|
||||
use std::{
|
||||
marker::{
|
||||
PhantomData,
|
||||
Unpin,
|
||||
},
|
||||
io,
|
||||
collections::HashMap,
|
||||
ops::Range,
|
||||
borrow::{
|
||||
Cow,
|
||||
Borrow,
|
||||
},
|
||||
error,
|
||||
fmt,
|
||||
};
|
||||
use tokio::{
|
||||
prelude::*,
|
||||
io::{
|
||||
AsyncRead,
|
||||
AsyncWrite,
|
||||
},
|
||||
};
|
||||
|
||||
/// Represents an opaque bytes stream of serialised data to insert into `SuspendStream`.
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct SuspendObject
|
||||
{
|
||||
data: Vec<u8>,
|
||||
data_instances: HashMap<Cow<'static, str>, Range<usize>>,
|
||||
}
|
||||
|
||||
fn calc_len<T,I,U>(from: I) -> U
|
||||
where I: IntoIterator<Item = T>,
|
||||
T: Borrow<Range<U>>,
|
||||
U: std::cmp::Ord + Default + Copy,
|
||||
{
|
||||
let mut max = Default::default();
|
||||
|
||||
for i in from.into_iter()
|
||||
{
|
||||
let i = i.borrow().end;
|
||||
if i > max {
|
||||
max = i
|
||||
}
|
||||
}
|
||||
max
|
||||
}
|
||||
|
||||
impl SuspendObject
|
||||
{
|
||||
/// Create a new empty `SuspendObject`.
|
||||
#[inline] pub fn new() -> Self
|
||||
{
|
||||
Self{data: Vec::new(), data_instances: HashMap::new()}
|
||||
}
|
||||
|
||||
/// Are the internal mappings of this object valid?
|
||||
pub fn validate(&self) -> bool
|
||||
{
|
||||
let len = self.data.len();
|
||||
for (_, range) in self.data_instances.iter() {
|
||||
if range.start + range.end > len {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
true
|
||||
}
|
||||
|
||||
/// Insert bytes directly with this name
|
||||
pub fn insert_bytes(&mut self, name: impl Into<Cow<'static, str>>, bytes: impl AsRef<[u8]>)
|
||||
{
|
||||
let bytes= bytes.as_ref();
|
||||
let start = self.data.len();
|
||||
self.data.extend_from_slice(bytes);
|
||||
let end = self.data.len();
|
||||
|
||||
self.data_instances.insert(name.into(), start..end).unwrap_none();
|
||||
}
|
||||
|
||||
/// Insert a value's bytes directly with this name
|
||||
pub unsafe fn insert_value<T,U>(&mut self, name: U, value: &T)
|
||||
where T: ?Sized,
|
||||
U: Into<Cow<'static, str>>
|
||||
{
|
||||
self.insert_bytes(name, bytes::refer(value))
|
||||
}
|
||||
|
||||
/// Try to get the bytes specified by name
|
||||
pub fn get_bytes(&self, name: impl Borrow<str>) -> Option<&[u8]>
|
||||
{
|
||||
if let Some(range) = self.data_instances.get(name.borrow()) {
|
||||
Some(&self.data[range.clone()])
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
/// Try to get the value spcified by name
|
||||
///
|
||||
/// # Panics
|
||||
/// If `T` cannot fit into the size of the range
|
||||
pub unsafe fn get_value<T>(&self, name: impl Borrow<str>) -> Option<&T>
|
||||
{
|
||||
self.get_bytes(name).map(|x| bytes::derefer(x))
|
||||
}
|
||||
|
||||
/// Try to get the value specified by name. Will return `None` if `T` cannot fit in the returned bytes.
|
||||
pub unsafe fn try_get_value<T>(&self, name: impl Borrow<str>) -> Option<&T>
|
||||
{
|
||||
if let Some(bytes) = self.get_bytes(name) {
|
||||
if bytes.len() >= std::mem::size_of::<T>() {
|
||||
Some(bytes::derefer(bytes))
|
||||
} else {
|
||||
#[cfg(debug_assertions)] eprintln!("Warning! Likely data corruption as {} (size {}) cannot fit into {} bytes",std::any::type_name::<T>(), std::mem::size_of::<T>(), bytes.len());
|
||||
None
|
||||
}
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
/// Consume into the data
|
||||
#[deprecated = "Invalid ABI"] fn into_bytes(self) -> Box<[u8]>
|
||||
{
|
||||
let mut output = Vec::new(); //TOOO: Get cap
|
||||
|
||||
debug_assert!(self.validate(), "passing invalid object to serialise");
|
||||
|
||||
unsafe {
|
||||
output.extend_from_slice(bytes::refer(&self.data_instances.len()));
|
||||
for (name, Range{start, end}) in self.data_instances.into_iter() {
|
||||
let name = name.as_bytes();
|
||||
|
||||
output.extend_from_slice(bytes::refer(&name.len()));
|
||||
output.extend_from_slice(name);
|
||||
|
||||
output.extend_from_slice(bytes::refer(&start));
|
||||
output.extend_from_slice(bytes::refer(&end));
|
||||
}
|
||||
}
|
||||
|
||||
output.extend(self.data);
|
||||
output.into_boxed_slice()
|
||||
}
|
||||
|
||||
/// Read an object from a stream
|
||||
pub async fn from_stream<T>(input: &mut T) -> io::Result<Self>
|
||||
where T: AsyncRead + Unpin + ?Sized
|
||||
{
|
||||
let mut ext_buf = Vec::new();
|
||||
|
||||
macro_rules! bin {
|
||||
(usize) => {
|
||||
{
|
||||
use std::convert::TryFrom;
|
||||
let value: u64 = input.read_u64().await?;
|
||||
usize::try_from(value).map_err(|_| io::Error::new(io::ErrorKind::InvalidData, "u64 cannot fit in usize"))?
|
||||
}
|
||||
};
|
||||
($size:expr) => {
|
||||
{
|
||||
let sz = $size;
|
||||
ext_buf.resize(sz, 0);
|
||||
assert_eq!(input.read_exact(&mut ext_buf[..sz]).await?, ext_buf.len());
|
||||
&ext_buf[..sz]
|
||||
}
|
||||
}
|
||||
}
|
||||
let entries = bin!(usize);
|
||||
|
||||
let mut instances = HashMap::with_capacity(entries);
|
||||
|
||||
for _i in 0..entries
|
||||
{
|
||||
let name_len = bin!(usize);
|
||||
|
||||
let name_bytes = bin!(name_len);
|
||||
let name_str = std::str::from_utf8(name_bytes).map_err(|_| io::Error::new(io::ErrorKind::InvalidData,"item name was corrupted"))?;
|
||||
|
||||
let start = bin!(usize);
|
||||
let end = bin!(usize);
|
||||
|
||||
instances.insert(Cow::Owned(name_str.to_owned()), start..end);
|
||||
}
|
||||
|
||||
let expected_len = bin!(usize);
|
||||
if expected_len != calc_len(instances.iter().map(|(_, v)| v))
|
||||
{
|
||||
return Err(io::Error::new(io::ErrorKind::InvalidData, "expected and read sizes differ"));
|
||||
}
|
||||
|
||||
let mut data = vec![0; expected_len];
|
||||
assert_eq!(input.read_exact(&mut data[..]).await?, expected_len);
|
||||
|
||||
Ok(Self {
|
||||
data,
|
||||
data_instances: instances,
|
||||
})
|
||||
}
|
||||
|
||||
/// Write this instance into an async stream
|
||||
pub async fn into_stream<T>(&self, output: &mut T) -> io::Result<usize>
|
||||
where T: AsyncWrite + Unpin + ?Sized
|
||||
{
|
||||
debug_assert!(self.validate(), "passing invalid object to serialise");
|
||||
|
||||
let mut written=0usize;
|
||||
macro_rules! bin {
|
||||
($bytes:expr) => {
|
||||
{
|
||||
let bytes = $bytes;
|
||||
output.write_all(bytes).await?;
|
||||
written+=bytes.len();
|
||||
}
|
||||
};
|
||||
(usize $value:expr) => {
|
||||
{
|
||||
use std::convert::TryInto;
|
||||
let val: u64 = $value.try_into().map_err(|_| io::Error::new(io::ErrorKind::InvalidData, "size cannot fit in u64"))?;
|
||||
output.write_u64(val).await?;
|
||||
written += std::mem::size_of::<u64>();
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
unsafe {
|
||||
bin!(usize self.data_instances.len());
|
||||
for (name, &Range{start, end}) in self.data_instances.iter() {
|
||||
let name = name.as_bytes();
|
||||
|
||||
bin!(usize name.len());
|
||||
bin!(name);
|
||||
|
||||
bin!(usize start);
|
||||
bin!(usize end);
|
||||
}
|
||||
}
|
||||
|
||||
bin!(usize self.data.len()); //for additional checks
|
||||
bin!(&self.data);
|
||||
Ok(written)
|
||||
}
|
||||
}
|
||||
|
||||
/// A suspend stream represents a stream of objects of _the same type_. Can be any number of them, but they all must be for the same type.
|
||||
#[async_trait]
|
||||
pub trait SuspendStream
|
||||
{
|
||||
/// Write an object into the opaque stream.
|
||||
async fn set_object(&mut self, obj: SuspendObject) -> Result<(), SuspendError>;
|
||||
/// Read an object from the opaque stream.
|
||||
async fn get_object(&mut self) -> Result<Option<SuspendObject>, SuspendError>;
|
||||
}
|
||||
|
||||
/// An error that occoured in a suspend operation
|
||||
#[derive(Debug)]
|
||||
#[non_exhaustive]
|
||||
pub enum SuspendError {
|
||||
BadObject,
|
||||
Corruption,
|
||||
IO(io::Error),
|
||||
|
||||
Unknown,
|
||||
}
|
||||
impl error::Error for SuspendError
|
||||
{
|
||||
fn source(&self) -> Option<&(dyn error::Error + 'static)> {
|
||||
Some(match &self {
|
||||
Self::IO(io) => io,
|
||||
_ => return None,
|
||||
})
|
||||
}
|
||||
}
|
||||
impl fmt::Display for SuspendError
|
||||
{
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result
|
||||
{
|
||||
match self {
|
||||
Self::BadObject => write!(f, "unexpected object in stream"),
|
||||
Self::Corruption => write!(f, "data stream corruption"),
|
||||
Self::IO(_) => write!(f, "i/o error"),
|
||||
_ => write!(f, "unknown error"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// A suspendable type, that can save and reload its data atomically
|
||||
#[async_trait]
|
||||
pub trait Suspendable: Sized
|
||||
{
|
||||
async fn suspend<S: SuspendStream + ?Sized>(self, into: &mut S) -> Result<(), SuspendError>;
|
||||
async fn load<S: SuspendStream + ?Sized>(from: &mut S) -> Result<Self, SuspendError>;
|
||||
}
|
||||
|
||||
/*
|
||||
pub struct SuspenceState<T>
|
||||
where T: Suspendable
|
||||
{
|
||||
|
||||
_phantom: PhantomData<T>,
|
||||
}*/
|
@ -0,0 +1,12 @@
|
||||
//! Tripcode. TODO: Use kana-hash
|
||||
use super::*;
|
||||
|
||||
|
||||
///TODO: A kana-hash tripcode
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Hash, Ord, PartialOrd)]
|
||||
pub enum Tripcode
|
||||
{
|
||||
Secure(i32),
|
||||
Normal(i32),
|
||||
Special(&'static str),
|
||||
}
|
Loading…
Reference in new issue