|
19 | 19 | # MAE: https://github.com/facebookresearch/mae/blob/main/models_mae.py |
20 | 20 | # -------------------------------------------------------- |
21 | 21 |
|
| 22 | +import logging |
22 | 23 | import math |
23 | 24 | from typing import List, Optional, Tuple |
24 | 25 | from dataclasses import dataclass |
|
31 | 32 |
|
32 | 33 | from library import custom_offloading_utils |
33 | 34 |
|
| 35 | +_logger = logging.getLogger(__name__) |
| 36 | + |
34 | 37 | try: |
35 | 38 | from flash_attn import flash_attn_varlen_func |
36 | 39 | from flash_attn.bert_padding import index_first_axis, pad_input, unpad_input # noqa |
37 | 40 | except ImportError: |
38 | 41 | # flash_attn may not be available but it is not required |
39 | 42 | pass |
40 | 43 |
|
| 44 | +# Verify flash_attn GPU compatibility: requires Ampere (sm_80) or newer. |
| 45 | +if "flash_attn_varlen_func" in dir(): |
| 46 | + try: |
| 47 | + if torch.cuda.is_available(): |
| 48 | + _capability = torch.cuda.get_device_capability() |
| 49 | + if _capability < (8, 0): |
| 50 | + _logger.warning( |
| 51 | + "flash_attn is installed but requires Ampere GPU (sm_80) or newer. " |
| 52 | + f"Current GPU compute capability: {_capability[0]}.{_capability[1]}. " |
| 53 | + "Disabling flash_attn for lumina models." |
| 54 | + ) |
| 55 | + flash_attn_varlen_func = None |
| 56 | + except Exception: |
| 57 | + _logger.debug("Could not determine GPU capability for flash_attn compatibility check") |
| 58 | + |
41 | 59 | try: |
42 | 60 | from sageattention import sageattn |
43 | 61 | except ImportError: |
@@ -317,6 +335,21 @@ def __init__( |
317 | 335 | else: |
318 | 336 | self.q_norm = self.k_norm = nn.Identity() |
319 | 337 |
|
| 338 | + # Disable flash_attn if not importable or GPU doesn't support it (requires Ampere+) |
| 339 | + # flash_attn_varlen_func is a module-level name; access it via the global scope. |
| 340 | + # Three states: (1) import failed -> NameError, (2) GPU unsupported -> None, (3) available -> function |
| 341 | + try: |
| 342 | + _flash_available = flash_attn_varlen_func is not None |
| 343 | + except NameError: |
| 344 | + _flash_available = False |
| 345 | + |
| 346 | + if use_flash_attn and not _flash_available: |
| 347 | + _logger.warning( |
| 348 | + "Flash attention requested but not available (not installed or GPU does not support it). " |
| 349 | + "Falling back to standard attention." |
| 350 | + ) |
| 351 | + use_flash_attn = False |
| 352 | + |
320 | 353 | self.use_flash_attn = use_flash_attn |
321 | 354 | self.use_sage_attn = use_sage_attn |
322 | 355 |
|
@@ -544,9 +577,10 @@ def flash_attn( |
544 | 577 | # end var_len_flash_attn |
545 | 578 |
|
546 | 579 | return output |
547 | | - except NameError as e: |
| 580 | + except (NameError, TypeError) as e: |
548 | 581 | raise RuntimeError( |
549 | | - f"Could not load flash attention. Please install flash_attn. / フラッシュアテンションを読み込めませんでした。flash_attn をインストールしてください。 / {e}" |
| 582 | + f"Could not load flash attention. Please install flash_attn (requires Ampere GPU or newer). / " |
| 583 | + f"フラッシュアテンションを読み込めませんでした。flash_attn をインストールしてください(Ampere GPU以降が必要です)。 / {e}" |
550 | 584 | ) |
551 | 585 |
|
552 | 586 |
|
|
0 commit comments