Instructions to use Phips/PULSE with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- TensorRT
How to use Phips/PULSE with TensorRT:
# No code snippets available yet for this library. # To use this model, check the repository files and the library's documentation. # Want to help? PRs adding snippets are welcome at: # https://github.com/huggingface/huggingface.js
- Notebooks
- Google Colab
- Kaggle
PULSE
A tiny, deployment-first super-resolution network.
PULSE is the tiny/fast sibling of NERVE: a much smaller convolutional SISR model with the same deployment-first philosophy. It trades capacity for size and speed, so it is less capable than NERVE and is intended for light cleanup and clean upscaling rather than heavy restoration. It trains on a consumer GPU, converts without surprises, and embeds almost anywhere.
pulse: 48 channels, 353,856 parameterspulse_fast: 32 channels, 162,192 parameters- 2x and 4x models
- PyTorch
.safetensors+ dynamic ONNX - MIT code and weights, trained on CC0 / public-domain images only
Links: HEART · NERVE · PULSE demo · PULSE ONNX converter
Short version: load a released
.safetensorswithpulse_arch.py, or an.onnxwith ONNX Runtime. Start with 2x for browser/CPU use.
Why PULSE
PULSE is not different for the sake of being different. Each constraint removes a real deployment or maintenance problem.
- No
Resizeop in the exported graph. The scale is done by a fixed MKS2013 base plus PixelShuffle. ONNX, TensorRT, NCNN, and other runtimes all see the same standard graph; there is no interpolation implementation mismatch. - Only standard ops.
Conv / Add / ReLU / Pad / DepthToSpace. No custom kernels, no fused/unfused checkpoint pair, no fragile converter step. That makes it easy to audit, port, optimize withonnxsim, and compile with TensorRT. - Fixed MKS2013 base. The base upsampler has no learned parameters and no dynamic branch. It anchors the output, reduces what the network must learn, and keeps the graph compact and deterministic.
- No attention and no normalization. That means stable bf16 AMP training, fewer memory spikes, and simpler maintenance. The whole model is readable.
- Tiny. 162K–354K parameters. It fits browser/WASM budgets, small GPUs, CPU fallbacks, and embedded pipelines where a transformer does not.
- Fast training. The pretrain uses Charbonnier only: no discriminator, no perceptual stack, no fragile GAN schedule. It trains on a single RTX 3060.
- Dynamic ONNX. One model works at any H/W; no per-resolution exports.
What it is for
PULSE is a local, low-cost upscaler. The released pretrains are clean 2x/4x models, not a general blind-restoration model.
- Browser or desktop upscaling. ONNX Runtime Web/WASM/WebGPU can run the 2x models; 4x is heavier but still small.
- Image viewers, galleries, thumbnail pipelines. A fast local pass before display, with no server round-trip.
- Anime and illustration stills. Clean 2x/4x upscaling; a compression-trained variant is a separate model.
- Batch/offline preprocessing. Small enough to share a consumer GPU or CPU.
- Embedding in apps. One architecture file, one op set, no fuse step.
Compression cleanup is a real use case, but it needs the separate PULSE-Web finetune. The released clean pretrain was not trained on JPEG/WebP/AVIF/H.265/GIF artifacts.
A temporal/video cleaner is not part of this release. Per-frame PULSE can be a component, but flicker-free video needs temporal conditioning.
When to use NERVE or HEART instead
| Need | Use |
|---|---|
| Browser/CPU, tiny model, fast 2x/4x | PULSE |
| Better quality / heavier restoration with a ~1.8M conv-only edge model | NERVE |
| Highest quality / desktop-server GPU budget | HEART |
| Blind OTF restoration, heavy blur/noise | NERVE/HEART OTF or a larger restoration model |
| Tiny/fast NERVE-like model for light cleanup | PULSE |
| Text/UI/screenshot upscaling | a text-aware restoration model, not PULSE |
| Temporal video restoration | a temporal model; PULSE is per-frame only |
PULSE is the tiny/fast NERVE sibling: the same practical philosophy, but far fewer parameters and a lighter operating envelope. NERVE is the more capable restoration model; PULSE is for light degradation, clean upscaling, browser/CPU use, and cases where the model itself must be almost free.
PULSE is not competing with HEART on PSNR.
Pick a model
| Want | Use | Scale | Params |
|---|---|---|---|
| Best small-model quality | pulse |
4x / 2x | 353,856 |
| Fastest / lowest compute | pulse_fast |
4x / 2x | 162,192 |
| CPU / ORT / engine | onnx/*_fp16.onnx |
4x / 2x | same |
All released models are pretrained only on CC0 / public-domain images. They are MIT-licensed and permissive.
Urban100 validation
| Model | PSNR | SSIM | TopIQ | LPIPS |
|---|---|---|---|---|
4x pulse |
25.6523 | 0.7717 | 0.5907 | 0.2452 |
2x pulse |
31.4423 | 0.9221 | 0.8614 | 0.0721 |
4x pulse_fast |
25.4239 | 0.7638 | 0.5748 | 0.2553 |
2x pulse_fast |
31.1371 | 0.9188 | 0.8551 | 0.0755 |
EMA weights, standard Urban100 validation. PSNR/SSIM are Y-channel with a 4px border crop; TopIQ/LPIPS are RGB. No TTA.
Inference speed
RTX 3060, batch 1, fp16. TensorRT engine built locally.
| Model | 256² eager | 720p eager | 1080p eager | 256² TRT | 720p TRT | 1080p TRT |
|---|---|---|---|---|---|---|
pulse_fast |
3.65 | 47.00 | 103.88 | 1.43 | 17.52 | 39.60 |
pulse |
6.71 | 90.20 | 199.28 | 2.82 | 35.35 | 79.65 |
Training speed
CC0/public-domain 200k fidelity pretrain, RTX 3060, batch 8, bf16:
pulse4x: ~29 it/spulse2x: ~9.8 it/spulse_fast4x: ~36 it/spulse_fast2x: ~20 it/s
Training is Charbonnier-only. Perceptual branches are experimental and are not part of the pretrain release.
Quickstart
ONNX Runtime
import onnxruntime as ort
sess = ort.InferenceSession("onnx/4x_pulse_fp16.onnx", providers=["CPUExecutionProvider"])
# input: float32 [1, 3, H, W] in [0, 1], RGB, dynamic H/W
The fp16 file is self-contained. Use 4x_pulse.onnx if your runtime lacks fp16.
PyTorch / spandrel
- Copy
pulse_arch.pyintotraiNNer/archs/(or use the file here). - Load the
.safetensorswith spandrel once PULSE is registered. - Input RGB
[0,1], output 2x/4x.
Train
cp pulse_arch.py <traiNNer-redux>/traiNNer/archs/
cp configs/4x_pulse_pretrain.yml <traiNNer-redux>/options/
cd <traiNNer-redux>
python train.py -opt options/4x_pulse_pretrain.yml
The sample configs use placeholder data paths and can be trained from scratch. The released pretrains are provided as warm starts.
Visual examples
Urban100 4x. Left: bicubic input. Right: released PULSE 4x pretrain.
Files
pulse_arch.py
models/
pulse/4x_pretrain.safetensors
pulse/2x_pretrain.safetensors
pulse_fast/4x_pretrain.safetensors
pulse_fast/2x_pretrain.safetensors
onnx/
*_fp16.onnx
*.onnx
configs/
4x_pulse_pretrain.yml
2x_pulse_pretrain.yml
4x_pulse_fast_pretrain.yml
2x_pulse_fast_pretrain.yml
PAPER.md
examples/
Limitations
- Not a blind-OTF model; no degradation embedding.
- Not a text/UI upscaler.
- The clean pretrain does not clean compression artifacts; use a web/anime finetune for that.
- No temporal/video model is included.
- PSNR is below HEART; that is the intended size/speed tradeoff.
Attribution
The fixed base uses Magic Kernel Sharp 2013 by John Costella
(https://johncostella.com/magic/). The public reference implementation
(felixr/magic-kernel-sharp, MIT) is credited in ATTRIBUTION.md. PULSE uses
an independent PyTorch implementation of the integer-scale phase kernels, not
a copy of the reference C code.
License
The code and released weights are MIT-licensed and permissive. Keep the
MIT copyright and permission notice with copies or substantial portions of the
software. See LICENSE.
The released weights were trained on a curated CC0 / public-domain image set. This is a provenance statement, not a guarantee; source-image rights and jurisdiction-specific rules can still matter. No warranty is provided.
@misc{pulse_body_2026,
title = {PULSE: A Deployment-First Single-Image Super-Resolution Network},
author = {Philip Hofmann and contributors},
year = {2026},
note = {BODY suite}
}


