-# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>\r
+# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>\r
# SPDX-License-Identifier: GPL-3.0-or-later\r
\r
# Logs\r
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
-Chris Duncan <chris@zoso.dev> (zoso.dev)
+Chris Duncan <chris@codecow.com> (codecow.com)
Ben Green <ben@latenightsketches.com> (numtel.github.io)
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
Update dependencies.
-
-
## v5.1.8
### Notable Changes
Update dependencies.
-
-
## v5.1.7
### Notable Changes
Eliminate self-references to allow esbuild to generate anonymous classes.
-
-
## v5.1.6
### Notable Changes
Update optional `puppeteer` dependency.
-
-
## v5.1.5
### Notable Changes
Update dev dependencies.
-
-
## v5.1.4
### Notable Changes
Adjust types for API support and fix optional options parameter types.
-
-
## v5.1.3
### Notable Changes
Fix types for optional properties of NanoPowOptions object.
-
-
## v5.1.2
### Notable Changes
Add missing license headers for REUSE compliance.
-
-
## v5.1.1
### Notable Changes
Fix test page CDN URL.
-
-
## v5.1.0
### Notable Changes
Consolidated npm scripts.
-
-
## v5.0.5
### Notable Changes
Reverted reduced WASM iteration count since it seems to be a Firefox issue.
-
-
## v5.0.4
### Notable Changes
Reduce WASM module hash iterations to check results more often.
-
-
## v5.0.3
### Notable Changes
Bump version due to npm publishing issue.
-
-
## v5.0.2
### Notable Changes
Remove additional logger statements from production builds.
-
-
## v5.0.1
### Notable Changes
Update test webpage import URLs.
-
-
## v5.0.0
### Notable Changes
Reorganized project structure.
-
-
## v4.1.7
### Notable Changes
Update dependencies.
-
-
## v4.1.6
### Notable Changes
Update server test script.
-
-
## v4.1.5
### Notable Changes
Tweak error messaging.
-
-
## v4.1.4
### Notable Changes
Adjust log timestamp formatting.
-
-
## v4.1.3
### Notable Changes
Fix fast exit failing to clean up resources by handling SIGINT and SIGTERM.
-
-
## v4.1.2
### Notable Changes
Load configuration from file (`$HOME/.nano-pow/config`) and use it to set
execution options if relevant environment variables are not present.
-
-
## v4.1.1
### Notable Changes
Improve reset process on errors and timeouts.
-
-
## v4.1.0
### Notable Changes
Prevent unnecessary favicon load in puppeteer source and in test webpage.
-
-
## v4.0.11
### Notable Changes
Improve formatting of environment variable documentation.
-
-
## v4.0.10
### Notable Changes
Remove deprecated functions from type definition file.
-
-
## v4.0.9
### Notable Changes
Fix missing crypto module used to compute source hash for CSP.
-
-
## v4.0.8
### Notable Changes
#### Control server config with environment variables
The server now recognizes the following envars:
-* NANO_POW_DEBUG
-* NANO_POW_EFFORT
-* NANO_POW_PORT (replaces `PORT`)
+
+- NANO_POW_DEBUG
+- NANO_POW_EFFORT
+- NANO_POW_PORT (replaces `PORT`)
### Other Changes
Update package configuration files.
-
-
## v4.0.7
### Notable Changes
Update README and manual for clarity, completeness, and accuracy.
-
-
## v4.0.6
### Notable Changes
Fix file paths in server test.
-
-
## v4.0.5
### Notable Changes
Use `npm prepare` script to ensure build artifacts are up-to-date before
installing locally or publishing.
-
-
## v4.0.4
### Notable Changes
Fix CLI file paths for older versions of Node that do not have
`import.meta.dirname` available.
-
-
## v4.0.3
### Notable Changes
Log IP address instead of static 'http://localhost' value from testing.
-
-
## v4.0.2
### Notable Changes
Fix server file paths for older versions of Node that do not have
`import.meta.dirname` available.
-
-
## v4.0.1
### Notable Changes
Update `nano-pow` command to call shell script which subsequently calls
`server.js` if called with `nano-pow --server` or `cli.js` as usual if not.
-
-
## v4.0.0
### Notable Changes
Fix Typescript types.
-
-
## v3.2.2
### Notable Changes
Fix getter type.
-
-
## v3.2.1
### Notable Changes
Implement hash-based Content Security Policy (CSP) in CLI puppeteer page.
-
-
## v3.2.0
### Notable Changes
Expand documentation.
-
-
## v3.1.4
### Notable Changes
PoW modules are filed by API instead of by file type. File paths have been
updated accordingly.
-
-
## v3.1.3
### Notable Changes
Update README license section.
-
-
## v3.1.2
### Notable Changes
Added file of blockhashes used in `test.html`.
-
-
## v3.1.1
### Notable Changes
Fixed minor issues with CLI inline help and manual.
-
-
## v3.1.0
### Notable Changes
Updated dependencies.
-
-
## v3.0.1
### Notable Changes
Implemented `esbuild` legal comment retention.
-
-
## v3.0.0
### Notable Changes
Add benchmark results table.
-
-
## v2.0.0
### Notable Changes
object parameter.
```javascript
-NanoPow.search(blockhash, { threshold: 'fffffc00', effort: 16, debug: true })
+NanoPow.search(blockhash, { threshold: "fffffc00", effort: 16, debug: true });
```
**This is a breaking change.** Integrations already using the optional threshold
Now, the same approach is used but implemented with vectors instead of scalars,
i.e. `vec2<u32>` instead of `u32`. This has several benefits:
-* Integer pairs of high and low bits are held in memory together, improving
-legibility as well as alignment with the original C reference implementation.
-* Arithmetic and bitwise operations are executed on both high and low bits in
-parallel using one statement instead of three.
-* File size is reduced by over 58%.
+
+- Integer pairs of high and low bits are held in memory together, improving
+ legibility as well as alignment with the original C reference implementation.
+- Arithmetic and bitwise operations are executed on both high and low bits in
+ parallel using one statement instead of three.
+- File size is reduced by over 58%.
### Other Changes
Fix a bug with the truncated average benchmark calculation.
-
-
## v1.2.4
### Notable Changes
Increase WebGPU dispatch size.
-
-
## v1.2.3
### Notable Changes
Remove usage of package `imports` property and use regular relative paths.
-
-
## v1.2.2
### Notable Changes
Compile to `dist/` instead of `build/`.
-
-
## v1.2.1
### Notable Changes
Rename bundle output file.
-
-
## v1.2.0
### Notable Changes
Provide additional context about test progress on the testing webpage.
-
-
## v1.1.0
### Notable Changes
Fix repo cloning so that `git clone https://zoso.dev/nano-pow.git` works as
expected (thanks to u/the_azarian for helping track this down).
-
-
## v1.0.0
### Notable Changes
achieve massively increased proof-of-work speed for supported devices directly
in the browser!
-* Faster than any other JavaScript implementation of Nano proof-of-work.
-* Avoids graphical stuttering seen in WebGL implementations.
-* Works entirely offline and locally on the device.
-* Zero external dependencies. Run it in any environment that supports WebGPU
-compute shaders.
-* Released under the GPLv3 license to promote user freedom and FOSS principles.
+- Faster than any other JavaScript implementation of Nano proof-of-work.
+- Avoids graphical stuttering seen in WebGL implementations.
+- Works entirely offline and locally on the device.
+- Zero external dependencies. Run it in any environment that supports WebGPU
+ compute shaders.
+- Released under the GPLv3 license to promote user freedom and FOSS principles.
Full announcement: https://www.reddit.com/r/nanocurrency/comments/1hz841f/announcing_nanopow_local_proofofwork_at/
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
# nano-pow
+
_Proof-of-work generation and validation with WebGPU/WebGL for Nano cryptocurrency._
NanoPow uses WebGPU to generate proof-of-work nonces meeting the requirements
All calculations take place client-side, so nonces can be generated offline and
cached for the next transaction block. For more information about the
proof-of-work equation defined by Nano, see
-https://docs.nano.org/integration-guides/work-generation/#work-calculation-details
+<https://docs.nano.org/integration-guides/work-generation/#work-calculation-details>
## Installation
+
```console
-$ npm i nano-pow
+npm i nano-pow
```
+
NanoPow can also be installed globally to add the `nano-pow` command to the
system environment. To learn more, see [#Executables](#executables).
## Usage
+
### Import
+
The easiest way to use NanoPow is to import it directly. Based on the features
available in the environment, NanoPow will try to use its most performant API.
accomodate project style preferences:
```javascript
-import { NanoPow } from 'nano-pow'
+import { NanoPow } from "nano-pow";
// OR
-import NanoPow from 'nano-pow'
+import NanoPow from "nano-pow";
```
Use it directly on a webpage with a script module:
```html
<script type="module">
- (async () => {
- const { NanoPow } = await import('https://cdn.jsdelivr.net/npm/nano-pow@latest')
- const { work } = await NanoPow.work_generate(some_hash)
- console.log(work)
- })()
+ (async () => {
+ const { NanoPow } =
+ await import("https://cdn.jsdelivr.net/npm/nano-pow@latest");
+ const { work } = await NanoPow.work_generate(some_hash);
+ console.log(work);
+ })();
</script>
```
### Generate
+
```javascript
// `hash` is a 64-char hex string
-const hash = '0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef'
-const { work } = await NanoPow.work_generate(hash)
+const hash = "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef";
+const { work } = await NanoPow.work_generate(hash);
// Result is a 16-char hex string
```
### Validate
+
```javascript
// `work` is a 16-char hex string
-const work = 'fedcba0987654321'
+const work = "fedcba0987654321";
// `hash` is a 64-char hex string
-const hash = '0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef'
-const { valid } = await NanoPow.work_validate(work, hash)
+const hash = "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef";
+const { valid } = await NanoPow.work_validate(work, hash);
// Result is a boolean
```
### Options
+
```javascript
const options = {
- // default best available in order: webgpu => webgl => wasm => cpu
- api: 'webgpu',
- // default FFFFFFF800000000 for send/change blocks
- difficulty: 'FFFFFFC000000000',
- // default 4, valid range 1-32
- effort: 2,
- // default false
- debug: true
-}
-const { work } = await NanoPow.work_generate(hash, options)
+ // default best available in order: webgpu => webgl => wasm => cpu
+ api: "webgpu",
+ // default FFFFFFF800000000 for send/change blocks
+ difficulty: "FFFFFFC000000000",
+ // default 4, valid range 1-32
+ effort: 2,
+ // default false
+ debug: true,
+};
+const { work } = await NanoPow.work_generate(hash, options);
```
#### What is "effort"?
+
NanoPow's "effort" metric is an abstraction of various GPU and CPU capabilities.
Different systems will have different optimal settings, but as a general rule of
thumb:
-* WebGPU must strike a balance between the overhead of dispatching work to the
-GPU and the time it takes to compute the dispatch itself. Start with a low value
-like 2 or 4.
-* WegGL works by drawing to an invisible 2-D canvas that is `effort * 256`
-pixels long on each side. Since PoW speed in this case depends on resolution
-_and_ framerate, push for a value as high as the GPU can support. For example, a
-GPU that can draw 4096 x 4096 at 15 FPS should be set around 16 effort.
-* WASM does not use the GPU at all and instead depends on Web Workers for CPU
-multi-threading capabilities. Set effort equal to the number of physical cores
-in the CPU.
+- WebGPU must strike a balance between the overhead of dispatching work to the
+ GPU and the time it takes to compute the dispatch itself. Start with a low value
+ like 2 or 4.
+- WegGL works by drawing to an invisible 2-D canvas that is `effort * 256`
+ pixels long on each side. Since PoW speed in this case depends on resolution
+ _and_ framerate, push for a value as high as the GPU can support. For example, a
+ GPU that can draw 4096 x 4096 at 15 FPS should be set around 16 effort.
+- WASM does not use the GPU at all and instead depends on Web Workers for CPU
+ multi-threading capabilities. Set effort equal to the number of physical cores
+ in the CPU.
## Executables
+
NanoPow can be installed globally and executed from the command line. This is
useful for systems without a graphical interface.
+
```console
-$ npm -g i nano-pow
-$ nano-pow --help # view abbreviated CLI help
-$ man nano-pow # view full manual
+npm -g i nano-pow
+nano-pow --help # view abbreviated CLI help
+man nano-pow # view full manual
```
+
Ensure proper permissions exist on the
[npm `prefix`](https://docs.npmjs.com/cli/v11/commands/npm-prefix) directory and
that `PATH` is also configured accordingly. [nvm](https://github.com/nvm-sh/nvm)
is a great tool that handles this automatically.
### Command Line
+
NanoPow provides a shell command—`nano-pow`—to accomodate systems
without a graphical user interface. It launches a headless Chrome browser using
`puppeteer` to access the required WebGPU or WebGL APIs. Use the `--global` flag
when installing to add the executable script to the system.
+
```console
-$ npm i -g nano-pow
+npm i -g nano-pow
```
+
Some examples are provided below, and for full documentation, read the manual
with `man nano-pow`.
```console
-$ # Generate a work value using default settings and debugging output enabled.
-$ nano-pow --debug 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
+# Generate a work value using default settings and debugging output enabled.
+nano-pow --debug 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Generate work using customized behavior with options.
-$ nano-pow --effort 32 --difficulty FFFFFFC000000000 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
+# Generate work using customized behavior with options.
+nano-pow --effort 32 --difficulty FFFFFFC000000000 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Validate an existing work nonce against a blockhash.
+# Validate an existing work nonce against a blockhash.
nano-pow --validate fedcba9876543210 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
```
+
```console
-$ # Process blockhashes in batches to reduce the initial startup overhead.
-$ nano-pow 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef [...]
-$ # OR
+# Process blockhashes in batches to reduce the initial startup overhead.
+nano-pow 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef [...]
+# OR
nano-pow $(cat /path/to/hashes/file)
-$ # OR
-$ cat /path/to/hashes/file | nano-pow
+# OR
+cat /path/to/hashes/file | nano-pow
```
### Server
+
NanoPow also provides a basic work server similar to the one included in the
official Nano node software. The installed command will launch the server in a
detached process, and it can also be started manually to customize behavior by
executing the server script directly.
#### Environment Variables
+
`NANO_POW_DEBUG`: enable additional logging saved to the HOME directory
`NANO_POW_EFFORT`: increase or decrease demand on the GPU
`NANO_POW_PORT`: override the default port 5040
```console
-$ # Launch the server and detach from the current session
-$ NANO_POW_PORT=8080 nano-pow --server
-$ # View process ID for "NanoPow Server"
-$ cat ~/.nano-pow/server.pid
-$ # Display list of server logs
-$ ls ~/.nano-pow/logs/
-$ # Find process ID manually
-$ pgrep NanoPow
+# Launch the server and detach from the current session
+NANO_POW_PORT=8080 nano-pow --server
+# View process ID for "NanoPow Server"
+cat ~/.nano-pow/server.pid
+# Display list of server logs
+ls ~/.nano-pow/logs/
+# Find process ID manually
+pgrep NanoPow
```
+
Work is generated or validated by sending an HTTP `POST` request to the
configured hostname or IP address of the machine. Some basic help is available
via `GET` request.
+
```console
$ # Generate a work value
$ curl -d '{
- "action": "work_generate",
- "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
+ "action": "work_generate",
+ "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
}' localhost:5040
```
+
```console
$ # Validate a work value
$ curl -d '{
- "action": "work_validate",
- "work": "e45835c3b291c3d1",
- "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
+ "action": "work_validate",
+ "work": "e45835c3b291c3d1",
+ "hash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
}' localhost:5040
```
## Notes
+
The `work` field in a Nano transaction block contains an 8-byte nonce that
satisfies the following equation:
> 𝘣𝘭𝘢𝘬𝘦2𝘣(𝘯𝘰𝘯𝘤𝘦 || 𝘣𝘭𝘰𝘤𝘬𝘩𝘢𝘴𝘩) ≥ 𝘵𝘩𝘳𝘦𝘴𝘩𝘰𝘭𝘥
-* 𝘣𝘭𝘢𝘬𝘦2𝘣() is the cryptographic hash function BLAKE2b.
-* 𝘯𝘰𝘯𝘤𝘦, an 8-byte value, is generated for the transaction.
-* || is concatenation.
-* 𝘣𝘭𝘰𝘤𝘬𝘩𝘢𝘴𝘩, a 32-byte value, is either the public key of brand new accounts
-without transactions or the hash of the most recent block in the account chain
-for all other accounts.
-* 𝘵𝘩𝘳𝘦𝘴𝘩𝘰𝘭𝘥 is 0xFFFFFFF800000000 for send/change blocks and 0xFFFFFE0000000000
-for receive/open/epoch blocks.
+- 𝘣𝘭𝘢𝘬𝘦2𝘣() is the cryptographic hash function BLAKE2b.
+- 𝘯𝘰𝘯𝘤𝘦, an 8-byte value, is generated for the transaction.
+- || is concatenation.
+- 𝘣𝘭𝘰𝘤𝘬𝘩𝘢𝘴𝘩, a 32-byte value, is either the public key of brand new accounts
+ without transactions or the hash of the most recent block in the account chain
+ for all other accounts.
+- 𝘵𝘩𝘳𝘦𝘴𝘩𝘰𝘭𝘥 is 0xFFFFFFF800000000 for send/change blocks and 0xFFFFFE0000000000
+ for receive/open/epoch blocks.
The BLAKE2b implementation has been optimized to the extreme for this package
due to the very narrow use case to which it is applied. The compute shader used
every last bit of speed and performance out of it.
## Tests
-A few basic tests are availabe in the source repository.
-* `test/index.html` in the source repository contains a web interface to change
-execution options and compare results.
-* `test/script.sh` runs some basic benchmarks to check the CLI, and then it
-starts the `nano-pow` server and sends some validate and generate requests.
+
+A few basic tests are available in the source repository.
+
+- `test/index.html` in the source repository contains a web interface to change
+ execution options and compare results.
+- `test/script.sh` runs some basic benchmarks to check the CLI, and then it
+ starts the `nano-pow` server and sends some validate and generate requests.
## Building
+
1. Clone source
1. Enter the directory
1. Install dev dependencies
1. Compile, minify, and bundle
```console
-$ git clone https://zoso.dev/nano-pow.git
-$ cd nano-pow
-$ npm i
+git clone https://codecow.com/nano-pow.git
+cd nano-pow
+npm i
```
## Reporting Bugs
-Email: <bug-nano-pow@zoso.dev>
+
+Email: <bug-nano-pow@codecow.com>
## Acknowledgements
-[numtel/nano-webgl-pow](https://github.com/numtel/nano-webgl-pow) for his WebGL
-implementation
+
+[numtel/nano-webgl-pow](https://github.com/numtel/nano-webgl-pow) for his
+original WebGL implementation.
## Licenses
+
GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>
Portions of this code are also provided under the MIT License: <https://spdx.org/licenses/MIT.html>
## Donations
+
Tips are always appreciated and can be sent to the following developer address:
-```
+
nano_1zosoqs47yt47bnfg7sdf46kj7asn58b7uzm9ek95jw7ccatq37898u1zoso
-```
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
# Benchmarks to compute 16,777,216 nonces
+
_Each test is 128 samples of one pass (dispatch or frame) at zero difficulty with no early exit_
## Summary
+
- Chromium WebGPU and Firefox WebGL are the clear winners
- Chromium WebGL seems to suffer from an Nvidia driver issue
- Firefox WebGPU exhibits a strange implementation bottleneck
- Firefox supports up to a whopping 8192x8192 which actually makes it competitive with WebGPU
## All Results
-| Version | System | Browser | API | Total | Rate | Median | Mean |
-|-----------|--------------|-------------|-----------|-----------|----------|----------|----------|
-| RC | RTX 3070 | Chromium N | WebGPU | 747 | 218.23 | 4.5 | 4.58 |
-| RC | RTX 3070 | Firefox N | WebGL | 1096 | 117.06 | 8.55 | 8.54 |
-| RC | RTX 3070 | Firefox | WebGL | 1174 | 116.57 | 9 | 8.58 |
-| 2.0.0 | RTX 3070 | Chromium N | WebGPU | 1339 | 112.02 | ? | 10.47 |
-| RC | Intel Xe | Chromium N | WebGPU | 5107 | 25.20 | 39.5 | 39.69 |
-| RC | Intel Xe | Firefox | WebGL | 7166 | 18.84 | 52 | 53.07 |
-| RC | Intel Xe | Firefox N | WebGL | 8060 | 16.71 | 63 | 59.83 |
-| RC | iPhone 12 | Safari | WebGPU | 8586 | 14.97 | 67 | 66.79 |
-| 2.0.0 | iPhone 12 | Safari | WebGPU | 8765 | 14.69 | 68 | 68.48 |
-| RC | Intel Xe | Chromium N | WebGL | 9764 | 15.42 | 62.8 | 64.85 |
-| 2.0.0 | Intel Xe | Chromium N | WebGPU | 10103 | 12.63 | ? | 78.93 |
-| RC | RTX 3070 | Chromium N | WebGL | 10681 | 19.81 | 50.60 | 50.47 |
-| RC | iPhone 12 | Safari | WebGL | 12631 | 10.54 | 95 | 94.86 |
-| RC | iPad Mini 5 | Safari | WebGPU | 14232 | 8.78 | 114 | 113.85 |
-| 2.0.0 | iPad Mini 5 | Safari | WebGPU | 14903 | 8.59 | 118 | 116.41 |
-| RC | iPad Mini 5 | Safari | WebGL | 18928 | 6.97 | 145 | 143.40 |
-| RC | Intel Xe | Firefox N | WebGPU | 25679 | 4.99 | 200 | 200.47 |
-| 2.0.0 | Intel Xe | Firefox N | WebGPU | 25805 | 4.94 | ? | 201.60 |
-| 2.0.0 | RTX 3070 | Firefox N | WebGPU | 25629 | 4.97 | ? | 200.23 |
-| RC | RTX 3070 | Firefox N | WebGPU | 25633 | 5.00 | 200 | 200.15 |
-| 2.0.0 | RTX 3070 | Firefox | WebGL | 35224 | 3.72 | ? | 275.19 |
-| 2.0.0 | RTX 3070 | Chromium N | WebGL | 47603 | 3.06 | ? | 371.90 |
-| 2.0.0 | RTX 3070 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | Intel Xe | Firefox | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | Intel Xe | Firefox N | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | Intel Xe | Chromium N | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | iPhone 12 | Safari | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | iPad Mini 5 | Safari | WebGL | Unusable | N/A | ? | N/A |
+
+| Version | System | Browser | API | Total | Rate | Median | Mean |
+| ------- | ----------- | ---------- | ------ | -------- | ------ | ------ | ------ |
+| RC | RTX 3070 | Chromium N | WebGPU | 747 | 218.23 | 4.5 | 4.58 |
+| RC | RTX 3070 | Firefox N | WebGL | 1096 | 117.06 | 8.55 | 8.54 |
+| RC | RTX 3070 | Firefox | WebGL | 1174 | 116.57 | 9 | 8.58 |
+| 2.0.0 | RTX 3070 | Chromium N | WebGPU | 1339 | 112.02 | ? | 10.47 |
+| RC | Intel Xe | Chromium N | WebGPU | 5107 | 25.20 | 39.5 | 39.69 |
+| RC | Intel Xe | Firefox | WebGL | 7166 | 18.84 | 52 | 53.07 |
+| RC | Intel Xe | Firefox N | WebGL | 8060 | 16.71 | 63 | 59.83 |
+| RC | iPhone 12 | Safari | WebGPU | 8586 | 14.97 | 67 | 66.79 |
+| 2.0.0 | iPhone 12 | Safari | WebGPU | 8765 | 14.69 | 68 | 68.48 |
+| RC | Intel Xe | Chromium N | WebGL | 9764 | 15.42 | 62.8 | 64.85 |
+| 2.0.0 | Intel Xe | Chromium N | WebGPU | 10103 | 12.63 | ? | 78.93 |
+| RC | RTX 3070 | Chromium N | WebGL | 10681 | 19.81 | 50.60 | 50.47 |
+| RC | iPhone 12 | Safari | WebGL | 12631 | 10.54 | 95 | 94.86 |
+| RC | iPad Mini 5 | Safari | WebGPU | 14232 | 8.78 | 114 | 113.85 |
+| 2.0.0 | iPad Mini 5 | Safari | WebGPU | 14903 | 8.59 | 118 | 116.41 |
+| RC | iPad Mini 5 | Safari | WebGL | 18928 | 6.97 | 145 | 143.40 |
+| RC | Intel Xe | Firefox N | WebGPU | 25679 | 4.99 | 200 | 200.47 |
+| 2.0.0 | Intel Xe | Firefox N | WebGPU | 25805 | 4.94 | ? | 201.60 |
+| 2.0.0 | RTX 3070 | Firefox N | WebGPU | 25629 | 4.97 | ? | 200.23 |
+| RC | RTX 3070 | Firefox N | WebGPU | 25633 | 5.00 | 200 | 200.15 |
+| 2.0.0 | RTX 3070 | Firefox | WebGL | 35224 | 3.72 | ? | 275.19 |
+| 2.0.0 | RTX 3070 | Chromium N | WebGL | 47603 | 3.06 | ? | 371.90 |
+| 2.0.0 | RTX 3070 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | Intel Xe | Firefox | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | Intel Xe | Firefox N | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | Intel Xe | Chromium N | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | iPhone 12 | Safari | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | iPad Mini 5 | Safari | WebGL | Unusable | N/A | ? | N/A |
## RTX 3070
-| Version | Browser | API | Total | Rate | Median | Mean |
-|-----------|-------------|-----------|-----------|----------|----------|----------|
-| RC | Chromium N | WebGPU | 747 | 218.23 | 4.5 | 4.58 |
-| RC | Firefox N | WebGL | 1096 | 117.06 | 8.55 | 8.54 |
-| RC | Firefox | WebGL | 1174 | 116.57 | 9 | 8.58 |
-| 2.0.0 | Chromium N | WebGPU | 1339 | 112.02 | ? | 10.47 |
-| RC | Chromium N | WebGL | 10681 | 19.81 | 50.60 | 50.47 |
-| 2.0.0 | Firefox N | WebGPU | 25629 | 4.97 | ? | 200.23 |
-| RC | Firefox N | WebGPU | 25633 | 5.00 | 200 | 200.15 |
-| 2.0.0 | Firefox | WebGL | 35224 | 3.72 | ? | 275.19 |
-| 2.0.0 | Chromium N | WebGL | 47603 | 3.06 | ? | 371.90 |
-| 2.0.0 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
+
+| Version | Browser | API | Total | Rate | Median | Mean |
+| ------- | ---------- | ------ | -------- | ------ | ------ | ------ |
+| RC | Chromium N | WebGPU | 747 | 218.23 | 4.5 | 4.58 |
+| RC | Firefox N | WebGL | 1096 | 117.06 | 8.55 | 8.54 |
+| RC | Firefox | WebGL | 1174 | 116.57 | 9 | 8.58 |
+| 2.0.0 | Chromium N | WebGPU | 1339 | 112.02 | ? | 10.47 |
+| RC | Chromium N | WebGL | 10681 | 19.81 | 50.60 | 50.47 |
+| 2.0.0 | Firefox N | WebGPU | 25629 | 4.97 | ? | 200.23 |
+| RC | Firefox N | WebGPU | 25633 | 5.00 | 200 | 200.15 |
+| 2.0.0 | Firefox | WebGL | 35224 | 3.72 | ? | 275.19 |
+| 2.0.0 | Chromium N | WebGL | 47603 | 3.06 | ? | 371.90 |
+| 2.0.0 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
## Intel Xe integrated graphics
-| Version | Browser | API | Total | Rate | Median | Mean |
-|-----------|-------------|-----------|-----------|----------|----------|----------|
-| RC | Chromium N | WebGPU | 5107 | 25.20 | 39.5 | 39.69 |
-| RC | Firefox | WebGL | 7166 | 18.84 | 52 | 53.07 |
-| RC | Firefox N | WebGL | 8060 | 16.71 | 63 | 59.83 |
-| RC | Chromium N | WebGL | 9764 | 15.42 | 62.8 | 64.85 |
-| 2.0.0 | Chromium N | WebGPU | 10103 | 12.63 | ? | 78.93 |
-| RC | Firefox N | WebGPU | 25679 | 4.99 | 200 | 200.47 |
-| 2.0.0 | Firefox N | WebGPU | 25805 | 4.94 | ? | 201.60 |
-| 2.0.0 | Firefox | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
-| 2.0.0 | Chromium N | WebGL | Unusable | N/A | ? | N/A |
+
+| Version | Browser | API | Total | Rate | Median | Mean |
+| ------- | ---------- | ------ | -------- | ----- | ------ | ------ |
+| RC | Chromium N | WebGPU | 5107 | 25.20 | 39.5 | 39.69 |
+| RC | Firefox | WebGL | 7166 | 18.84 | 52 | 53.07 |
+| RC | Firefox N | WebGL | 8060 | 16.71 | 63 | 59.83 |
+| RC | Chromium N | WebGL | 9764 | 15.42 | 62.8 | 64.85 |
+| 2.0.0 | Chromium N | WebGPU | 10103 | 12.63 | ? | 78.93 |
+| RC | Firefox N | WebGPU | 25679 | 4.99 | 200 | 200.47 |
+| 2.0.0 | Firefox N | WebGPU | 25805 | 4.94 | ? | 201.60 |
+| 2.0.0 | Firefox | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | Firefox N | WebGL | Unusable | N/A | ? | N/A |
+| 2.0.0 | Chromium N | WebGL | Unusable | N/A | ? | N/A |
## iPhone 12 (A14 Bionic, ??? 4-core GPU)
-| Version | Browser | API | Total | Rate | Median | Mean |
-|-----------|-------------|-----------|-----------|----------|----------|----------|
-| RC | Safari | WebGPU | 8586 | 14.97 | 67 | 66.79 |
-| 2.0.0 | Safari | WebGPU | 8765 | 14.69 | 68 | 68.48 |
-| RC | Safari | WebGL | 12631 | 10.54 | 95 | 94.86 |
-| 2.0.0 | Safari | WebGL | Unusable | N/A | ? | N/A |
+
+| Version | Browser | API | Total | Rate | Median | Mean |
+| ------- | ------- | ------ | -------- | ----- | ------ | ----- |
+| RC | Safari | WebGPU | 8586 | 14.97 | 67 | 66.79 |
+| 2.0.0 | Safari | WebGPU | 8765 | 14.69 | 68 | 68.48 |
+| RC | Safari | WebGL | 12631 | 10.54 | 95 | 94.86 |
+| 2.0.0 | Safari | WebGL | Unusable | N/A | ? | N/A |
## iPad Mini 5 (A12 Bionic, G11P 4-core GPU)
-| Version | Browser | API | Total | Rate | Median | Mean |
-|-----------|-------------|-----------|-----------|----------|----------|----------|
-| RC | Safari | WebGPU | 14232 | 8.78 | 114 | 113.85 |
-| 2.0.0 | Safari | WebGPU | 14903 | 8.59 | 118 | 116.41 |
-| RC | Safari | WebGL | 18928 | 6.97 | 145 | 143.40 |
-| 2.0.0 | Safari | WebGL | Unusable | N/A | ? | N/A |
+
+| Version | Browser | API | Total | Rate | Median | Mean |
+| ------- | ------- | ------ | -------- | ---- | ------ | ------ |
+| RC | Safari | WebGPU | 14232 | 8.78 | 114 | 113.85 |
+| 2.0.0 | Safari | WebGPU | 14903 | 8.59 | 118 | 116.41 |
+| RC | Safari | WebGL | 18928 | 6.97 | 145 | 143.40 |
+| 2.0.0 | Safari | WebGL | Unusable | N/A | ? | N/A |
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
Twelve rounds of G mixing as part of BLAKE2b compression step, each divided into eight subprocesses. Each subprocess applies transformations to `m` and `v` variables based on a defined set of index inputs. The algorithm for each subprocess is defined as ollows:
-* r is the current round
-* i is the current subprocess within that round
-* a, b, c, d are elements of `v` at specific indexes
-* sigma is a defined set of array indexes for `m`
-* rotr64 is a right-hand bit rotation function
+- r is the current round
+- i is the current subprocess within that round
+- a, b, c, d are elements of `v` at specific indexes
+- sigma is a defined set of array indexes for `m`
+- rotr64 is a right-hand bit rotation function
```
a = a + b
-\# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+\# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
\# SPDX-License-Identifier: GPL-3.0-or-later
.TH nano-pow 1 2025-06-27 "nano-pow v5.1.2"
Written by Chris Duncan.
.SH BUGS
-Email <bug-nano-pow@zoso.dev>.
+Email <bug-nano-pow@codecow.com>.
.SH COPYRIGHT
.PP
.EX
-Copyright \(co 2025 Chris Duncan <chris@zoso.dev>
+Copyright \(co 2025 Chris Duncan <chris@codecow.com>
Nano PoW documentation: <https://docs.nano.org/integration-guides/work-generation/#work-calculation-details>
License GPLv3+: GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>
Portions of this code are also provided under the MIT License: <https://spdx.org/licenses/MIT.html>
-# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
# SPDX-License-Identifier: GPL-3.0-or-later
## Example systemd service unit file to start the nano-pow server at login.
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { build } from 'esbuild'
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
"webgl",
"webgl2"
],
- "homepage": "https://zoso.dev",
- "bugs": "bug-nano-pow@zoso.dev",
+ "homepage": "https://codecow.com",
+ "bugs": "bug-nano-pow@codecow.com",
"license": "(GPL-3.0-or-later AND MIT)",
- "author": "Chris Duncan <chris@zoso.dev>",
+ "author": "Chris Duncan <chris@codecow.com>",
"funding": {
"type": "nano",
"url": "nano:nano_1zosoqs47yt47bnfg7sdf46kj7asn58b7uzm9ek95jw7ccatq37898u1zoso"
"man": "./docs/nano-pow.1",
"repository": {
"type": "git",
- "url": "git+https://zoso.dev/nano-pow.git"
+ "url": "git+https://codecow.com/nano-pow.git"
},
"scripts": {
"benchmark": "npm run build && ./dist/bin/nano-pow.sh --benchmark 10 --debug",
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { writeFile } from 'node:fs/promises'
const main = (() => {
switch (api) {
case 'wasm': {
- return `//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+ return `//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
export function main (seed: u64, h0: u64, h1: u64, h2: u64, h3: u64, difficulty: u64): u64 {
case 'webgl': {
return `#version 300 es
#pragma vscode_glsllint_stage: frag
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-FileContributor: Ben Green <ben@latenightsketches.com>
//! SPDX-License-Identifier: GPL-3.0-or-later AND MIT
`
}
case 'webgpu': {
- return `//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+ return `//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
// Input buffers
#!/usr/bin/env node
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { Serializable, spawn } from 'node:child_process'
Effort must be a decimal number between 1-32.
Difficulty must be a hexadecimal string between 0-FFFFFFFFFFFFFFFF.
-Report bugs: <bug-nano-pow@zoso.dev>
+Report bugs: <bug-nano-pow@codecow.com>
Full documentation: <https://www.npmjs.com/package/nano-pow>
`)
process.exit(0)
#!/usr/bin/env bash
-# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
# SPDX-License-Identifier: GPL-3.0-or-later
SCRIPT_LINK=$(readlink -f "$0");
#!/usr/bin/env node
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import * as http from 'node:http'
WORK is little-endian 16-character hexadecimal string.
DIFFICULTY is an optional 16-character hexadecimal string (default: FFFFFFF800000000)
-Report bugs: <bug-nano-pow@zoso.dev>
+Report bugs: <bug-nano-pow@codecow.com>
Full documentation: <https://www.npmjs.com/package/nano-pow>
`)
}
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { NanoPowOptions } from '#types'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { NanoPowValidate } from '#lib/validate'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
export { generate as NanoPowCpu } from '#lib/generate/cpu'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
export function main (seed: u64, h0: u64, h1: u64, h2: u64, h3: u64, difficulty: u64): u64 {
let m0 = v128.splat<u64>(0);
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { NanoPowValidate } from '#lib/validate'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
//@ts-expect-error
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-FileContributor: Ben Green <ben@latenightsketches.com>
//! SPDX-License-Identifier: GPL-3.0-or-later AND MIT
#version 300 es
#pragma vscode_glsllint_stage: frag
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
#ifdef GL_FRAGMENT_PRECISION_HIGH
#version 300 es
#pragma vscode_glsllint_stage: frag
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-FileContributor: Ben Green <ben@latenightsketches.com>
//! SPDX-License-Identifier: GPL-3.0-or-later AND MIT
// hash - Array of 32-bit integers comprising a 32-byte Nano block hash
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { default as downsampleSource } from './downsample.frag'
#version 300 es
#pragma vscode_glsllint_stage: vert
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-FileContributor: Ben Green <ben@latenightsketches.com>
//! SPDX-License-Identifier: GPL-3.0-or-later AND MIT
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
declare module '*.frag' {
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { default as NanoPowGpuComputeShader } from './shaders/compute.wgsl'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
// Input buffers
struct INPUT {
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
declare module '*.wgsl' {
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { NanoPowValidate } from '#lib/validate'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { WorkValidateResponse } from '#types'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { work_generate, work_validate } from './lib'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
declare global {
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { wasm } from './wasm'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
const wasm = { isSupported: false }
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
const webgl = { isSupported: false }
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
const webgpu = { isSupported: false }
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
export function bigintAsUintNArray (int: bigint, bits: number, length: number = 0) {
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { WorkGenerateResponse } from "#types"
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
import { Cache } from '.'
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
/**
-//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+//! SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
//! SPDX-License-Identifier: GPL-3.0-or-later
/**
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
<!--
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later
-->
<h3>Scoring</h3>
<label for="runs">Score Runs</label>
<input id="runs" type="number" value="1" autofocus />
- <button id="btnStartScore">Score ❗</button>
+ <button id="btnStartScore">Score ❗</button>
<hr />
<h3 id="status">WAITING</h3>
<hr />
#!/usr/bin/env bash
-# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+# SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
# SPDX-License-Identifier: GPL-3.0-or-later
set -euo pipefail
-SPDX-FileCopyrightText: 2025 Chris Duncan <chris@zoso.dev>
+SPDX-FileCopyrightText: 2025 Chris Duncan <chris@codecow.com>
SPDX-License-Identifier: GPL-3.0-or-later