This repository has been archived on 2026-08-19. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
2026-08-20 00:45:43 +02:00

96 lines
3.2 KiB
Python

import torch
import time
import os
import sys
import gc
print(f'Device: {torch.cuda.get_device_name(0)}')
print(f'Total Memory: {torch.cuda.get_device_properties(0).total_memory / 1e9:.1f} GB')
print()
def mem_info():
alloc = torch.cuda.memory_allocated() / 1e6
reserved = torch.cuda.memory_reserved() / 1e6
return f'alloc={alloc:.0f}MB, reserved={reserved:.0f}MB'
def test_attention(heads, seq_len, head_dim, dtype=torch.float32):
label = f'Attn h={heads} s={seq_len} d={head_dim} {"fp32" if dtype==torch.float32 else "fp16"}'
print(f'=== {label} ===', flush=True)
# Calculate memory needed
attn_size = heads * seq_len * seq_len * (4 if dtype==torch.float32 else 2)
qk_size = 2 * heads * seq_len * head_dim * (4 if dtype==torch.float32 else 2)
total_est = (attn_size + qk_size) / 1e6
print(f' Est memory: {total_est:.0f}MB ({mem_info()})', flush=True)
try:
q = torch.randn(1, heads, seq_len, head_dim, device='cuda', dtype=dtype)
k = torch.randn(1, heads, seq_len, head_dim, device='cuda', dtype=dtype)
print(f' Q/K allocated ({mem_info()})', flush=True)
torch.cuda.synchronize()
t = time.time()
scores = torch.matmul(q, k.transpose(-2, -1))
torch.cuda.synchronize()
elapsed = time.time() - t
print(f' OK: {elapsed:.3f}s, scores shape={list(scores.shape)} ({mem_info()})', flush=True)
del q, k, scores
gc.collect()
torch.cuda.empty_cache()
return True
except Exception as e:
print(f' FAIL: {e}', flush=True)
gc.collect()
torch.cuda.empty_cache()
return False
# Progressive attention scaling
test_attention(4, 512, 64)
test_attention(8, 1024, 64)
test_attention(8, 1024, 128)
test_attention(16, 2048, 128)
test_attention(24, 2048, 128)
test_attention(24, 4096, 128) # full Lumina2 scale!
# If full scale fails in fp32, try fp16
print()
print('=== fp16 ATTENTION TESTS ===', flush=True)
test_attention(24, 4096, 128, torch.float16)
# Test split attention approach (process in chunks)
print()
print('=== SPLIT ATTENTION (simulate ComfyUI split attn) ===', flush=True)
try:
heads = 24
seq = 4096
hd = 128
chunk = 512 # process 512 tokens at a time
q = torch.randn(1, heads, seq, hd, device='cuda', dtype=torch.float32)
k = torch.randn(1, heads, seq, hd, device='cuda', dtype=torch.float32)
v = torch.randn(1, heads, seq, hd, device='cuda', dtype=torch.float32)
out = torch.zeros(1, heads, seq, hd, device='cuda', dtype=torch.float32)
torch.cuda.synchronize()
t = time.time()
for i in range(0, seq, chunk):
q_chunk = q[:, :, i:i+chunk, :]
scores = torch.matmul(q_chunk, k.transpose(-2, -1))
attn = torch.softmax(scores, dim=-1)
out[:, :, i:i+chunk, :] = torch.matmul(attn, v)
del scores, attn
torch.cuda.synchronize()
elapsed = time.time() - t
print(f' Split attention OK: {elapsed:.3f}s', flush=True)
del q, k, v, out
gc.collect()
torch.cuda.empty_cache()
except Exception as e:
print(f' Split attention FAIL: {e}', flush=True)
print()
print('=== DONE ===', flush=True)
torch.cuda.synchronize()
os._exit(0)