- reg: memory window mapping address and length
- clocks: Input clock used to derive the sample clock. Expected to be the
SoC's APB clock.
+- resets: Reset controller phandle
- #io-channel-cells: Must be set to <1> to indicate channels are selected
by index.
adc@1e6e9000 {
compatible = "aspeed,ast2400-adc";
reg = <0x1e6e9000 0xb0>;
- clocks = <&clk_apb>;
+ clocks = <&syscon ASPEED_CLK_APB>;
+ resets = <&syscon ASPEED_RESET_ADC>;
#io-channel-cells = <1>;
};
#include <linux/module.h>
#include <linux/of_platform.h>
#include <linux/platform_device.h>
+#include <linux/reset.h>
#include <linux/spinlock.h>
#include <linux/types.h>
};
struct aspeed_adc_data {
- struct device *dev;
- void __iomem *base;
- spinlock_t clk_lock;
- struct clk_hw *clk_prescaler;
- struct clk_hw *clk_scaler;
+ struct device *dev;
+ void __iomem *base;
+ spinlock_t clk_lock;
+ struct clk_hw *clk_prescaler;
+ struct clk_hw *clk_scaler;
+ struct reset_control *rst;
};
#define ASPEED_CHAN(_idx, _data_reg_addr) { \
goto scaler_error;
}
+ data->rst = devm_reset_control_get_exclusive(&pdev->dev, NULL);
+ if (IS_ERR(data->rst)) {
+ dev_err(&pdev->dev,
+ "invalid or missing reset controller device tree entry");
+ ret = PTR_ERR(data->rst);
+ goto reset_error;
+ }
+ reset_control_deassert(data->rst);
+
model_data = of_device_get_match_data(&pdev->dev);
if (model_data->wait_init_sequence) {
writel(ASPEED_OPERATION_MODE_POWER_DOWN,
data->base + ASPEED_REG_ENGINE_CONTROL);
clk_disable_unprepare(data->clk_scaler->clk);
+reset_error:
+ reset_control_assert(data->rst);
clk_enable_error:
clk_hw_unregister_divider(data->clk_scaler);
-
scaler_error:
clk_hw_unregister_divider(data->clk_prescaler);
return ret;
writel(ASPEED_OPERATION_MODE_POWER_DOWN,
data->base + ASPEED_REG_ENGINE_CONTROL);
clk_disable_unprepare(data->clk_scaler->clk);
+ reset_control_assert(data->rst);
clk_hw_unregister_divider(data->clk_scaler);
clk_hw_unregister_divider(data->clk_prescaler);