Adjusting NVIDIA PWM Fan Frequency to 2.4 kHz on Thor

Hi Nvidia,

We are currently using NVIDIA’s FAN_PWM pin for buzzer control. The pin is set high by default, and after analyzing the output signal, we measured the frequency at approximately 52.7 kHz.

Our requirement is to adjust the PWM frequency to 2.4 kHz. We have reviewed the NVIDIA documentation and related forum discussions, but we could not find any information explaining how to modify this frequency.

We also found the Tegra PWM driver code here:

https://codebrowser.dev/linux/linux/drivers/pwm/pwm-tegra.c.html

However, we are still unable to adjust the frequency to the required value, and there does not appear to be a manual or reference guide available for this configuration.

Could you please advise how we can modify the PWM frequency to 2.4 kHz for this pin?

In addition, if we need to modify the PWM output setting or related pin configuration, could you also advise what steps, driver changes, device tree settings, or register configurations are required?

Thanks

check if these links help:

Hi morganweng,

Are you using the devkit or custom board for Thor?
What’s the Jetpack version in use?

It maps to c6a0000.pwm.
Please simply run ls -l /sys/class/pwm to check the sysfs node and refer to the link shared by nagesh_accord.

You can also check PWM Frequency Configuration — NVIDIA Jetson Linux Developer Guide for details.

Jetpack 7.2 has a more recent file Linux_for_Tegra/source/kernel/kernel-noble/drivers/pwm/pwm-tegra.c
Here’s the header/document

// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * drivers/pwm/pwm-tegra.c
 *
 * Tegra pulse-width-modulation controller driver
 *
 * Copyright (c) 2010-2020, NVIDIA Corporation.
 * Based on arch/arm/plat-mxc/pwm.c by Sascha Hauer <s.hauer@pengutronix.de>
 *
 * Overview of Tegra Pulse Width Modulator Register
 * CSR_0 of Tegra20, Tegra186, and Tegra194:
 * +-------+-------+-----------------------------------------------------------+
 * | Bit   | Field | Description                                               |
 * +-------+-------+-----------------------------------------------------------+
 * | 31    | ENB   | Enable Pulse width modulator.                             |
 * |       |       | 0 = DISABLE, 1 = ENABLE.                                  |
 * +-------+-------+-----------------------------------------------------------+
 * | 30:16 | PWM_0 | Pulse width that needs to be programmed.                  |
 * |       |       | 0 = Always low.                                           |
 * |       |       | 1 = 1 / (1 + PWM_DEPTH) pulse high.                       |
 * |       |       | 2 = 2 / (1 + PWM_DEPTH) pulse high.                       |
 * |       |       | N = N / (1 + PWM_DEPTH) pulse high.                       |
 * |       |       | Only 8 bits are usable [23:16].                           |
 * |       |       | Bit[24] can be programmed to 1 to achieve 100% duty       |
 * |       |       | cycle. In this case the other bits [23:16] are set to     |
 * |       |       | don't care.                                               |
 * +-------+-------+-----------------------------------------------------------+
 * | 12:0  | PFM_0 | Frequency divider that needs to be programmed, also known |
 * |       |       | as SCALE. Division by (1 + PFM_0).                        |
 * +-------+-------+-----------------------------------------------------------+
 *
 * CSR_0 of Tegra264:
 * +-------+-------+-----------------------------------------------------------+
 * | Bit   | Field | Description                                               |
 * +-------+-------+-----------------------------------------------------------+
 * | 31:16 | PWM_0 | Pulse width that needs to be programmed.                  |
 * |       |       | 0 = Always low.                                           |
 * |       |       | 1 = 1 / (1 + PWM_DEPTH) pulse high.                       |
 * |       |       | 2 = 2 / (1 + PWM_DEPTH) pulse high.                       |
 * |       |       | N = N / (1 + PWM_DEPTH) pulse high.                       |
 * +-------+-------+-----------------------------------------------------------+
 * | 15:0  | PFM_0 | Frequency divider that needs to be programmed, also known |
 * |       |       | as SCALE. Division by (1 + PFM_0).                        |
 * +-------+-------+-----------------------------------------------------------+
 *
 * CSR_1 of Tegra264:
 * +-------+-------+-----------------------------------------------------------+
 * | Bit   | Field | Description                                               |
 * +-------+-------+-----------------------------------------------------------+
 * | 31    | ENB   | Enable Pulse width modulator.                             |
 * |       |       | 0 = DISABLE, 1 = ENABLE.                                  |
 * +-------+-------+-----------------------------------------------------------+
 * | 30:15 | DEPTH | Depth for pulse width modulator. This controls the pulse  |
 * |       |       | time generated. Division by (1 + PWM_DEPTH).              |
 * +-------+-------+-----------------------------------------------------------+
 *
 * The PWM clock frequency is divided by (1 + PWM_DEPTH) before subdividing it
 * based on the programmable frequency division value to generate the required
 * frequency for PWM output. The maximum output frequency that can be
 * achieved is (max rate of source clock) / (1 + PWM_DEPTH).
 * e.g. if source clock rate is 408 MHz and PWM_DEPTH is 255, maximum output
 * frequency can be: 408 MHz / (1 + 255) ~= 1.6 MHz.
 * This 1.6 MHz frequency can further be divided using SCALE value in PWM.
 *
 * Limitations:
 * -    When PWM is disabled, the output is driven to inactive.
 * -    It does not allow the current PWM period to complete and
 *      stops abruptly.
 *
 * -    If the register is reconfigured while PWM is running,
 *      it does not complete the currently running period.
 *
 * -    If the user input duty is beyond acceptible limits,
 *      -EINVAL is returned.
 */