ccu_common.h 2.6 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
/*
 * Copyright (c) 2016 Maxime Ripard. All rights reserved.
 *
 * This software is licensed under the terms of the GNU General Public
 * License version 2, as published by the Free Software Foundation, and
 * may be copied, distributed, and modified under those terms.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 */

#ifndef _COMMON_H_
#define _COMMON_H_

#include <linux/compiler.h>
#include <linux/clk-provider.h>

#define CCU_FEATURE_FRACTIONAL		BIT(0)
#define CCU_FEATURE_VARIABLE_PREDIV	BIT(1)
#define CCU_FEATURE_FIXED_PREDIV	BIT(2)
#define CCU_FEATURE_FIXED_POSTDIV	BIT(3)
24
#define CCU_FEATURE_ALL_PREDIV		BIT(4)
25
#define CCU_FEATURE_LOCK_REG		BIT(5)
26 27 28 29
#define CCU_FEATURE_MMC_TIMING_SWITCH	BIT(6)

/* MMC timing mode switch bit */
#define CCU_MMC_NEW_TIMING_MODE		BIT(30)
30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64

struct device_node;

#define CLK_HW_INIT(_name, _parent, _ops, _flags)			\
	&(struct clk_init_data) {					\
		.flags		= _flags,				\
		.name		= _name,				\
		.parent_names	= (const char *[]) { _parent },		\
		.num_parents	= 1,					\
		.ops 		= _ops,					\
	}

#define CLK_HW_INIT_PARENTS(_name, _parents, _ops, _flags)		\
	&(struct clk_init_data) {					\
		.flags		= _flags,				\
		.name		= _name,				\
		.parent_names	= _parents,				\
		.num_parents	= ARRAY_SIZE(_parents),			\
		.ops 		= _ops,					\
	}

#define CLK_FIXED_FACTOR(_struct, _name, _parent,			\
			_div, _mult, _flags)				\
	struct clk_fixed_factor _struct = {				\
		.div		= _div,					\
		.mult		= _mult,				\
		.hw.init	= CLK_HW_INIT(_name,			\
					      _parent,			\
					      &clk_fixed_factor_ops,	\
					      _flags),			\
	}

struct ccu_common {
	void __iomem	*base;
	u16		reg;
65
	u16		lock_reg;
66
	u32		prediv;
67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89

	unsigned long	features;
	spinlock_t	*lock;
	struct clk_hw	hw;
};

static inline struct ccu_common *hw_to_ccu_common(struct clk_hw *hw)
{
	return container_of(hw, struct ccu_common, hw);
}

struct sunxi_ccu_desc {
	struct ccu_common		**ccu_clks;
	unsigned long			num_ccu_clks;

	struct clk_hw_onecell_data	*hw_clks;

	struct ccu_reset_map		*resets;
	unsigned long			num_resets;
};

void ccu_helper_wait_for_lock(struct ccu_common *common, u32 lock);

90 91 92 93 94 95 96 97 98 99 100 101
struct ccu_pll_nb {
	struct notifier_block	clk_nb;
	struct ccu_common	*common;

	u32	enable;
	u32	lock;
};

#define to_ccu_pll_nb(_nb) container_of(_nb, struct ccu_pll_nb, clk_nb)

int ccu_pll_notifier_register(struct ccu_pll_nb *pll_nb);

102 103 104 105
int sunxi_ccu_probe(struct device_node *node, void __iomem *reg,
		    const struct sunxi_ccu_desc *desc);

#endif /* _COMMON_H_ */