Skip to content

Commit 98419df

Browse files
committed
Add different MBConv norm configs
1 parent 697554b commit 98419df

1 file changed

Lines changed: 53 additions & 5 deletions

File tree

timm/models/cpubone.py

Lines changed: 53 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,14 @@
2323
__all__ = ['CPUBone']
2424

2525

26+
_LOCAL_MBCONV_NORM_MODES = {
27+
# mode: (expand, depthwise, project)
28+
'proj': (False, False, True),
29+
'depth_proj': (False, True, True),
30+
'all': (True, True, True),
31+
}
32+
33+
2634
def remap_legacy_state_dict(state_dict: Dict[str, torch.Tensor]) -> Dict[str, torch.Tensor]:
2735
"""Remap keys from original CPUBone checkpoints to the current model layout."""
2836
remapped = {}
@@ -369,8 +377,14 @@ def __init__(
369377
small_kernels: bool = False,
370378
attn_upsample: str = 'transpose',
371379
drop_path: float = 0.,
380+
local_mbconv_norm: str = 'proj',
372381
):
373382
super().__init__()
383+
if local_mbconv_norm not in _LOCAL_MBCONV_NORM_MODES:
384+
raise ValueError(
385+
f'Invalid local_mbconv_norm={local_mbconv_norm!r}; '
386+
f'expected one of {tuple(_LOCAL_MBCONV_NORM_MODES)}.'
387+
)
374388
att_kernel = 5 if att_stride > 1 else 3
375389

376390
block = ConvAttention(
@@ -405,14 +419,18 @@ def __init__(
405419
act_layer=(act_layer, None),
406420
)
407421
else:
422+
norm_mask = _LOCAL_MBCONV_NORM_MODES[local_mbconv_norm]
423+
local_norms = tuple(norm_layer if enabled else None for enabled in norm_mask)
424+
# A convolution bias is redundant whenever normalization follows it.
425+
local_biases = tuple(not enabled for enabled in norm_mask)
408426
local_module = MBConv(
409427
in_channels=in_channels,
410428
out_channels=in_channels,
411429
expand_ratio=expand_ratio,
412430
expand_groups=expand_groups,
413-
use_bias=(True, True, False),
431+
use_bias=local_biases,
414432
kernel_size=2 if small_kernels else 3,
415-
norm_layer=(None, None, norm_layer),
433+
norm_layer=local_norms,
416434
act_layer=(act_layer, act_layer, None),
417435
)
418436

@@ -496,6 +514,7 @@ def __init__(
496514
expand_groups: int = 1,
497515
small_kernels: bool = False,
498516
attn_upsample: str = 'transpose',
517+
local_mbconv_norm: str = 'proj',
499518
) -> None:
500519
"""
501520
Args:
@@ -522,6 +541,9 @@ def __init__(
522541
local conv branch).
523542
attn_upsample: Upsampling mode after strided attention, 'transpose' (learned
524543
ConvTranspose2d) or 'nearest' (parameter-free nearest-neighbor).
544+
local_mbconv_norm: Normalization placement in unfused CPUBoneBlock local MBConvs;
545+
one of 'proj', 'depth_proj', or 'all'. Convolution biases are disabled wherever
546+
normalization is enabled.
525547
526548
The ablation flags of the original implementation map onto these args as follows:
527549
`fastit=True` → `fused_conv=True, fused_downsample=True, attn_mlp_ratio=4` (adding
@@ -533,6 +555,11 @@ def __init__(
533555
super().__init__()
534556
assert global_pool in ("", "avg"), "CPUBone only supports average or disabled pooling"
535557
assert attn_upsample in ('transpose', 'nearest')
558+
if local_mbconv_norm not in _LOCAL_MBCONV_NORM_MODES:
559+
raise ValueError(
560+
f'Invalid local_mbconv_norm={local_mbconv_norm!r}; '
561+
f'expected one of {tuple(_LOCAL_MBCONV_NORM_MODES)}.'
562+
)
536563
num_stages = len(width_list) - 1
537564
if downsample_expand_ratios is None:
538565
downsample_expand_ratios = (expand_ratio,) * num_stages
@@ -554,6 +581,7 @@ def __init__(
554581
self.expand_groups = expand_groups
555582
self.small_kernels = small_kernels
556583
self.attn_upsample = attn_upsample
584+
self.local_mbconv_norm = local_mbconv_norm
557585

558586
# stochastic depth: linear ramp of drop rates across all blocks (downsample blocks have no
559587
# shortcut and ignore theirs)
@@ -681,6 +709,7 @@ def _build_attention_stage(
681709
small_kernels=self.small_kernels,
682710
attn_upsample=self.attn_upsample,
683711
drop_path=dpr[i],
712+
local_mbconv_norm=self.local_mbconv_norm,
684713
)
685714
)
686715
return blocks, in_channels
@@ -842,6 +871,8 @@ def _cfg(url: str = "", **kwargs: Any) -> Dict[str, Any]:
842871
"cpubone_nano.in1k": _cfg(hf_hub_id="Kaeruu/CPUBone", hf_hub_filename="cpubone_nano.safetensors"),
843872
"cpubone_b0.in1k": _cfg(hf_hub_id="Kaeruu/CPUBone", hf_hub_filename="cpubone_b0.safetensors"),
844873
"cpubone_b1.in1k": _cfg(hf_hub_id="Kaeruu/CPUBone", hf_hub_filename="cpubone_b1.safetensors"),
874+
"cpubone_b1_dwnorm.untrained": _cfg(),
875+
"cpubone_b1_allnorm.untrained": _cfg(),
845876
"cpubone_b2.in1k": _cfg(hf_hub_id="Kaeruu/CPUBone", hf_hub_filename="cpubone_b2.safetensors"),
846877
"cpubone_b3.in1k": _cfg(hf_hub_id="Kaeruu/CPUBone", hf_hub_filename="cpubone_b3.safetensors"),
847878
})
@@ -894,9 +925,8 @@ def cpubone_b0(pretrained: bool = False, **kwargs: Any) -> CPUBone:
894925
return _create_cpubone("cpubone_b0", pretrained=pretrained, **dict(model_args, **kwargs))
895926

896927

897-
@register_model
898-
def cpubone_b1(pretrained: bool = False, **kwargs: Any) -> CPUBone:
899-
model_args = dict(
928+
def _cpubone_b1_args(local_mbconv_norm: str = 'proj') -> Dict[str, Any]:
929+
return dict(
900930
width_list=[16, 32, 64, 128, 256],
901931
depth_list=[0, 1, 1, 5, 5],
902932
fused_conv=True,
@@ -906,10 +936,28 @@ def cpubone_b1(pretrained: bool = False, **kwargs: Any) -> CPUBone:
906936
expand_groups=2,
907937
small_kernels=True,
908938
attn_upsample="nearest",
939+
local_mbconv_norm=local_mbconv_norm,
909940
)
941+
942+
943+
@register_model
944+
def cpubone_b1(pretrained: bool = False, **kwargs: Any) -> CPUBone:
945+
model_args = _cpubone_b1_args()
910946
return _create_cpubone("cpubone_b1", pretrained=pretrained, **dict(model_args, **kwargs))
911947

912948

949+
@register_model
950+
def cpubone_b1_dwnorm(pretrained: bool = False, **kwargs: Any) -> CPUBone:
951+
model_args = _cpubone_b1_args(local_mbconv_norm='depth_proj')
952+
return _create_cpubone("cpubone_b1_dwnorm", pretrained=pretrained, **dict(model_args, **kwargs))
953+
954+
955+
@register_model
956+
def cpubone_b1_allnorm(pretrained: bool = False, **kwargs: Any) -> CPUBone:
957+
model_args = _cpubone_b1_args(local_mbconv_norm='all')
958+
return _create_cpubone("cpubone_b1_allnorm", pretrained=pretrained, **dict(model_args, **kwargs))
959+
960+
913961
@register_model
914962
def cpubone_b2(pretrained: bool = False, **kwargs: Any) -> CPUBone:
915963
model_args = dict(

0 commit comments

Comments
 (0)