mirror of
https://github.com/vladmandic/automatic
synced 2026-09-20 01:31:13 +02:00
lora direct on-demand apply/unapply
Signed-off-by: Vladimir Mandic <mandic00@live.com>
This commit is contained in:
+16
-14
@@ -1,24 +1,26 @@
|
||||
# Change Log for SD.Next
|
||||
|
||||
## Update for 2024-12-28
|
||||
|
||||
### Post release
|
||||
## Update for 2024-12-29
|
||||
|
||||
- **LoRA**:
|
||||
- **Sana** support
|
||||
- quantized models support
|
||||
- fuse support with on-demand apply/unapply
|
||||
- add legacy option in *settings -> networks*
|
||||
- **HunyuanVideo** optimizations: full offload, quantization and tiling support
|
||||
- **LTXVideo** optimizations: full offload, quantization and tiling support
|
||||
- VAE tiling granular options in *settings -> variable auto encoder*
|
||||
- LoRA loader add legacy option in *settings -> networks*
|
||||
- LoRA loader better apply for quantized models
|
||||
- Live preview: add sigma calculation, thanks @Disty0
|
||||
- UI: live preview add sigma calculation, thanks @Disty0
|
||||
- UI: CSS optimizations when log view is disabled
|
||||
- Sampler options: add flow shift and separate dynamic thresholding from dynamic shifting
|
||||
- Fix: do not show disabled networks
|
||||
- Fix: live preview image sizes in modern and standard UI
|
||||
- Fix: image width/height calculation when doing img2img
|
||||
- Fix: flux pipeline switches: txt/img/inpaint
|
||||
- Fix: interrogate caption with T5
|
||||
- Fix: on-the-fly quantization using TorchAO
|
||||
- Fix: remove concurrent preview requests
|
||||
- Samplers: add flow shift options and separate dynamic thresholding from dynamic shifting
|
||||
- **Fixes**
|
||||
- do not show disabled networks
|
||||
- live preview image sizes in modern and standard UI
|
||||
- image width/height calculation when doing img2img
|
||||
- flux pipeline switches: txt/img/inpaint
|
||||
- interrogate caption with T5
|
||||
- on-the-fly quantization using TorchAO
|
||||
- remove concurrent preview requests
|
||||
|
||||
## Update for 2024-12-24
|
||||
|
||||
|
||||
@@ -516,6 +516,7 @@ def randn_without_seed(shape):
|
||||
return torch.randn(shape, device=cpu).to(device)
|
||||
return torch.randn(shape, device=device)
|
||||
|
||||
|
||||
def autocast(disable=False):
|
||||
if disable or dtype == torch.float32:
|
||||
return contextlib.nullcontext()
|
||||
|
||||
@@ -80,14 +80,14 @@ def activate(p, extra_network_data=None, step=0, include=[], exclude=[]):
|
||||
if p.disable_extra_networks:
|
||||
return
|
||||
extra_network_data = extra_network_data or p.network_data
|
||||
if extra_network_data is None or len(extra_network_data) == 0:
|
||||
return
|
||||
# if extra_network_data is None or len(extra_network_data) == 0:
|
||||
# return
|
||||
stepwise = False
|
||||
for extra_network_args in extra_network_data.values():
|
||||
stepwise = stepwise or is_stepwise(extra_network_args)
|
||||
functional = shared.opts.lora_functional
|
||||
if shared.opts.lora_force_diffusers and stepwise:
|
||||
shared.log.warning("Composable LoRA not compatible with 'lora_force_diffusers'")
|
||||
shared.log.warning("Load network: type=LoRA method=composable loader=diffusers not compatible")
|
||||
stepwise = False
|
||||
shared.opts.data['lora_functional'] = stepwise or functional
|
||||
|
||||
@@ -110,7 +110,12 @@ def activate(p, extra_network_data=None, step=0, include=[], exclude=[]):
|
||||
if args is not None:
|
||||
continue
|
||||
try:
|
||||
extra_network.activate(p, [])
|
||||
# extra_network.activate(p, [])
|
||||
signature = list(inspect.signature(extra_network.activate).parameters)
|
||||
if 'include' in signature and 'exclude' in signature:
|
||||
extra_network.activate(p, [], include=include, exclude=exclude)
|
||||
else:
|
||||
extra_network.activate(p, [])
|
||||
except Exception as e:
|
||||
errors.display(e, f"Activating network: type={extra_network_name}")
|
||||
|
||||
@@ -125,8 +130,8 @@ def deactivate(p, extra_network_data=None):
|
||||
if p.disable_extra_networks:
|
||||
return
|
||||
extra_network_data = extra_network_data or p.network_data
|
||||
if extra_network_data is None or len(extra_network_data) == 0:
|
||||
return
|
||||
# if extra_network_data is None or len(extra_network_data) == 0:
|
||||
# return
|
||||
for extra_network_name in extra_network_data:
|
||||
extra_network = extra_network_registry.get(extra_network_name, None)
|
||||
if extra_network is None:
|
||||
|
||||
@@ -1,11 +1,16 @@
|
||||
from typing import List
|
||||
import os
|
||||
import re
|
||||
import numpy as np
|
||||
import modules.lora.networks as networks
|
||||
from modules.lora import networks
|
||||
from modules import extra_networks, shared
|
||||
|
||||
|
||||
# from https://github.com/cheald/sd-webui-loractl/blob/master/loractl/lib/utils.py
|
||||
def get_stepwise(param, step, steps):
|
||||
debug = os.environ.get('SD_SCRIPT_DEBUG', None) is not None
|
||||
debug_log = shared.log.trace if debug else lambda *args, **kwargs: None
|
||||
|
||||
|
||||
def get_stepwise(param, step, steps): # from https://github.com/cheald/sd-webui-loractl/blob/master/loractl/lib/utils.py
|
||||
def sorted_positions(raw_steps):
|
||||
steps = [[float(s.strip()) for s in re.split("[@~]", x)]
|
||||
for x in re.split("[,;]", str(raw_steps))]
|
||||
@@ -46,7 +51,8 @@ def prompt(p):
|
||||
if len(all_tags) > 0:
|
||||
all_tags = list(set(all_tags))
|
||||
all_tags = [t for t in all_tags if t not in p.prompt]
|
||||
shared.log.debug(f"Load network: type=LoRA tags={all_tags} max={shared.opts.lora_apply_tags} apply")
|
||||
if len(all_tags) > 0:
|
||||
shared.log.debug(f"Load network: type=LoRA tags={all_tags} max={shared.opts.lora_apply_tags} apply")
|
||||
all_tags = ', '.join(all_tags)
|
||||
p.extra_generation_params["LoRA tags"] = all_tags
|
||||
if '_tags_' in p.prompt:
|
||||
@@ -114,26 +120,58 @@ class ExtraNetworkLora(extra_networks.ExtraNetwork):
|
||||
self.model = None
|
||||
self.errors = {}
|
||||
|
||||
def signature(self, names: List[str], te_multipliers: List, unet_multipliers: List):
|
||||
return [f'{name}:{te}:{unet}' for name, te, unet in zip(names, te_multipliers, unet_multipliers)]
|
||||
|
||||
def changed(self, requested: List[str], include: List[str], exclude: List[str]):
|
||||
sd_model = getattr(shared.sd_model, "pipe", shared.sd_model)
|
||||
if not hasattr(sd_model, 'loaded_loras'):
|
||||
sd_model.loaded_loras = {}
|
||||
key = f'{','.join(include)}:{','.join(exclude)}'
|
||||
loaded = sd_model.loaded_loras.get(key, [])
|
||||
# shared.log.trace(f'Load network: type=LoRA key="{key}" requested={requested} loaded={loaded}')
|
||||
if len(requested) != len(loaded):
|
||||
sd_model.loaded_loras[key] = requested
|
||||
return True
|
||||
for r, l in zip(requested, loaded):
|
||||
if r != l:
|
||||
sd_model.loaded_loras[key] = requested
|
||||
return True
|
||||
return False
|
||||
|
||||
def activate(self, p, params_list, step=0, include=[], exclude=[]):
|
||||
self.errors.clear()
|
||||
if self.active:
|
||||
if self.model != shared.opts.sd_model_checkpoint: # reset if model changed
|
||||
self.active = False
|
||||
if len(params_list) > 0 and not self.active: # activate patches once
|
||||
# shared.log.debug(f'Activate network: type=LoRA model="{shared.opts.sd_model_checkpoint}"')
|
||||
self.active = True
|
||||
self.model = shared.opts.sd_model_checkpoint
|
||||
if 'text_encoder' in include:
|
||||
networks.timer.clear(complete=True)
|
||||
names, te_multipliers, unet_multipliers, dyn_dims = parse(p, params_list, step)
|
||||
requested = self.signature(names, te_multipliers, unet_multipliers)
|
||||
|
||||
if debug:
|
||||
import sys
|
||||
fn = f'{sys._getframe(2).f_code.co_name}:{sys._getframe(1).f_code.co_name}' # pylint: disable=protected-access
|
||||
debug_log(f'Load network: type=LoRA include={include} exclude={exclude} requested={requested} fn={fn}')
|
||||
|
||||
networks.network_load(names, te_multipliers, unet_multipliers, dyn_dims) # load
|
||||
networks.network_activate(include, exclude)
|
||||
has_changed = self.changed(requested, include, exclude)
|
||||
if has_changed:
|
||||
networks.network_deactivate(include, exclude)
|
||||
networks.network_activate(include, exclude)
|
||||
debug_log(f'Load network: type=LoRA previous={[n.name for n in networks.previously_loaded_networks]} current={[n.name for n in networks.loaded_networks]} changed')
|
||||
|
||||
if len(networks.loaded_networks) > 0 and len(networks.applied_layers) > 0 and step == 0:
|
||||
infotext(p)
|
||||
prompt(p)
|
||||
shared.log.info(f'Load network: type=LoRA apply={[n.name for n in networks.loaded_networks]} mode={"fuse" if shared.opts.lora_fuse_diffusers else "backup"} te={te_multipliers} unet={unet_multipliers} time={networks.timer.summary}')
|
||||
if has_changed and len(include) == 0: # print only once
|
||||
shared.log.info(f'Load network: type=LoRA apply={[n.name for n in networks.loaded_networks]} mode={"fuse" if shared.opts.lora_fuse_diffusers else "backup"} te={te_multipliers} unet={unet_multipliers} time={networks.timer.summary}')
|
||||
|
||||
def deactivate(self, p):
|
||||
if shared.native:
|
||||
networks.previously_loaded_networks = networks.loaded_networks.copy()
|
||||
debug_log(f'Load network: type=LoRA active={[n.name for n in networks.previously_loaded_networks]} deactivate')
|
||||
if shared.native and len(networks.diffuser_loaded) > 0:
|
||||
if hasattr(shared.sd_model, "unload_lora_weights") and hasattr(shared.sd_model, "text_encoder"):
|
||||
if not (shared.compiled_model_state is not None and shared.compiled_model_state.is_compiled is True):
|
||||
@@ -143,7 +181,6 @@ class ExtraNetworkLora(extra_networks.ExtraNetwork):
|
||||
shared.sd_model.unload_lora_weights() # fails for non-CLIP models
|
||||
except Exception:
|
||||
pass
|
||||
networks.network_deactivate()
|
||||
if self.active and networks.debug:
|
||||
shared.log.debug(f"Network end: type=LoRA time={networks.timer.summary}")
|
||||
if self.errors:
|
||||
|
||||
+27
-17
@@ -19,6 +19,7 @@ extra_network_lora = ExtraNetworkLora()
|
||||
available_networks = {}
|
||||
available_network_aliases = {}
|
||||
loaded_networks: List[network.Network] = []
|
||||
previously_loaded_networks: List[network.Network] = []
|
||||
applied_layers: list[str] = []
|
||||
bnb = None
|
||||
lora_cache = {}
|
||||
@@ -286,7 +287,7 @@ def network_load(names, te_multipliers=None, unet_multipliers=None, dyn_dims=Non
|
||||
errors.display(e, 'LoRA')
|
||||
|
||||
if len(loaded_networks) > 0 and debug:
|
||||
shared.log.debug(f'Load network: type=LoRA loaded={len(loaded_networks)} cache={list(lora_cache)}')
|
||||
shared.log.debug(f'Load network: type=LoRA loaded={[n.name for n in loaded_networks]} cache={list(lora_cache)}')
|
||||
|
||||
if recompile_model:
|
||||
shared.log.info("Load network: type=LoRA recompiling model")
|
||||
@@ -362,7 +363,7 @@ def network_backup_weights(self: Union[torch.nn.Conv2d, torch.nn.Linear, torch.n
|
||||
return backup_size
|
||||
|
||||
|
||||
def network_calc_weights(self: Union[torch.nn.Conv2d, torch.nn.Linear, torch.nn.GroupNorm, torch.nn.LayerNorm, diffusers.models.lora.LoRACompatibleLinear, diffusers.models.lora.LoRACompatibleConv], network_layer_name: str):
|
||||
def network_calc_weights(self: Union[torch.nn.Conv2d, torch.nn.Linear, torch.nn.GroupNorm, torch.nn.LayerNorm, diffusers.models.lora.LoRACompatibleLinear, diffusers.models.lora.LoRACompatibleConv], network_layer_name: str, use_previous: bool = False):
|
||||
if shared.opts.diffusers_offload_mode == "none":
|
||||
try:
|
||||
self.to(devices.device)
|
||||
@@ -370,7 +371,8 @@ def network_calc_weights(self: Union[torch.nn.Conv2d, torch.nn.Linear, torch.nn.
|
||||
pass
|
||||
batch_updown = None
|
||||
batch_ex_bias = None
|
||||
for net in loaded_networks:
|
||||
loaded = loaded_networks if not use_previous else previously_loaded_networks
|
||||
for net in loaded:
|
||||
module = net.modules.get(network_layer_name, None)
|
||||
if module is None:
|
||||
continue
|
||||
@@ -495,22 +497,26 @@ def network_apply_weights(self: Union[torch.nn.Conv2d, torch.nn.Linear, torch.nn
|
||||
return self.weight.device, self.weight.dtype
|
||||
|
||||
|
||||
def network_deactivate():
|
||||
def network_deactivate(include=[], exclude=[]):
|
||||
if not shared.opts.lora_fuse_diffusers:
|
||||
return
|
||||
t0 = time.time()
|
||||
timer.clear()
|
||||
sd_model = getattr(shared.sd_model, "pipe", shared.sd_model) # wrapped model compatiblility
|
||||
if shared.opts.diffusers_offload_mode == "sequential":
|
||||
sd_models.disable_offload(sd_model)
|
||||
sd_models.move_model(sd_model, device=devices.cpu)
|
||||
modules = {}
|
||||
for component_name in ['text_encoder', 'text_encoder_2', 'unet', 'transformer']:
|
||||
component = getattr(sd_model, component_name, None)
|
||||
|
||||
components = include if len(include) > 0 else ['text_encoder', 'text_encoder_2', 'text_encoder_3', 'unet', 'transformer']
|
||||
components = [x for x in components if x not in exclude]
|
||||
active_components = []
|
||||
for name in components:
|
||||
component = getattr(sd_model, name, None)
|
||||
if component is not None and hasattr(component, 'named_modules'):
|
||||
modules[component_name] = list(component.named_modules())
|
||||
modules[name] = list(component.named_modules())
|
||||
active_components.append(name)
|
||||
total = sum(len(x) for x in modules.values())
|
||||
if len(loaded_networks) > 0:
|
||||
if len(previously_loaded_networks) > 0 and debug:
|
||||
pbar = rp.Progress(rp.TextColumn('[cyan]Network: type=LoRA action=deactivate'), rp.BarColumn(), rp.TaskProgressColumn(), rp.TimeRemainingColumn(), rp.TimeElapsedColumn(), rp.TextColumn('[cyan]{task.description}'), console=shared.console)
|
||||
task = pbar.add_task(description='', total=total)
|
||||
else:
|
||||
@@ -528,7 +534,7 @@ def network_deactivate():
|
||||
if task is not None:
|
||||
pbar.update(task, advance=1)
|
||||
continue
|
||||
batch_updown, batch_ex_bias = network_calc_weights(module, network_layer_name)
|
||||
batch_updown, batch_ex_bias = network_calc_weights(module, network_layer_name, use_previous=True)
|
||||
if shared.opts.lora_fuse_diffusers:
|
||||
weights_device, weights_dtype = network_apply_direct(module, batch_updown, batch_ex_bias, deactivate=True)
|
||||
else:
|
||||
@@ -540,11 +546,12 @@ def network_deactivate():
|
||||
del batch_updown, batch_ex_bias
|
||||
module.network_current_names = ()
|
||||
if task is not None:
|
||||
pbar.update(task, advance=1, description=f'networks={len(loaded_networks)} modules={len(modules)} deactivate={len(applied_layers)}')
|
||||
weights_devices, weights_dtypes = list(set([x for x in weights_devices if x is not None])), list(set([x for x in weights_dtypes if x is not None])) # noqa: C403 # pylint: disable=R1718
|
||||
pbar.update(task, advance=1, description=f'networks={len(previously_loaded_networks)} modules={active_components} layers={total} unapply={len(applied_layers)}')
|
||||
|
||||
timer.deactivate = time.time() - t0
|
||||
if debug and len(loaded_networks) > 0:
|
||||
shared.log.debug(f'Deactivate network: type=LoRA networks={len(loaded_networks)} modules={total} deactivate={len(applied_layers)} device={weights_devices} dtype={weights_dtypes} fuse={shared.opts.lora_fuse_diffusers} time={timer.summary}')
|
||||
if debug and len(previously_loaded_networks) > 0:
|
||||
weights_devices, weights_dtypes = list(set([x for x in weights_devices if x is not None])), list(set([x for x in weights_dtypes if x is not None])) # noqa: C403 # pylint: disable=R1718
|
||||
shared.log.debug(f'Deactivate network: type=LoRA networks={[n.name for n in previously_loaded_networks]} modules={active_components} layers={total} apply={len(applied_layers)} device={weights_devices} dtype={weights_dtypes} fuse={shared.opts.lora_fuse_diffusers} time={timer.summary}')
|
||||
modules.clear()
|
||||
if shared.opts.diffusers_offload_mode == "sequential":
|
||||
sd_models.set_diffuser_offload(sd_model, op="model")
|
||||
@@ -559,9 +566,11 @@ def network_activate(include=[], exclude=[]):
|
||||
modules = {}
|
||||
components = include if len(include) > 0 else ['text_encoder', 'text_encoder_2', 'text_encoder_3', 'unet', 'transformer']
|
||||
components = [x for x in components if x not in exclude]
|
||||
active_components = []
|
||||
for name in components:
|
||||
component = getattr(sd_model, name, None)
|
||||
if component is not None and hasattr(component, 'named_modules'):
|
||||
active_components.append(name)
|
||||
modules[name] = list(component.named_modules())
|
||||
total = sum(len(x) for x in modules.values())
|
||||
if len(loaded_networks) > 0:
|
||||
@@ -598,13 +607,14 @@ def network_activate(include=[], exclude=[]):
|
||||
del batch_updown, batch_ex_bias
|
||||
module.network_current_names = wanted_names
|
||||
if task is not None:
|
||||
pbar.update(task, advance=1, description=f'networks={len(loaded_networks)} modules={total} apply={len(applied_layers)} backup={backup_size}')
|
||||
pbar.update(task, advance=1, description=f'networks={len(loaded_networks)} modules={active_components} layers={total} apply={len(applied_layers)} backup={backup_size}')
|
||||
|
||||
if task is not None and len(applied_layers) == 0:
|
||||
pbar.remove_task(task) # hide progress bar for no action
|
||||
weights_devices, weights_dtypes = list(set([x for x in weights_devices if x is not None])), list(set([x for x in weights_dtypes if x is not None])) # noqa: C403 # pylint: disable=R1718
|
||||
timer.activate += time.time() - t0
|
||||
if debug and len(loaded_networks) > 0:
|
||||
shared.log.debug(f'Load network: type=LoRA networks={len(loaded_networks)} components={components} modules={total} apply={len(applied_layers)} device={weights_devices} dtype={weights_dtypes} backup={backup_size} fuse={shared.opts.lora_fuse_diffusers} time={timer.summary}')
|
||||
weights_devices, weights_dtypes = list(set([x for x in weights_devices if x is not None])), list(set([x for x in weights_dtypes if x is not None])) # noqa: C403 # pylint: disable=R1718
|
||||
shared.log.debug(f'Load network: type=LoRA networks={[n.name for n in loaded_networks]} modules={active_components} layers={total} apply={len(applied_layers)} device={weights_devices} dtype={weights_dtypes} backup={backup_size} fuse={shared.opts.lora_fuse_diffusers} time={timer.summary}')
|
||||
modules.clear()
|
||||
if shared.opts.diffusers_offload_mode == "sequential":
|
||||
sd_models.set_diffuser_offload(sd_model, op="model")
|
||||
|
||||
@@ -148,9 +148,10 @@ def load_quants(kwargs, repo_id, cache_dir):
|
||||
quant_args = model_quant.create_bnb_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_bnb(f'Load model: type=FLUX quant={quant_args}')
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=FLUX quant={quant_args}')
|
||||
if not quant_args:
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=FLUX quant={quant_args}')
|
||||
if not quant_args:
|
||||
return kwargs
|
||||
if 'transformer' not in kwargs and ('Model' in shared.opts.bnb_quantization or 'Model' in shared.opts.torchao_quantization):
|
||||
|
||||
@@ -11,9 +11,10 @@ def load_quants(kwargs, repo_id, cache_dir):
|
||||
quant_args = model_quant.create_bnb_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_bnb(f'Load model: type=Sana quant={quant_args}')
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=Sana quant={quant_args}')
|
||||
if not quant_args:
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=Sana quant={quant_args}')
|
||||
if not quant_args:
|
||||
return kwargs
|
||||
load_args = kwargs.copy()
|
||||
|
||||
@@ -56,9 +56,10 @@ def load_quants(kwargs, repo_id, cache_dir):
|
||||
quant_args = model_quant.create_bnb_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_bnb(f'Load model: type=SD3 quant={quant_args}')
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=SD3 quant={quant_args}')
|
||||
if not quant_args:
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=SD3 quant={quant_args}')
|
||||
if not quant_args:
|
||||
return kwargs
|
||||
if 'Model' in shared.opts.bnb_quantization and 'transformer' not in kwargs:
|
||||
|
||||
@@ -221,7 +221,10 @@ def set_pipeline_args(p, model, prompts: list, negative_prompts: list, prompts_2
|
||||
if 'img_guidance_scale' in possible and hasattr(p, 'image_cfg_scale'):
|
||||
args['img_guidance_scale'] = p.image_cfg_scale
|
||||
if 'generator' in possible:
|
||||
args['generator'] = get_generator(p)
|
||||
generator = get_generator(p)
|
||||
args['generator'] = generator
|
||||
else:
|
||||
generator = None
|
||||
if 'latents' in possible and getattr(p, "init_latent", None) is not None:
|
||||
if sd_models.get_diffusers_task(model) == sd_models.DiffusersTaskType.TEXT_2_IMAGE:
|
||||
args['latents'] = p.init_latent
|
||||
@@ -321,7 +324,8 @@ def set_pipeline_args(p, model, prompts: list, negative_prompts: list, prompts_2
|
||||
clean['prompt'] = len(clean['prompt'])
|
||||
if 'negative_prompt' in clean and clean['negative_prompt'] is not None:
|
||||
clean['negative_prompt'] = len(clean['negative_prompt'])
|
||||
clean.pop('generator', None)
|
||||
if generator is not None:
|
||||
clean['generator'] = f'{generator[0].device}:{[g.initial_seed() for g in generator]}'
|
||||
clean['parser'] = parser
|
||||
for k, v in clean.copy().items():
|
||||
if isinstance(v, torch.Tensor) or isinstance(v, np.ndarray):
|
||||
@@ -331,7 +335,7 @@ def set_pipeline_args(p, model, prompts: list, negative_prompts: list, prompts_2
|
||||
if not debug_enabled and k.endswith('_embeds'):
|
||||
del clean[k]
|
||||
clean['prompt'] = 'embeds'
|
||||
shared.log.debug(f'Diffuser pipeline: {model.__class__.__name__} task={sd_models.get_diffusers_task(model)} batch={p.iteration + 1}/{p.n_iter}x{p.batch_size} set={clean}')
|
||||
shared.log.info(f'{desc}: pipeline={model.__class__.__name__} task={sd_models.get_diffusers_task(model)} batch={p.iteration + 1}/{p.n_iter}x{p.batch_size} set={clean}')
|
||||
|
||||
if p.hdr_clamp or p.hdr_maximize or p.hdr_brightness != 0 or p.hdr_color != 0 or p.hdr_sharpen != 0:
|
||||
txt = 'HDR:'
|
||||
|
||||
@@ -57,7 +57,6 @@ def process_base(p: processing.StableDiffusionProcessing):
|
||||
use_denoise_start = not is_txt2img() and p.refiner_start > 0 and p.refiner_start < 1
|
||||
|
||||
shared.sd_model = update_pipeline(shared.sd_model, p)
|
||||
shared.log.info(f'Base: class={shared.sd_model.__class__.__name__}')
|
||||
update_sampler(p, shared.sd_model)
|
||||
timer.process.record('prepare')
|
||||
base_args = set_pipeline_args(
|
||||
@@ -90,7 +89,7 @@ def process_base(p: processing.StableDiffusionProcessing):
|
||||
sd_models.move_model(shared.sd_model.unet, devices.device)
|
||||
if hasattr(shared.sd_model, 'transformer'):
|
||||
sd_models.move_model(shared.sd_model.transformer, devices.device)
|
||||
extra_networks.activate(p, exclude=['text_encoder', 'text_encoder_2'])
|
||||
extra_networks.activate(p, exclude=['text_encoder', 'text_encoder_2', 'text_encoder_3'])
|
||||
hidiffusion.apply(p, shared.sd_model_type)
|
||||
# if 'image' in base_args:
|
||||
# base_args['image'] = set_latents(p)
|
||||
@@ -195,7 +194,6 @@ def process_hires(p: processing.StableDiffusionProcessing, output):
|
||||
if p.hr_force:
|
||||
shared.state.job_count = 2 * p.n_iter
|
||||
shared.sd_model = sd_models.set_diffuser_pipe(shared.sd_model, sd_models.DiffusersTaskType.IMAGE_2_IMAGE)
|
||||
shared.log.info(f'HiRes: class={shared.sd_model.__class__.__name__} sampler="{p.hr_sampler_name}"')
|
||||
if 'Upscale' in shared.sd_model.__class__.__name__ or 'Flux' in shared.sd_model.__class__.__name__:
|
||||
output.images = processing_vae.vae_decode(latents=output.images, model=shared.sd_model, full_quality=p.full_quality, output_type='pil', width=p.width, height=p.height)
|
||||
if p.is_control and hasattr(p, 'task_args') and p.task_args.get('image', None) is not None:
|
||||
@@ -294,7 +292,6 @@ def process_refine(p: processing.StableDiffusionProcessing, output):
|
||||
if p.task_args.get('image', None) is not None and output is not None: # replace input with output so it can be used by hires/refine
|
||||
# p.task_args['image'] = image
|
||||
p.init_images = [image]
|
||||
shared.log.info(f'Refiner: class={shared.sd_refiner.__class__.__name__}')
|
||||
update_sampler(p, shared.sd_refiner, second_pass=True)
|
||||
refiner_args = set_pipeline_args(
|
||||
p=p,
|
||||
|
||||
@@ -511,10 +511,9 @@ def get_generator(p):
|
||||
else:
|
||||
generator_device = devices.cpu if shared.opts.diffusers_generator_device == "CPU" else shared.device
|
||||
try:
|
||||
p.seeds = [seed if seed != -1 else get_fixed_seed(seed) for seed in p.seeds if seed]
|
||||
devices.randn(p.seeds[0])
|
||||
generator = [torch.Generator(generator_device).manual_seed(s) for s in p.seeds]
|
||||
seeds = [g.initial_seed() for g in generator]
|
||||
shared.log.debug(f'Torch generator: device={generator_device} seeds={seeds}')
|
||||
except Exception as e:
|
||||
shared.log.error(f'Torch generator: seeds={p.seeds} device={generator_device} {e}')
|
||||
generator = None
|
||||
|
||||
@@ -135,9 +135,9 @@ def full_vae_decode(latents, model):
|
||||
latents = latents + shift_factor
|
||||
|
||||
vae_name = os.path.splitext(os.path.basename(sd_vae.loaded_vae_file))[0] if sd_vae.loaded_vae_file is not None else "default"
|
||||
vae_stats = f'name="{vae_name}" dtype={model.vae.dtype} device={model.vae.device} upcast={upcast} slicing={getattr(model.vae, "use_slicing", None)} tiling={getattr(model.vae, "use_tiling", None)}'
|
||||
vae_stats = f'vae="{vae_name}" dtype={model.vae.dtype} device={model.vae.device} upcast={upcast} slicing={getattr(model.vae, "use_slicing", None)} tiling={getattr(model.vae, "use_tiling", None)}'
|
||||
latents_stats = f'shape={latents.shape} dtype={latents.dtype} device={latents.device}'
|
||||
stats = f'vae {vae_stats} latents {latents_stats}'
|
||||
stats = f'{vae_stats} latents {latents_stats}'
|
||||
|
||||
log_debug(f'VAE config: {model.vae.config}')
|
||||
try:
|
||||
@@ -165,7 +165,7 @@ def full_vae_decode(latents, model):
|
||||
t1 = time.time()
|
||||
if debug:
|
||||
log_debug(f'VAE memory: {shared.mem_mon.read()}')
|
||||
shared.log.debug(f'VAE decode: {stats} time={round(t1-t0, 3)}')
|
||||
shared.log.debug(f'Decode: {stats} time={round(t1-t0, 3)}')
|
||||
return decoded
|
||||
|
||||
|
||||
|
||||
@@ -510,7 +510,7 @@ def apply_balanced_offload(sd_model, exclude=[]):
|
||||
module = module.to(devices.cpu, non_blocking=True)
|
||||
used_gpu -= module_size
|
||||
if not cached:
|
||||
shared.log.debug(f'Offload: type=balanced module={module_name} cls={module.__class__.__name__} dtype={module.dtype} quant={getattr(module, "quantization_method", None)} params={offload_hook_instance.param_map[module_name]:.3f} size={offload_hook_instance.offload_map[module_name]:.3f}')
|
||||
shared.log.debug(f'Model module={module_name} type={module.__class__.__name__} dtype={module.dtype} quant={getattr(module, "quantization_method", None)} params={offload_hook_instance.param_map[module_name]:.3f} size={offload_hook_instance.offload_map[module_name]:.3f}')
|
||||
debug_move(f'Offload: type=balanced op={"move" if do_offload else "skip"} gpu={prev_gpu:.3f}:{used_gpu:.3f} perc={perc_gpu:.2f} ram={used_ram:.3f} current={module.device} dtype={module.dtype} quant={getattr(module, "quantization_method", None)} module={module.__class__.__name__} size={module_size:.3f}')
|
||||
except Exception as e:
|
||||
if 'out of memory' in str(e):
|
||||
@@ -544,7 +544,7 @@ def apply_balanced_offload(sd_model, exclude=[]):
|
||||
fn = f'{sys._getframe(2).f_code.co_name}:{sys._getframe(1).f_code.co_name}' # pylint: disable=protected-access
|
||||
debug_move(f'Apply offload: time={t:.2f} type=balanced fn={fn}')
|
||||
if not cached:
|
||||
shared.log.info(f'Offload: type=balanced op=apply class={sd_model.__class__.__name__} modules={len(offload_hook_instance.offload_map)} size={offload_hook_instance.model_size():.3f}')
|
||||
shared.log.info(f'Model class={sd_model.__class__.__name__} modules={len(offload_hook_instance.offload_map)} size={offload_hook_instance.model_size():.3f}')
|
||||
return sd_model
|
||||
|
||||
|
||||
|
||||
@@ -61,7 +61,7 @@ def create_sampler(name, model):
|
||||
model.prior_pipe.scheduler = copy.deepcopy(model.default_scheduler)
|
||||
model.prior_pipe.scheduler.config.clip_sample = False
|
||||
config = {k: v for k, v in model.scheduler.config.items() if not k.startswith('_')}
|
||||
shared.log.debug(f'Sampler: sampler=default class={current}: {config}')
|
||||
shared.log.debug(f'Sampler: default class={current}: {config}')
|
||||
if "flow" in model.scheduler.__class__.__name__.lower():
|
||||
shared.state.prediction_type = "flow_prediction"
|
||||
elif hasattr(model.scheduler, "config") and hasattr(model.scheduler.config, "prediction_type"):
|
||||
@@ -77,7 +77,7 @@ def create_sampler(name, model):
|
||||
sampler.config = config
|
||||
sampler.name = name
|
||||
sampler.initialize(p=None)
|
||||
shared.log.debug(f'Sampler: sampler="{name}" config={config.options}')
|
||||
shared.log.debug(f'Sampler: "{name}" config={config.options}')
|
||||
return sampler
|
||||
elif shared.native:
|
||||
FlowModels = ['Flux', 'StableDiffusion3', 'Lumina', 'AuraFlow', 'Sana', 'HunyuanVideoPipeline']
|
||||
@@ -103,7 +103,7 @@ def create_sampler(name, model):
|
||||
elif hasattr(model.scheduler, "config") and hasattr(model.scheduler.config, "prediction_type"):
|
||||
shared.state.prediction_type = model.scheduler.config.prediction_type
|
||||
clean_config = {k: v for k, v in sampler.config.items() if v is not None and v is not False}
|
||||
shared.log.debug(f'Sampler: sampler="{sampler.name}" class="{model.scheduler.__class__.__name__} config={clean_config}')
|
||||
shared.log.debug(f'Sampler: "{sampler.name}" class={model.scheduler.__class__.__name__} config={clean_config}')
|
||||
return sampler.sampler
|
||||
else:
|
||||
return None
|
||||
|
||||
+3
-3
@@ -103,9 +103,9 @@ def apply_wildcards_to_prompt(prompt, all_wildcards, seed=-1, silent=False):
|
||||
prompt, replaced_file, not_found = apply_file_wildcards(prompt, [], [], recursion=0, seed=seed)
|
||||
t2 = time.time()
|
||||
if replaced and not silent:
|
||||
shared.log.debug(f'Wildcards applied: {replaced} path="{shared.opts.wildcards_dir}" type=style time={t1-t0:.2f}')
|
||||
shared.log.debug(f'Apply wildcards: {replaced} path="{shared.opts.wildcards_dir}" type=style time={t1-t0:.2f}')
|
||||
if (len(replaced_file) > 0 or len(not_found) > 0) and not silent:
|
||||
shared.log.debug(f'Wildcards applied: {replaced_file} missing: {not_found} path="{shared.opts.wildcards_dir}" type=file time={t2-t2:.2f} ')
|
||||
shared.log.debug(f'Apply wildcards: {replaced_file} missing: {not_found} path="{shared.opts.wildcards_dir}" type=file time={t2-t2:.2f} ')
|
||||
if old_state is not None:
|
||||
random.setstate(old_state)
|
||||
return prompt
|
||||
@@ -158,7 +158,7 @@ def apply_styles_to_extra(p, style: Style):
|
||||
fields.append(f'{k}={v}')
|
||||
else:
|
||||
skipped.append(f'{k}={v}')
|
||||
shared.log.debug(f'Applying style: name="{style.name}" extra={fields} skipped={skipped} reference={True if reference_style else False}')
|
||||
shared.log.debug(f'Apply style: name="{style.name}" extra={fields} skipped={skipped} reference={True if reference_style else False}')
|
||||
|
||||
|
||||
class StyleDatabase:
|
||||
|
||||
@@ -104,9 +104,10 @@ class Script(scripts.Script):
|
||||
quant_args = model_quant.create_bnb_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_bnb(f'Load model: type=HunyuanVideo quant={quant_args}')
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=HunyuanVideo quant={quant_args}')
|
||||
if not quant_args:
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=HunyuanVideo quant={quant_args}')
|
||||
transformer = diffusers.HunyuanVideoTransformer3DModel.from_pretrained(
|
||||
repo_id,
|
||||
subfolder="transformer",
|
||||
|
||||
+4
-3
@@ -19,9 +19,10 @@ def load_quants(kwargs, repo_id):
|
||||
quant_args = model_quant.create_bnb_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_bnb(f'Load model: type=LTXVideo quant={quant_args}')
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=LTXVideo quant={quant_args}')
|
||||
if not quant_args:
|
||||
quant_args = model_quant.create_ao_config(quant_args)
|
||||
if quant_args:
|
||||
model_quant.load_torchao(f'Load model: type=LTXVideo quant={quant_args}')
|
||||
if not quant_args:
|
||||
return kwargs
|
||||
model_quant.load_bnb(f'Load model: type=LTX quant={quant_args}')
|
||||
|
||||
Reference in New Issue
Block a user