forked from Kieran/snort
feat: schnorr check in wasm
This commit is contained in:
parent
9431b294c6
commit
8d6cdb3868
@ -2,7 +2,15 @@ import "./index.css";
|
|||||||
import "@szhsin/react-menu/dist/index.css";
|
import "@szhsin/react-menu/dist/index.css";
|
||||||
import "./fonts/inter.css";
|
import "./fonts/inter.css";
|
||||||
|
|
||||||
import { compress, expand_filter, flat_merge, get_diff, pow, default as wasmInit } from "@snort/system-wasm";
|
import {
|
||||||
|
compress,
|
||||||
|
expand_filter,
|
||||||
|
flat_merge,
|
||||||
|
get_diff,
|
||||||
|
pow,
|
||||||
|
schnorr_verify,
|
||||||
|
default as wasmInit,
|
||||||
|
} from "@snort/system-wasm";
|
||||||
import WasmPath from "@snort/system-wasm/pkg/system_wasm_bg.wasm";
|
import WasmPath from "@snort/system-wasm/pkg/system_wasm_bg.wasm";
|
||||||
|
|
||||||
import { StrictMode } from "react";
|
import { StrictMode } from "react";
|
||||||
@ -76,6 +84,9 @@ const WasmQueryOptimizer = {
|
|||||||
compress: (all: Array<ReqFilter>) => {
|
compress: (all: Array<ReqFilter>) => {
|
||||||
return compress(all) as Array<ReqFilter>;
|
return compress(all) as Array<ReqFilter>;
|
||||||
},
|
},
|
||||||
|
schnorrVerify: (id, sig, pubkey) => {
|
||||||
|
return schnorr_verify(id, sig, pubkey);
|
||||||
|
},
|
||||||
} as QueryOptimizer;
|
} as QueryOptimizer;
|
||||||
|
|
||||||
export class WasmPowWorker implements PowMiner {
|
export class WasmPowWorker implements PowMiner {
|
||||||
|
19
packages/system-wasm/Cargo.lock
generated
19
packages/system-wasm/Cargo.lock
generated
@ -644,6 +644,24 @@ version = "1.2.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
|
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "secp256k1"
|
||||||
|
version = "0.28.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "2acea373acb8c21ecb5a23741452acd2593ed44ee3d343e72baaa143bc89d0d5"
|
||||||
|
dependencies = [
|
||||||
|
"secp256k1-sys",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "secp256k1-sys"
|
||||||
|
version = "0.9.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "4dd97a086ec737e30053fd5c46f097465d25bb81dd3608825f65298c4c98be83"
|
||||||
|
dependencies = [
|
||||||
|
"cc",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "serde"
|
name = "serde"
|
||||||
version = "1.0.188"
|
version = "1.0.188"
|
||||||
@ -736,6 +754,7 @@ dependencies = [
|
|||||||
"hex",
|
"hex",
|
||||||
"itertools 0.11.0",
|
"itertools 0.11.0",
|
||||||
"rand",
|
"rand",
|
||||||
|
"secp256k1",
|
||||||
"serde",
|
"serde",
|
||||||
"serde-wasm-bindgen",
|
"serde-wasm-bindgen",
|
||||||
"serde_json",
|
"serde_json",
|
||||||
|
@ -12,6 +12,7 @@ argon2 = "0.5.2"
|
|||||||
console_error_panic_hook = "0.1.7"
|
console_error_panic_hook = "0.1.7"
|
||||||
hex = { version = "0.4.3", features = [], default-features = false }
|
hex = { version = "0.4.3", features = [], default-features = false }
|
||||||
itertools = "0.11.0"
|
itertools = "0.11.0"
|
||||||
|
secp256k1 = "0.28.0"
|
||||||
serde = { version = "1.0.188", features = ["derive"], default-features = false }
|
serde = { version = "1.0.188", features = ["derive"], default-features = false }
|
||||||
serde-wasm-bindgen = "0.5.0"
|
serde-wasm-bindgen = "0.5.0"
|
||||||
sha256 = { version = "1.4.0", features = [], default-features = false }
|
sha256 = { version = "1.4.0", features = [], default-features = false }
|
||||||
|
12
packages/system-wasm/pkg/system_wasm.d.ts
vendored
12
packages/system-wasm/pkg/system_wasm.d.ts
vendored
@ -39,6 +39,13 @@ export function pow(val: any, target: any): any;
|
|||||||
* @returns {any}
|
* @returns {any}
|
||||||
*/
|
*/
|
||||||
export function argon2(password: any, salt: any): any;
|
export function argon2(password: any, salt: any): any;
|
||||||
|
/**
|
||||||
|
* @param {any} hash
|
||||||
|
* @param {any} sig
|
||||||
|
* @param {any} pub_key
|
||||||
|
* @returns {boolean}
|
||||||
|
*/
|
||||||
|
export function schnorr_verify(hash: any, sig: any, pub_key: any): boolean;
|
||||||
|
|
||||||
export type InitInput = RequestInfo | URL | Response | BufferSource | WebAssembly.Module;
|
export type InitInput = RequestInfo | URL | Response | BufferSource | WebAssembly.Module;
|
||||||
|
|
||||||
@ -51,6 +58,11 @@ export interface InitOutput {
|
|||||||
readonly compress: (a: number, b: number) => void;
|
readonly compress: (a: number, b: number) => void;
|
||||||
readonly pow: (a: number, b: number, c: number) => void;
|
readonly pow: (a: number, b: number, c: number) => void;
|
||||||
readonly argon2: (a: number, b: number, c: number) => void;
|
readonly argon2: (a: number, b: number, c: number) => void;
|
||||||
|
readonly schnorr_verify: (a: number, b: number, c: number, d: number) => void;
|
||||||
|
readonly rustsecp256k1_v0_9_1_context_create: (a: number) => number;
|
||||||
|
readonly rustsecp256k1_v0_9_1_context_destroy: (a: number) => void;
|
||||||
|
readonly rustsecp256k1_v0_9_1_default_illegal_callback_fn: (a: number, b: number) => void;
|
||||||
|
readonly rustsecp256k1_v0_9_1_default_error_callback_fn: (a: number, b: number) => void;
|
||||||
readonly __wbindgen_malloc: (a: number, b: number) => number;
|
readonly __wbindgen_malloc: (a: number, b: number) => number;
|
||||||
readonly __wbindgen_realloc: (a: number, b: number, c: number, d: number) => number;
|
readonly __wbindgen_realloc: (a: number, b: number, c: number, d: number) => number;
|
||||||
readonly __wbindgen_add_to_stack_pointer: (a: number) => number;
|
readonly __wbindgen_add_to_stack_pointer: (a: number) => number;
|
||||||
|
@ -361,6 +361,28 @@ export function argon2(password, salt) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {any} hash
|
||||||
|
* @param {any} sig
|
||||||
|
* @param {any} pub_key
|
||||||
|
* @returns {boolean}
|
||||||
|
*/
|
||||||
|
export function schnorr_verify(hash, sig, pub_key) {
|
||||||
|
try {
|
||||||
|
const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
|
||||||
|
wasm.schnorr_verify(retptr, addHeapObject(hash), addHeapObject(sig), addHeapObject(pub_key));
|
||||||
|
var r0 = getInt32Memory0()[retptr / 4 + 0];
|
||||||
|
var r1 = getInt32Memory0()[retptr / 4 + 1];
|
||||||
|
var r2 = getInt32Memory0()[retptr / 4 + 2];
|
||||||
|
if (r2) {
|
||||||
|
throw takeObject(r1);
|
||||||
|
}
|
||||||
|
return r0 !== 0;
|
||||||
|
} finally {
|
||||||
|
wasm.__wbindgen_add_to_stack_pointer(16);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
function handleError(f, args) {
|
function handleError(f, args) {
|
||||||
try {
|
try {
|
||||||
return f.apply(this, args);
|
return f.apply(this, args);
|
||||||
|
Binary file not shown.
@ -8,6 +8,11 @@ export function flat_merge(a: number, b: number): void;
|
|||||||
export function compress(a: number, b: number): void;
|
export function compress(a: number, b: number): void;
|
||||||
export function pow(a: number, b: number, c: number): void;
|
export function pow(a: number, b: number, c: number): void;
|
||||||
export function argon2(a: number, b: number, c: number): void;
|
export function argon2(a: number, b: number, c: number): void;
|
||||||
|
export function schnorr_verify(a: number, b: number, c: number, d: number): void;
|
||||||
|
export function rustsecp256k1_v0_9_1_context_create(a: number): number;
|
||||||
|
export function rustsecp256k1_v0_9_1_context_destroy(a: number): void;
|
||||||
|
export function rustsecp256k1_v0_9_1_default_illegal_callback_fn(a: number, b: number): void;
|
||||||
|
export function rustsecp256k1_v0_9_1_default_error_callback_fn(a: number, b: number): void;
|
||||||
export function __wbindgen_malloc(a: number, b: number): number;
|
export function __wbindgen_malloc(a: number, b: number): number;
|
||||||
export function __wbindgen_realloc(a: number, b: number, c: number, d: number): number;
|
export function __wbindgen_realloc(a: number, b: number, c: number, d: number): number;
|
||||||
export function __wbindgen_add_to_stack_pointer(a: number): number;
|
export function __wbindgen_add_to_stack_pointer(a: number): number;
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
extern crate console_error_panic_hook;
|
extern crate console_error_panic_hook;
|
||||||
|
|
||||||
use argon2::{Argon2};
|
use argon2::{Argon2};
|
||||||
|
use secp256k1::{Message, Secp256k1, XOnlyPublicKey};
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
use crate::filter::{FlatReqFilter, ReqFilter};
|
use crate::filter::{FlatReqFilter, ReqFilter};
|
||||||
use wasm_bindgen::prelude::*;
|
use wasm_bindgen::prelude::*;
|
||||||
@ -98,6 +99,20 @@ pub fn argon2(password: JsValue, salt: JsValue) -> Result<JsValue, JsValue> {
|
|||||||
Ok(serde_wasm_bindgen::to_value(&hex::encode(key))?)
|
Ok(serde_wasm_bindgen::to_value(&hex::encode(key))?)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[wasm_bindgen]
|
||||||
|
pub fn schnorr_verify(hash: JsValue, sig: JsValue, pub_key: JsValue) -> Result<bool, JsValue> {
|
||||||
|
console_error_panic_hook::set_once();
|
||||||
|
let msg_hex: String = serde_wasm_bindgen::from_value(hash)?;
|
||||||
|
let sig_hex: String = serde_wasm_bindgen::from_value(sig)?;
|
||||||
|
let pub_key_hex: String = serde_wasm_bindgen::from_value(pub_key)?;
|
||||||
|
|
||||||
|
let secp = Secp256k1::new();
|
||||||
|
let msg = Message::from_digest_slice(&hex::decode(msg_hex).unwrap()).unwrap();
|
||||||
|
let key = XOnlyPublicKey::from_slice(&hex::decode(pub_key_hex).unwrap()).unwrap();
|
||||||
|
let sig = secp256k1::schnorr::Signature::from_slice(&hex::decode(sig_hex).unwrap()).unwrap();
|
||||||
|
Ok(secp.verify_schnorr(&sig, &msg, &key).is_ok())
|
||||||
|
}
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
|
@ -199,9 +199,12 @@ export class NostrSystem extends EventEmitter<NostrSystemEvents> implements Syst
|
|||||||
this.#log("Rejecting invalid event %O", ev);
|
this.#log("Rejecting invalid event %O", ev);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (this.checkSigs && !EventExt.verify(ev)) {
|
if (this.checkSigs) {
|
||||||
this.#log("Invalid sig %O", ev);
|
const id = EventExt.createId(ev);
|
||||||
return;
|
if (!this.#queryOptimizer.schnorrVerify(id, ev.sig, ev.pubkey)) {
|
||||||
|
this.#log("Invalid sig %O", ev);
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const [, v] of this.Queries) {
|
for (const [, v] of this.Queries) {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import { schnorr } from "@noble/curves/secp256k1";
|
||||||
import { ReqFilter } from "../nostr";
|
import { ReqFilter } from "../nostr";
|
||||||
import { expandFilter } from "./request-expander";
|
import { expandFilter } from "./request-expander";
|
||||||
import { flatMerge, mergeSimilar } from "./request-merger";
|
import { flatMerge, mergeSimilar } from "./request-merger";
|
||||||
@ -24,6 +25,7 @@ export interface QueryOptimizer {
|
|||||||
getDiff(prev: Array<ReqFilter>, next: Array<ReqFilter>): Array<FlatReqFilter>;
|
getDiff(prev: Array<ReqFilter>, next: Array<ReqFilter>): Array<FlatReqFilter>;
|
||||||
flatMerge(all: Array<FlatReqFilter>): Array<ReqFilter>;
|
flatMerge(all: Array<FlatReqFilter>): Array<ReqFilter>;
|
||||||
compress(all: Array<ReqFilter>): Array<ReqFilter>;
|
compress(all: Array<ReqFilter>): Array<ReqFilter>;
|
||||||
|
schnorrVerify(hash: string, sig: string, pubkey: string): boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const DefaultQueryOptimizer = {
|
export const DefaultQueryOptimizer = {
|
||||||
@ -43,4 +45,7 @@ export const DefaultQueryOptimizer = {
|
|||||||
compress: (all: Array<ReqFilter>) => {
|
compress: (all: Array<ReqFilter>) => {
|
||||||
return mergeSimilar(all);
|
return mergeSimilar(all);
|
||||||
},
|
},
|
||||||
|
schnorrVerify: (hash, sig, pubkey) => {
|
||||||
|
return schnorr.verify(sig, hash, pubkey);
|
||||||
|
},
|
||||||
} as QueryOptimizer;
|
} as QueryOptimizer;
|
||||||
|
Loading…
Reference in New Issue
Block a user