Conversation
Signed-off-by: Kirthi Shankar Sivamani <ksivamani@nvidia.com>
Signed-off-by: Kirthi Shankar Sivamani <ksivamani@nvidia.com>
|
| LayerNorm, | ||
| RMSNorm, | ||
| TransformerEngineBaseModule, | ||
| LinearAttentionBase, |
There was a problem hiding this comment.
FSDP setup calls missing method
Adding LinearAttentionBase to the TE-class registry makes directly or individually FSDP-wrapped GDN modules enter prepare_te_modules_for_fsdp. That function unconditionally calls fast_setattr, but the new base is a plain torch.nn.Module and does not implement this method. FSDP preparation therefore raises AttributeError before the model can run.
| "pydantic", | ||
| "nvdlfw-inspect", | ||
| "nvidia-cudnn-frontend>=1.28.0", | ||
| "nvidia-cudnn-frontend>=1.29.0", |
There was a problem hiding this comment.
Required runtime is not installed
GDN2 explicitly requires the cuDNN frontend cutedsl runtime, but both installation declarations request only the base nvidia-cudnn-frontend package. If that base package does not include the optional cutlass runtime, the newly mandatory L0 GDN2 test fails during collection and the advertised feature cannot run.
for more information, see https://pre-commit.ci
Signed-off-by: Kirthi Shankar Sivamani <ksivamani@nvidia.com>
Signed-off-by: Kirthi Shankar Sivamani <ksivamani@nvidia.com>
| attention(q, k, v, g=g, beta=beta) | ||
|
|
||
|
|
||
| def test_gdn2_rejects_fp8_autocast(): |
There was a problem hiding this comment.
On a CUDA device where FP8 is unavailable, autocast(enabled=True) raises RuntimeError while entering the context, before GDN2 can raise the expected ValueError. Because this test no longer checks FP8 availability, it fails on those supported test configurations instead of validating the module's FP8 rejection behavior.
Signed-off-by: Kirthi Shankar Sivamani <ksivamani@nvidia.com>
|
/te-ci pytorch |
KshitijLakhani
left a comment
There was a problem hiding this comment.
-
Can we consider moving both gdn and gdn2 tests into the same linear attention file for testing and then we can just add the newer linear attention types to it in the future. I'm also assuming here that the tests could share some setup/boilerplate info (e.g. is gdn/gdn op available ?) .
The other (maybe preferred) option is to have a these separate as you currently have them and then have a shared test file/class in which the shared utilities could cover (for e.g.) :
i) RMS comparison helpers.
ii) THD input conversion.
iii) TP/lifecycle tests.
iv) Checkpointing tests.
v) Common output-shape/layout conformance. -
nit: I understand this might be for simplicity in interest of time that even thought cuDNN GDN2 supports distinct Q, K and V head counts, the TE wrapper requires all head counts to be equal, but please one of the following - i) Add this support (ideal) or ii) Add a TODO and add either Charlene or my name for it for the future) . And on the same note, I learnt from my agent that cuDNN GDN API seems to be supporting a a lot of other args, but I'm guessing yoau are intentionally using a minimal GDN2 API ??
-
This is not supposed to be a blocker for this PR but @cyanguwa I think it would make sense to have a plan for integration into upper Transformer Layers ? (right now it is DPA/MHA hard-coded but we might have to change it with linear / spare right ?)
Something liek this:
TransformerLayer
├── MultiheadAttention
│ QKV projection → DPA → output projection
│
└── GDN2 attention block
QKV + gate projections → GDN2 core → output projection
- Non-blocking: I understand the hesitation to refactor TransformerEngineBaseModule, especially since it is central and has been relatively stable. Keeping LinearAttentionBase separate is reasonable for this PR and avoids pulling unused FP8 state into parameter-free LA kernels.
My concern is less the duplicated implementation and more that this creates a second module type participating in TE-wide lifecycle behavior. This PR already updates get_te_classes(), CUDA-graph discovery, and implements the FSDP fast_setattr contract. Future framework-level code could recognize TransformerEngineBaseModule but unintentionally omit LinearAttentionBase.
For now, as discussed offline, could you please document the minimal TE lifecycle contract being implemented here ?
| return True | ||
|
|
||
|
|
||
| def _gdn2_supported_arch() -> bool: |
There was a problem hiding this comment.
nit: Any reason this check does not exist for GDN and only GDN-2 tests ?
There was a problem hiding this comment.
GDN-2 doesn't have a cu-tile backend, only FROST engine is supported here, so blackwell+
| return None | ||
|
|
||
|
|
||
| class LinearAttentionKernelAdapter(torch.nn.Module): |
There was a problem hiding this comment.
Non-blocking follow-up: I like the private adapter as a thin shim, but _run() currently encodes several GDN/GDN2-specific assumptions: aligned Q/K/V token dimensions, identical Q/K shapes, equal Q/V head counts, and state heads derived from Q heads. These do not describe LA generally: GDP uses T Q/g rows but T ×num_householder K/V/beta rows, while KDA supports HK = H or HK = HV and uses HO = max(H, HV) for output/state heads.
Based on our offline discussion, I am okay deferring that generalization until KDA/GDP are added. At that point, I think these checks should move into the flavor-specific adapter rather than simply being removed or weakened globally, so GDN/GDN2 retain strict validation.
It would be helpful to leave a TODO or tracking issue recording that intended boundary.
|
|
||
| Gated DeltaNet v2 replaces Gated DeltaNet's scalar gates with channel-wise | ||
| ones: ``g`` and ``beta`` carry one value per query/key channel and ``w`` one | ||
| value per value channel. The cuDNN frontend serves GDN-2 on Blackwell |
There was a problem hiding this comment.
Incorrectly clubs 107 as Blackwell ?
| if not torch.cuda.is_available(): | ||
| return False | ||
| major, minor = torch.cuda.get_device_capability() | ||
| return (major, minor) in {(10, 0), (10, 1), (10, 2), (10, 3), (10, 7)} |
|
|
||
|
|
||
| _GDN2_OP_AVAILABLE = _gdn2_op_available() | ||
| if os.getenv("NVTE_GDN2_TEST_REQUIRED", "0") == "1" and not _GDN2_OP_AVAILABLE: |
There was a problem hiding this comment.
I'm unsure, but, could required mode also fail when the GPU architecture is unsupported? Currently it checks only whether the op/runtime imports; requires_gdn2 can then skip every numerical test on the wrong GPU, allowing the required CI command to pass without exercising GDN2. MAybe use a shared condition such as _GDN2_SUPPORTED = _GDN2_OP_AVAILABLE and _gdn2_supported_arch() for both the required-mode failure and the skip marker.
There was a problem hiding this comment.
We run the CI with NVTE_GDN2_TEST_REQUIRED=1 and the _GDN2_OP_AVAILABLE checks GDN support. Later, _gdn2_supported_arch skips this test on unsupported architectures. So we will only run this test on supported hardware and skip otherwise.
|
/te-ci pytorch L0 |
| value per value channel. The cuDNN frontend serves GDN-2 on Blackwell+ | ||
| (SM100/SM103/SM107) only. |
There was a problem hiding this comment.
Architecture Support Is Overstated
Describing support as “Blackwell+” implies compatibility with architectures beyond Blackwell, but the same sentence limits the available engine to SM100, SM103, and SM107. This may lead users of later architectures to expect GDN2 to work when that support is not documented.
| value per value channel. The cuDNN frontend serves GDN-2 on Blackwell+ | |
| (SM100/SM103/SM107) only. | |
| value per value channel. The cuDNN frontend serves GDN-2 on Blackwell | |
| (SM100/SM103/SM107) only. |
Note: If this suggestion doesn't match your team's coding style, reply to this and let me know. I'll remember it for next time!
Description
Adds support for GDN2 variant and redesign the linear attention API.
Type of change
Changes
cudnn-frontend(v1.29.0required).Checklist: