2013-12-02 15:07:02 +01:00
/*
* drivers / clk / at91 / pmc . h
*
* Copyright ( C ) 2013 Boris BREZILLON < b . brezillon @ overkiz . com >
*
* This program is free software ; you can redistribute it and / or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation ; either version 2 of the License , or
* ( at your option ) any later version .
*/
# ifndef __PMC_H_
# define __PMC_H_
# include <linux/io.h>
# include <linux/irqdomain.h>
2014-09-05 09:54:13 +02:00
# include <linux/regmap.h>
2013-12-02 15:07:02 +01:00
# include <linux/spinlock.h>
2014-09-07 08:14:29 +02:00
extern spinlock_t pmc_pcr_lock ;
2018-10-16 16:21:45 +02:00
struct pmc_data {
unsigned int ncore ;
struct clk_hw * * chws ;
unsigned int nsystem ;
struct clk_hw * * shws ;
unsigned int nperiph ;
struct clk_hw * * phws ;
unsigned int ngck ;
struct clk_hw * * ghws ;
} ;
2013-12-02 15:07:02 +01:00
struct clk_range {
unsigned long min ;
unsigned long max ;
} ;
# define CLK_RANGE(MIN, MAX) {.min = MIN, .max = MAX,}
2018-10-16 16:21:44 +02:00
struct clk_master_layout {
2019-04-02 14:50:53 +02:00
u32 offset ;
2018-10-16 16:21:44 +02:00
u32 mask ;
u8 pres_shift ;
} ;
extern const struct clk_master_layout at91rm9200_master_layout ;
extern const struct clk_master_layout at91sam9x5_master_layout ;
struct clk_master_characteristics {
struct clk_range output ;
u32 divisors [ 4 ] ;
u8 have_div3_pres ;
} ;
struct clk_pll_layout {
u32 pllr_mask ;
u16 mul_mask ;
u8 mul_shift ;
} ;
extern const struct clk_pll_layout at91rm9200_pll_layout ;
extern const struct clk_pll_layout at91sam9g45_pll_layout ;
extern const struct clk_pll_layout at91sam9g20_pllb_layout ;
extern const struct clk_pll_layout sama5d3_pll_layout ;
struct clk_pll_characteristics {
struct clk_range input ;
int num_output ;
2019-04-25 14:15:54 -07:00
const struct clk_range * output ;
2018-10-16 16:21:44 +02:00
u16 * icpll ;
u8 * out ;
2019-04-02 14:50:54 +02:00
u8 upll : 1 ;
2018-10-16 16:21:44 +02:00
} ;
struct clk_programmable_layout {
2019-03-18 11:50:45 +01:00
u8 pres_mask ;
2018-10-16 16:21:44 +02:00
u8 pres_shift ;
u8 css_mask ;
u8 have_slck_mck ;
2019-03-18 11:50:45 +01:00
u8 is_pres_direct ;
2018-10-16 16:21:44 +02:00
} ;
extern const struct clk_programmable_layout at91rm9200_programmable_layout ;
extern const struct clk_programmable_layout at91sam9g45_programmable_layout ;
extern const struct clk_programmable_layout at91sam9x5_programmable_layout ;
2019-04-02 14:50:50 +02:00
struct clk_pcr_layout {
u32 offset ;
u32 cmd ;
u32 div_mask ;
u32 gckcss_mask ;
u32 pid_mask ;
} ;
# define field_get(_mask, _reg) (((_reg) & (_mask)) >> (ffs(_mask) - 1))
# define field_prep(_mask, _val) (((_val) << (ffs(_mask) - 1)) & (_mask))
2018-10-16 16:21:45 +02:00
# define ndck(a, s) (a[s - 1].id + 1)
# define nck(a) (a[ARRAY_SIZE(a) - 1].id + 1)
struct pmc_data * pmc_data_allocate ( unsigned int ncore , unsigned int nsystem ,
unsigned int nperiph , unsigned int ngck ) ;
void pmc_data_free ( struct pmc_data * pmc_data ) ;
2013-12-02 15:07:02 +01:00
int of_at91_get_clk_range ( struct device_node * np , const char * propname ,
struct clk_range * range ) ;
2018-10-16 16:21:44 +02:00
struct clk_hw * of_clk_hw_pmc_get ( struct of_phandle_args * clkspec , void * data ) ;
struct clk_hw * __init
at91_clk_register_audio_pll_frac ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
at91_clk_register_audio_pll_pad ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
at91_clk_register_audio_pll_pmc ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
at91_clk_register_generated ( struct regmap * regmap , spinlock_t * lock ,
2019-04-02 14:50:51 +02:00
const struct clk_pcr_layout * layout ,
2018-10-16 16:21:44 +02:00
const char * name , const char * * parent_names ,
u8 num_parents , u8 id , bool pll_audio ,
const struct clk_range * range ) ;
struct clk_hw * __init
at91_clk_register_h32mx ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
at91_clk_i2s_mux_register ( struct regmap * regmap , const char * name ,
const char * const * parent_names ,
unsigned int num_parents , u8 bus_id ) ;
struct clk_hw * __init
at91_clk_register_main_rc_osc ( struct regmap * regmap , const char * name ,
u32 frequency , u32 accuracy ) ;
struct clk_hw * __init
at91_clk_register_main_osc ( struct regmap * regmap , const char * name ,
const char * parent_name , bool bypass ) ;
struct clk_hw * __init
at91_clk_register_rm9200_main ( struct regmap * regmap ,
const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
at91_clk_register_sam9x5_main ( struct regmap * regmap , const char * name ,
const char * * parent_names , int num_parents ) ;
struct clk_hw * __init
at91_clk_register_master ( struct regmap * regmap , const char * name ,
int num_parents , const char * * parent_names ,
const struct clk_master_layout * layout ,
const struct clk_master_characteristics * characteristics ) ;
struct clk_hw * __init
at91_clk_register_peripheral ( struct regmap * regmap , const char * name ,
const char * parent_name , u32 id ) ;
struct clk_hw * __init
at91_clk_register_sam9x5_peripheral ( struct regmap * regmap , spinlock_t * lock ,
2019-04-02 14:50:50 +02:00
const struct clk_pcr_layout * layout ,
2018-10-16 16:21:44 +02:00
const char * name , const char * parent_name ,
u32 id , const struct clk_range * range ) ;
struct clk_hw * __init
at91_clk_register_pll ( struct regmap * regmap , const char * name ,
const char * parent_name , u8 id ,
const struct clk_pll_layout * layout ,
const struct clk_pll_characteristics * characteristics ) ;
struct clk_hw * __init
at91_clk_register_plldiv ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
2019-04-02 14:50:54 +02:00
struct clk_hw * __init
sam9x60_clk_register_pll ( struct regmap * regmap , spinlock_t * lock ,
const char * name , const char * parent_name , u8 id ,
const struct clk_pll_characteristics * characteristics ) ;
2018-10-16 16:21:44 +02:00
struct clk_hw * __init
at91_clk_register_programmable ( struct regmap * regmap , const char * name ,
const char * * parent_names , u8 num_parents , u8 id ,
const struct clk_programmable_layout * layout ) ;
struct clk_hw * __init
at91_clk_register_sam9260_slow ( struct regmap * regmap ,
const char * name ,
const char * * parent_names ,
int num_parents ) ;
struct clk_hw * __init
at91sam9x5_clk_register_smd ( struct regmap * regmap , const char * name ,
const char * * parent_names , u8 num_parents ) ;
struct clk_hw * __init
at91_clk_register_system ( struct regmap * regmap , const char * name ,
const char * parent_name , u8 id ) ;
struct clk_hw * __init
at91sam9x5_clk_register_usb ( struct regmap * regmap , const char * name ,
const char * * parent_names , u8 num_parents ) ;
struct clk_hw * __init
at91sam9n12_clk_register_usb ( struct regmap * regmap , const char * name ,
const char * parent_name ) ;
struct clk_hw * __init
2019-04-02 14:50:52 +02:00
sam9x60_clk_register_usb ( struct regmap * regmap , const char * name ,
const char * * parent_names , u8 num_parents ) ;
struct clk_hw * __init
2018-10-16 16:21:44 +02:00
at91rm9200_clk_register_usb ( struct regmap * regmap , const char * name ,
const char * parent_name , const u32 * divisors ) ;
struct clk_hw * __init
at91_clk_register_utmi ( struct regmap * regmap_pmc , struct regmap * regmap_sfr ,
const char * name , const char * parent_name ) ;
2017-06-08 02:36:47 +02:00
# ifdef CONFIG_PM
void pmc_register_id ( u8 id ) ;
2017-12-11 17:55:35 +01:00
void pmc_register_pck ( u8 pck ) ;
2017-06-08 02:36:47 +02:00
# else
static inline void pmc_register_id ( u8 id ) { }
2017-12-11 17:55:35 +01:00
static inline void pmc_register_pck ( u8 pck ) { }
2017-06-08 02:36:47 +02:00
# endif
2013-12-02 15:07:02 +01:00
# endif /* __PMC_H_ */