0001
0002
0003
0004
0005
0006 #include <linux/clk-provider.h>
0007 #include <linux/clk/sunxi-ng.h>
0008 #include <linux/io.h>
0009
0010 #include "ccu_common.h"
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020 int sunxi_ccu_set_mmc_timing_mode(struct clk *clk, bool new_mode)
0021 {
0022 struct clk_hw *hw = __clk_get_hw(clk);
0023 struct ccu_common *cm = hw_to_ccu_common(hw);
0024 unsigned long flags;
0025 u32 val;
0026
0027 if (!(cm->features & CCU_FEATURE_MMC_TIMING_SWITCH))
0028 return -ENOTSUPP;
0029
0030 spin_lock_irqsave(cm->lock, flags);
0031
0032 val = readl(cm->base + cm->reg);
0033 if (new_mode)
0034 val |= CCU_MMC_NEW_TIMING_MODE;
0035 else
0036 val &= ~CCU_MMC_NEW_TIMING_MODE;
0037 writel(val, cm->base + cm->reg);
0038
0039 spin_unlock_irqrestore(cm->lock, flags);
0040
0041 return 0;
0042 }
0043 EXPORT_SYMBOL_GPL(sunxi_ccu_set_mmc_timing_mode);
0044
0045
0046
0047
0048
0049
0050
0051
0052
0053 int sunxi_ccu_get_mmc_timing_mode(struct clk *clk)
0054 {
0055 struct clk_hw *hw = __clk_get_hw(clk);
0056 struct ccu_common *cm = hw_to_ccu_common(hw);
0057
0058 if (!(cm->features & CCU_FEATURE_MMC_TIMING_SWITCH))
0059 return -ENOTSUPP;
0060
0061 return !!(readl(cm->base + cm->reg) & CCU_MMC_NEW_TIMING_MODE);
0062 }
0063 EXPORT_SYMBOL_GPL(sunxi_ccu_get_mmc_timing_mode);