Skip to content

Commit d1dbc71

Browse files
committed
eager: dequantize INT8 weights instead of torch._int_mm on AMD RDNA / CPU
1 parent 685ac8b commit d1dbc71

1 file changed

Lines changed: 39 additions & 0 deletions

File tree

comfy_kitchen/backends/eager/quantization.py

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@
66
# Copyright (c) Meta Platforms, Inc. and affiliates.
77
# Licensed under the BSD 3-Clause License (see NOTICE file for details)
88

9+
import functools
10+
import os
11+
912
import torch
1013

1114
from comfy_kitchen.float_utils import (
@@ -861,6 +864,33 @@ def dequantize_int8_simple(q: torch.Tensor, scale: torch.Tensor) -> torch.Tensor
861864
return q.float() * scale
862865

863866

867+
_CDNA_ARCHS = frozenset({"gfx908", "gfx90a", "gfx940", "gfx941", "gfx942", "gfx950"})
868+
869+
870+
def _use_int8_mm(device_type: str, device_index: int) -> bool:
871+
mode = os.environ.get("COMFY_KITCHEN_INT8_EAGER", "auto").strip().lower()
872+
if mode == "int_mm":
873+
return True
874+
if mode == "dequant":
875+
return False
876+
if mode == "auto":
877+
return _use_int8_mm_auto(device_type, device_index)
878+
raise ValueError("COMFY_KITCHEN_INT8_EAGER must be one of: auto, int_mm, dequant")
879+
880+
881+
@functools.lru_cache(maxsize=None)
882+
def _use_int8_mm_auto(device_type: str, device_index: int) -> bool:
883+
if device_type != "cuda" or not torch.cuda.is_available():
884+
return False
885+
if getattr(torch.version, "hip", None) is None:
886+
return True
887+
try:
888+
arch = torch.cuda.get_device_properties(device_index).gcnArchName.split(":")[0]
889+
except Exception:
890+
return False
891+
return arch in _CDNA_ARCHS
892+
893+
864894
def int8_linear(
865895
x: torch.Tensor,
866896
weight: torch.Tensor,
@@ -908,6 +938,15 @@ def int8_linear(
908938
h = _build_hadamard(convrot_groupsize, device=x.device, dtype=x.dtype)
909939
x = _rotate_activation(x, h, convrot_groupsize)
910940

941+
if not _use_int8_mm(x.device.type, x.device.index if x.device.index is not None else 0):
942+
ws = weight_scale.float()
943+
w = (weight.float() * (ws if ws.numel() == 1 else ws.reshape(-1, 1))).to(out_dtype)
944+
return torch.nn.functional.linear(
945+
x.to(out_dtype),
946+
w,
947+
None if bias is None else bias.to(device=x.device, dtype=out_dtype),
948+
)
949+
911950
orig_shape = x.shape
912951
x_2d = x.reshape(-1, x.shape[-1])
913952

0 commit comments

Comments
 (0)