# Tuning Models This tutorial explains how to improve model inference performance using the Tuner API. It explains step-by-step how to tune a model to reduce latency on a Snapdragon device. Note If you want a shorter version, you can find it in the QAIRT SDK at: > > > - `examples/QAIRT/python/tuning_tutorial.py` Tutorial setup: - Framework: PyTorch - Host OS: Linux (x86\_64) - Model: [ResNet18](https://docs.pytorch.org/vision/main/models/generated/torchvision.models.resnet18.html) - Target Device: Snapdragon Android Device SM8750 - Processor: Qualcomm NPU - Backend: HTP Tip This tutorial creates temporary files. To change where these files are saved, set the *QAIRT\_TMP\_DIR* environment variable. ## Step 1: Setup First, import the libraries and create a directory for output files. import json import os from pathlib import Path import numpy as np import torch from torchvision import models import qairt from qairt import CompileConfig, Device, DevicePlatformType ENABLE_QAIRT_VISUALIZER = False tuned_artifacts_dir = Path("./tuned_artifacts") tuned_artifacts_dir.mkdir(exist_ok=True) Copy to clipboard ## Step 2: Get a ResNet model Load a pre-trained ResNet18 model and export it to ONNX format. resnet_model = models.resnet18(weights=models.ResNet18_Weights.DEFAULT) resnet_model.eval() dummy_input = torch.randn(1, 3, 32, 32) resnet_model_path = "resnet18.onnx" torch.onnx.export( resnet_model, dummy_input, resnet_model_path, input_names=["input"], ) Copy to clipboard ## Step 3: Connect to an Android device Set up your Android device using environment variables. android_serial = os.getenv("ANDROID_SERIAL") android_hostname = os.getenv("ANDROID_HOSTNAME") android_device = None if android_serial: print(f"INFO: ANDROID_SERIAL : {android_serial} was set. Enabling tutorial for Android") device_id = f"{android_serial}@{android_hostname}" if android_hostname else android_serial android_device = Device(identifier=device_id, type=DevicePlatformType.ANDROID) if not android_device: print("INFO: ANDROID_SERIAL was not set. Exiting") exit(1) Copy to clipboard ## Step 4: Create the first QHAS report Convert and compile the model, then run it and generate a QHAS report. resnet_model_converted = qairt.convert( resnet_model_path, input_tensor_config=[dict(name="input", shape=(1, 3, 32, 32))] ) resnet_model_converted.save(tuned_artifacts_dir / "resnet_model_converted.dlc") compile_config = CompileConfig(backend="HTP", soc_details=f"chipset:{android_device.get_chipset()}") with qairt.Profiler(context=dict(level="detailed", option="optrace")) as pf: compiled_model = qairt.compile(resnet_model_converted, config=compile_config) input_array = np.random.randn(1, 3, 32, 32).astype(np.float32) _ = compiled_model(inputs=input_array, device=android_device) op_trace_report = pf.generate_report() qhas_report_path = tuned_artifacts_dir / "qhas_report.json" qhas_report = op_trace_report.summary.dump(qhas_report_path) Copy to clipboard Note Sometimes, get\_chipset may not return the correct value. You can get the chipset using this command on your host: adb -H ${ANDROID_HOSTNAME} -s $ANDROID_SERIAL shell getprop ro.soc.model def print_or_view_qhas(report_path): if ENABLE_QAIRT_VISUALIZER: from qairt_visualizer import view view(reports=str(qhas_report_path)) else: qhas_report = json.load(open(report_path)) data = qhas_report["data"]["htp_overall_summary"]["data"][0] qhas_summary = {} for key, value in data.items(): if key != "htp_resources": qhas_summary[key] = value print("QHAS Summary: \n") print(json.dumps(qhas_summary, indent=4)) print_or_view_qhas(qhas_report_path) Copy to clipboard The report shows *total dram* (DDR bandwidth in bytes) and *time\_us* (latency in microseconds). The next section introduces the Tuner API, which can help reduce bandwidth and latency. The Tuner API tries different options to find the fastest model. It compiles and runs the model several times to find the best result. ## Step 5: Tune the model Use the Tuner API to reduce latency (*time\_us*). The code below shows how to use it. from qairt.api.compiler.backends.common import tuner input_array = np.random.randn(1, 3, 32, 32).astype(np.float32) best_compiled_model, report = tuner.optimize( resnet_model_converted, criteria="latency", compile_args=dict(config=compile_config), execution_args=dict(inputs=input_array, device=android_device), ) Copy to clipboard Note that compile\_args and execution\_args are dictionaries passed to qairt.compile and CompiledModel.__call__. The tuner simply forwards these arguments to the respective APIs. To illustrate the connection, an example call to each API is shown below: # Compile the model with the same arguments passed to the tuner compiled_model = qairt.compile( resnet_model_converted, config=compile_config, ) # Run the compiled model with the same arguments passed to the tuner outputs = compiled_model(inputs=input_array, device=android_device) Copy to clipboard Please refer to the qairt.compile and CompiledModel.__call__ documentation for more details on additional arguments that can be passed. Following the optimize call, you should see messages in your console indicating progress and improvements. Example output: 2025-07-18 13:18:15,005 - qairt.tuner - INFO - Improvement in criteria (latency) observed: 10.67% Copy to clipboard After tuning, view the new QHAS report: assert report.summary is not None bw_tuned_qhas_report_path = Path(tuned_artifacts_dir / "latency_tuned_model_qhas.json") bw_qhas = report.summary.dump(bw_tuned_qhas_report_path) print_or_view_qhas(bw_tuned_qhas_report_path) Copy to clipboard On a Snapdragon SM8750 device, you should see about 10% lower *total\_time (us)*. Results may vary by device and run. You may need to tune several times to see a clear improvement. Finally, you can save the tuned model as a context binary: best_compiled_model.save(tuned_artifacts_dir / "resnet_model_tuned.bin") Copy to clipboard Note You can also tune for lower bandwidth (*total\_dram*) by setting criteria=”bandwidth”. Last Published: Aug 19, 2026 [Previous Topic Step 8. Performance Reports](https://docs.qualcomm.com/bundle/publicresource/80-87189-2/topics/profiling_models_with_visualizer.md) [Next Topic For Windows on Snapdragon devices](https://docs.qualcomm.com/bundle/publicresource/80-87189-2/topics/tutorials.md)