Instructions to use ProCreations/Image-2.1-Calibrated-NVFP4 with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- Diffusers
How to use ProCreations/Image-2.1-Calibrated-NVFP4 with Diffusers:
pip install -U diffusers transformers accelerate
import torch from diffusers import DiffusionPipeline # switch to "mps" for apple devices pipe = DiffusionPipeline.from_pretrained("ProCreations/Image-2.1-Calibrated-NVFP4", dtype=torch.bfloat16, device_map="cuda") prompt = "Astronaut in a jungle, cold color palette, muted colors, detailed, 8k" image = pipe(prompt).images[0] - Notebooks
- Google Colab
- Kaggle
- Local Apps Settings
- Draw Things
- DiffusionBee
Release calibrated Image2.1 NVFP4 transformer with dynamic scaling and BF16 rank correction, native SM120 runtime, quality evidence and real-time demo
1961af5 verified Download source/weight_quant.py from ProCreations/Image-2.1-Calibrated-NVFP4: direct link, hf CLI and curl.
- Browser
- Download file 1.82 kB
-
https://huggingface.co/ProCreations/Image-2.1-Calibrated-NVFP4/resolve/main/source/weight_quant.py
- Command line
-
hf download hf://ProCreations/Image-2.1-Calibrated-NVFP4/source/weight_quant.py
-
curl -L -o weight_quant.py https://huggingface.co/ProCreations/Image-2.1-Calibrated-NVFP4/resolve/main/source/weight_quant.py
1.82 kB
| """Offline activation-weighted block-scale search for NVFP4 weights.""" | |
| import torch | |
| import triton | |
| import triton.language as tl | |
| def _round(v): | |
| a=tl.abs(v) | |
| code=(a>.25).to(tl.int32)+(a>=.75)+(a>1.25)+(a>=1.75)+(a>2.5)+(a>=3.5)+(a>5.) | |
| val=tl.where(code<4,code*.5,tl.where(code==4,2.,tl.where(code==5,3.,tl.where(code==6,4.,6.)))) | |
| return code|tl.where(v<0,8,0),val*tl.where(v<0,-1.,1.) | |
| def _quant(W,H,G,Q,S,COUNT:tl.constexpr,K:tl.constexpr,SEARCH:tl.constexpr,B:tl.constexpr): | |
| b=tl.program_id(0)*B+tl.arange(0,B) | |
| i=tl.arange(0,16) | |
| w=tl.load(W+b[:,None]*16+i[None,:],b[:,None]<COUNT,0).to(tl.float32) | |
| h=tl.load(H+(b[:,None]*16+i[None,:])%K).to(tl.float32) | |
| g=tl.load(G) | |
| amax=tl.max(tl.abs(w),1)*g/6 | |
| best=tl.full((B,),float('inf'),tl.float32) | |
| selected=tl.full((B,),1.,tl.float32) | |
| for j in range(SEARCH): | |
| factor=1. if SEARCH==1 else .7+.05*j | |
| s=tl.minimum(448.,tl.maximum(amax*factor,.001953125)).to(tl.float8e4nv).to(tl.float32) | |
| code,dq=_round(w*g/s[:,None]) | |
| delta=w-dq*s[:,None]/g | |
| err=tl.sum(delta*delta*h,1) | |
| selected=tl.where(err<best,s,selected);best=tl.minimum(err,best) | |
| code,_=_round(w*g/selected[:,None]) | |
| halves=tl.reshape(code,(B,8,2)) | |
| packed=tl.sum(halves << (tl.arange(0,2)[None,None,:]*4),2) | |
| tl.store(Q+b[:,None]*8+tl.arange(0,8)[None,:],packed,b[:,None]<COUNT) | |
| tl.store(S+b,selected,b<COUNT) | |
| def quantize_weight(w,global_scale,hdiag,search=True): | |
| n,k=w.shape | |
| assert n%128==0 and k%64==0 | |
| q=torch.empty((n,k//2),device=w.device,dtype=torch.uint8) | |
| sf=torch.empty((n,k//16),device=w.device,dtype=torch.float8_e4m3fn) | |
| _quant[(triton.cdiv(n*k//16,64),)](w.contiguous(),hdiag.contiguous(),global_scale,q,sf,n*k//16,k,15 if search else 1,64,num_warps=4) | |
| sw=sf.view(torch.uint8).reshape(n//128,4,32,k//64,4).permute(0,3,2,1,4).contiguous().flatten() | |
| return q,sw | |