Linux Audio

Check our new training course

Loading...
Note: File does not exist in v4.6.
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Intel Atom SOC Power Management Controller Driver
  4 * Copyright (c) 2014, Intel Corporation.
  5 */
  6
  7#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  8
  9#include <linux/debugfs.h>
 10#include <linux/device.h>
 11#include <linux/dmi.h>
 12#include <linux/init.h>
 13#include <linux/io.h>
 14#include <linux/platform_data/x86/clk-pmc-atom.h>
 15#include <linux/platform_data/x86/pmc_atom.h>
 16#include <linux/platform_device.h>
 17#include <linux/pci.h>
 18#include <linux/seq_file.h>
 19
 20struct pmc_bit_map {
 21	const char *name;
 22	u32 bit_mask;
 23};
 24
 25struct pmc_reg_map {
 26	const struct pmc_bit_map *d3_sts_0;
 27	const struct pmc_bit_map *d3_sts_1;
 28	const struct pmc_bit_map *func_dis;
 29	const struct pmc_bit_map *func_dis_2;
 30	const struct pmc_bit_map *pss;
 31};
 32
 33struct pmc_data {
 34	const struct pmc_reg_map *map;
 35	const struct pmc_clk *clks;
 36};
 37
 38struct pmc_dev {
 39	u32 base_addr;
 40	void __iomem *regmap;
 41	const struct pmc_reg_map *map;
 42#ifdef CONFIG_DEBUG_FS
 43	struct dentry *dbgfs_dir;
 44#endif /* CONFIG_DEBUG_FS */
 45	bool init;
 46};
 47
 48static struct pmc_dev pmc_device;
 49static u32 acpi_base_addr;
 50
 51static const struct pmc_clk byt_clks[] = {
 52	{
 53		.name = "xtal",
 54		.freq = 25000000,
 55		.parent_name = NULL,
 56	},
 57	{
 58		.name = "pll",
 59		.freq = 19200000,
 60		.parent_name = "xtal",
 61	},
 62	{},
 63};
 64
 65static const struct pmc_clk cht_clks[] = {
 66	{
 67		.name = "xtal",
 68		.freq = 19200000,
 69		.parent_name = NULL,
 70	},
 71	{},
 72};
 73
 74static const struct pmc_bit_map d3_sts_0_map[] = {
 75	{"LPSS1_F0_DMA",	BIT_LPSS1_F0_DMA},
 76	{"LPSS1_F1_PWM1",	BIT_LPSS1_F1_PWM1},
 77	{"LPSS1_F2_PWM2",	BIT_LPSS1_F2_PWM2},
 78	{"LPSS1_F3_HSUART1",	BIT_LPSS1_F3_HSUART1},
 79	{"LPSS1_F4_HSUART2",	BIT_LPSS1_F4_HSUART2},
 80	{"LPSS1_F5_SPI",	BIT_LPSS1_F5_SPI},
 81	{"LPSS1_F6_Reserved",	BIT_LPSS1_F6_XXX},
 82	{"LPSS1_F7_Reserved",	BIT_LPSS1_F7_XXX},
 83	{"SCC_EMMC",		BIT_SCC_EMMC},
 84	{"SCC_SDIO",		BIT_SCC_SDIO},
 85	{"SCC_SDCARD",		BIT_SCC_SDCARD},
 86	{"SCC_MIPI",		BIT_SCC_MIPI},
 87	{"HDA",			BIT_HDA},
 88	{"LPE",			BIT_LPE},
 89	{"OTG",			BIT_OTG},
 90	{"USH",			BIT_USH},
 91	{"GBE",			BIT_GBE},
 92	{"SATA",		BIT_SATA},
 93	{"USB_EHCI",		BIT_USB_EHCI},
 94	{"SEC",			BIT_SEC},
 95	{"PCIE_PORT0",		BIT_PCIE_PORT0},
 96	{"PCIE_PORT1",		BIT_PCIE_PORT1},
 97	{"PCIE_PORT2",		BIT_PCIE_PORT2},
 98	{"PCIE_PORT3",		BIT_PCIE_PORT3},
 99	{"LPSS2_F0_DMA",	BIT_LPSS2_F0_DMA},
100	{"LPSS2_F1_I2C1",	BIT_LPSS2_F1_I2C1},
101	{"LPSS2_F2_I2C2",	BIT_LPSS2_F2_I2C2},
102	{"LPSS2_F3_I2C3",	BIT_LPSS2_F3_I2C3},
103	{"LPSS2_F3_I2C4",	BIT_LPSS2_F4_I2C4},
104	{"LPSS2_F5_I2C5",	BIT_LPSS2_F5_I2C5},
105	{"LPSS2_F6_I2C6",	BIT_LPSS2_F6_I2C6},
106	{"LPSS2_F7_I2C7",	BIT_LPSS2_F7_I2C7},
107	{},
108};
109
110static struct pmc_bit_map byt_d3_sts_1_map[] = {
111	{"SMB",			BIT_SMB},
112	{"OTG_SS_PHY",		BIT_OTG_SS_PHY},
113	{"USH_SS_PHY",		BIT_USH_SS_PHY},
114	{"DFX",			BIT_DFX},
115	{},
116};
117
118static struct pmc_bit_map cht_d3_sts_1_map[] = {
119	{"SMB",			BIT_SMB},
120	{"GMM",			BIT_STS_GMM},
121	{"ISH",			BIT_STS_ISH},
122	{},
123};
124
125static struct pmc_bit_map cht_func_dis_2_map[] = {
126	{"SMB",			BIT_SMB},
127	{"GMM",			BIT_FD_GMM},
128	{"ISH",			BIT_FD_ISH},
129	{},
130};
131
132static const struct pmc_bit_map byt_pss_map[] = {
133	{"GBE",			PMC_PSS_BIT_GBE},
134	{"SATA",		PMC_PSS_BIT_SATA},
135	{"HDA",			PMC_PSS_BIT_HDA},
136	{"SEC",			PMC_PSS_BIT_SEC},
137	{"PCIE",		PMC_PSS_BIT_PCIE},
138	{"LPSS",		PMC_PSS_BIT_LPSS},
139	{"LPE",			PMC_PSS_BIT_LPE},
140	{"DFX",			PMC_PSS_BIT_DFX},
141	{"USH_CTRL",		PMC_PSS_BIT_USH_CTRL},
142	{"USH_SUS",		PMC_PSS_BIT_USH_SUS},
143	{"USH_VCCS",		PMC_PSS_BIT_USH_VCCS},
144	{"USH_VCCA",		PMC_PSS_BIT_USH_VCCA},
145	{"OTG_CTRL",		PMC_PSS_BIT_OTG_CTRL},
146	{"OTG_VCCS",		PMC_PSS_BIT_OTG_VCCS},
147	{"OTG_VCCA_CLK",	PMC_PSS_BIT_OTG_VCCA_CLK},
148	{"OTG_VCCA",		PMC_PSS_BIT_OTG_VCCA},
149	{"USB",			PMC_PSS_BIT_USB},
150	{"USB_SUS",		PMC_PSS_BIT_USB_SUS},
151	{},
152};
153
154static const struct pmc_bit_map cht_pss_map[] = {
155	{"SATA",		PMC_PSS_BIT_SATA},
156	{"HDA",			PMC_PSS_BIT_HDA},
157	{"SEC",			PMC_PSS_BIT_SEC},
158	{"PCIE",		PMC_PSS_BIT_PCIE},
159	{"LPSS",		PMC_PSS_BIT_LPSS},
160	{"LPE",			PMC_PSS_BIT_LPE},
161	{"UFS",			PMC_PSS_BIT_CHT_UFS},
162	{"UXD",			PMC_PSS_BIT_CHT_UXD},
163	{"UXD_FD",		PMC_PSS_BIT_CHT_UXD_FD},
164	{"UX_ENG",		PMC_PSS_BIT_CHT_UX_ENG},
165	{"USB_SUS",		PMC_PSS_BIT_CHT_USB_SUS},
166	{"GMM",			PMC_PSS_BIT_CHT_GMM},
167	{"ISH",			PMC_PSS_BIT_CHT_ISH},
168	{"DFX_MASTER",		PMC_PSS_BIT_CHT_DFX_MASTER},
169	{"DFX_CLUSTER1",	PMC_PSS_BIT_CHT_DFX_CLUSTER1},
170	{"DFX_CLUSTER2",	PMC_PSS_BIT_CHT_DFX_CLUSTER2},
171	{"DFX_CLUSTER3",	PMC_PSS_BIT_CHT_DFX_CLUSTER3},
172	{"DFX_CLUSTER4",	PMC_PSS_BIT_CHT_DFX_CLUSTER4},
173	{"DFX_CLUSTER5",	PMC_PSS_BIT_CHT_DFX_CLUSTER5},
174	{},
175};
176
177static const struct pmc_reg_map byt_reg_map = {
178	.d3_sts_0	= d3_sts_0_map,
179	.d3_sts_1	= byt_d3_sts_1_map,
180	.func_dis	= d3_sts_0_map,
181	.func_dis_2	= byt_d3_sts_1_map,
182	.pss		= byt_pss_map,
183};
184
185static const struct pmc_reg_map cht_reg_map = {
186	.d3_sts_0	= d3_sts_0_map,
187	.d3_sts_1	= cht_d3_sts_1_map,
188	.func_dis	= d3_sts_0_map,
189	.func_dis_2	= cht_func_dis_2_map,
190	.pss		= cht_pss_map,
191};
192
193static const struct pmc_data byt_data = {
194	.map = &byt_reg_map,
195	.clks = byt_clks,
196};
197
198static const struct pmc_data cht_data = {
199	.map = &cht_reg_map,
200	.clks = cht_clks,
201};
202
203static inline u32 pmc_reg_read(struct pmc_dev *pmc, int reg_offset)
204{
205	return readl(pmc->regmap + reg_offset);
206}
207
208static inline void pmc_reg_write(struct pmc_dev *pmc, int reg_offset, u32 val)
209{
210	writel(val, pmc->regmap + reg_offset);
211}
212
213int pmc_atom_read(int offset, u32 *value)
214{
215	struct pmc_dev *pmc = &pmc_device;
216
217	if (!pmc->init)
218		return -ENODEV;
219
220	*value = pmc_reg_read(pmc, offset);
221	return 0;
222}
223EXPORT_SYMBOL_GPL(pmc_atom_read);
224
225int pmc_atom_write(int offset, u32 value)
226{
227	struct pmc_dev *pmc = &pmc_device;
228
229	if (!pmc->init)
230		return -ENODEV;
231
232	pmc_reg_write(pmc, offset, value);
233	return 0;
234}
235EXPORT_SYMBOL_GPL(pmc_atom_write);
236
237static void pmc_power_off(void)
238{
239	u16	pm1_cnt_port;
240	u32	pm1_cnt_value;
241
242	pr_info("Preparing to enter system sleep state S5\n");
243
244	pm1_cnt_port = acpi_base_addr + PM1_CNT;
245
246	pm1_cnt_value = inl(pm1_cnt_port);
247	pm1_cnt_value &= SLEEP_TYPE_MASK;
248	pm1_cnt_value |= SLEEP_TYPE_S5;
249	pm1_cnt_value |= SLEEP_ENABLE;
250
251	outl(pm1_cnt_value, pm1_cnt_port);
252}
253
254static void pmc_hw_reg_setup(struct pmc_dev *pmc)
255{
256	/*
257	 * Disable PMC S0IX_WAKE_EN events coming from:
258	 * - LPC clock run
259	 * - GPIO_SUS ored dedicated IRQs
260	 * - GPIO_SCORE ored dedicated IRQs
261	 * - GPIO_SUS shared IRQ
262	 * - GPIO_SCORE shared IRQ
263	 */
264	pmc_reg_write(pmc, PMC_S0IX_WAKE_EN, (u32)PMC_WAKE_EN_SETTING);
265}
266
267#ifdef CONFIG_DEBUG_FS
268static void pmc_dev_state_print(struct seq_file *s, int reg_index,
269				u32 sts, const struct pmc_bit_map *sts_map,
270				u32 fd, const struct pmc_bit_map *fd_map)
271{
272	int offset = PMC_REG_BIT_WIDTH * reg_index;
273	int index;
274
275	for (index = 0; sts_map[index].name; index++) {
276		seq_printf(s, "Dev: %-2d - %-32s\tState: %s [%s]\n",
277			offset + index, sts_map[index].name,
278			fd_map[index].bit_mask & fd ?  "Disabled" : "Enabled ",
279			sts_map[index].bit_mask & sts ?  "D3" : "D0");
280	}
281}
282
283static int pmc_dev_state_show(struct seq_file *s, void *unused)
284{
285	struct pmc_dev *pmc = s->private;
286	const struct pmc_reg_map *m = pmc->map;
287	u32 func_dis, func_dis_2;
288	u32 d3_sts_0, d3_sts_1;
289
290	func_dis = pmc_reg_read(pmc, PMC_FUNC_DIS);
291	func_dis_2 = pmc_reg_read(pmc, PMC_FUNC_DIS_2);
292	d3_sts_0 = pmc_reg_read(pmc, PMC_D3_STS_0);
293	d3_sts_1 = pmc_reg_read(pmc, PMC_D3_STS_1);
294
295	/* Low part */
296	pmc_dev_state_print(s, 0, d3_sts_0, m->d3_sts_0, func_dis, m->func_dis);
297
298	/* High part */
299	pmc_dev_state_print(s, 1, d3_sts_1, m->d3_sts_1, func_dis_2, m->func_dis_2);
300
301	return 0;
302}
303
304DEFINE_SHOW_ATTRIBUTE(pmc_dev_state);
305
306static int pmc_pss_state_show(struct seq_file *s, void *unused)
307{
308	struct pmc_dev *pmc = s->private;
309	const struct pmc_bit_map *map = pmc->map->pss;
310	u32 pss = pmc_reg_read(pmc, PMC_PSS);
311	int index;
312
313	for (index = 0; map[index].name; index++) {
314		seq_printf(s, "Island: %-2d - %-32s\tState: %s\n",
315			index, map[index].name,
316			map[index].bit_mask & pss ? "Off" : "On");
317	}
318	return 0;
319}
320
321DEFINE_SHOW_ATTRIBUTE(pmc_pss_state);
322
323static int pmc_sleep_tmr_show(struct seq_file *s, void *unused)
324{
325	struct pmc_dev *pmc = s->private;
326	u64 s0ir_tmr, s0i1_tmr, s0i2_tmr, s0i3_tmr, s0_tmr;
327
328	s0ir_tmr = (u64)pmc_reg_read(pmc, PMC_S0IR_TMR) << PMC_TMR_SHIFT;
329	s0i1_tmr = (u64)pmc_reg_read(pmc, PMC_S0I1_TMR) << PMC_TMR_SHIFT;
330	s0i2_tmr = (u64)pmc_reg_read(pmc, PMC_S0I2_TMR) << PMC_TMR_SHIFT;
331	s0i3_tmr = (u64)pmc_reg_read(pmc, PMC_S0I3_TMR) << PMC_TMR_SHIFT;
332	s0_tmr = (u64)pmc_reg_read(pmc, PMC_S0_TMR) << PMC_TMR_SHIFT;
333
334	seq_printf(s, "S0IR Residency:\t%lldus\n", s0ir_tmr);
335	seq_printf(s, "S0I1 Residency:\t%lldus\n", s0i1_tmr);
336	seq_printf(s, "S0I2 Residency:\t%lldus\n", s0i2_tmr);
337	seq_printf(s, "S0I3 Residency:\t%lldus\n", s0i3_tmr);
338	seq_printf(s, "S0   Residency:\t%lldus\n", s0_tmr);
339	return 0;
340}
341
342DEFINE_SHOW_ATTRIBUTE(pmc_sleep_tmr);
343
344static void pmc_dbgfs_register(struct pmc_dev *pmc)
345{
346	struct dentry *dir;
347
348	dir = debugfs_create_dir("pmc_atom", NULL);
349
350	pmc->dbgfs_dir = dir;
351
352	debugfs_create_file("dev_state", S_IFREG | S_IRUGO, dir, pmc,
353			    &pmc_dev_state_fops);
354	debugfs_create_file("pss_state", S_IFREG | S_IRUGO, dir, pmc,
355			    &pmc_pss_state_fops);
356	debugfs_create_file("sleep_state", S_IFREG | S_IRUGO, dir, pmc,
357			    &pmc_sleep_tmr_fops);
358}
359#else
360static void pmc_dbgfs_register(struct pmc_dev *pmc)
361{
362}
363#endif /* CONFIG_DEBUG_FS */
364
365/*
366 * Some systems need one or more of their pmc_plt_clks to be
367 * marked as critical.
368 */
369static const struct dmi_system_id critclk_systems[] = {
370	{
371		/* pmc_plt_clk0 is used for an external HSIC USB HUB */
372		.ident = "MPL CEC1x",
373		.matches = {
374			DMI_MATCH(DMI_SYS_VENDOR, "MPL AG"),
375			DMI_MATCH(DMI_PRODUCT_NAME, "CEC10 Family"),
376		},
377	},
378	{
379		/* pmc_plt_clk0 - 3 are used for the 4 ethernet controllers */
380		.ident = "Lex 3I380D",
381		.matches = {
382			DMI_MATCH(DMI_SYS_VENDOR, "Lex BayTrail"),
383			DMI_MATCH(DMI_PRODUCT_NAME, "3I380D"),
384		},
385	},
386	{
387		/* pmc_plt_clk* - are used for ethernet controllers */
388		.ident = "Beckhoff CB3163",
389		.matches = {
390			DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"),
391			DMI_MATCH(DMI_BOARD_NAME, "CB3163"),
392		},
393	},
394	{
395		/* pmc_plt_clk* - are used for ethernet controllers */
396		.ident = "Beckhoff CB4063",
397		.matches = {
398			DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"),
399			DMI_MATCH(DMI_BOARD_NAME, "CB4063"),
400		},
401	},
402	{
403		/* pmc_plt_clk* - are used for ethernet controllers */
404		.ident = "Beckhoff CB6263",
405		.matches = {
406			DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"),
407			DMI_MATCH(DMI_BOARD_NAME, "CB6263"),
408		},
409	},
410	{
411		/* pmc_plt_clk* - are used for ethernet controllers */
412		.ident = "Beckhoff CB6363",
413		.matches = {
414			DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"),
415			DMI_MATCH(DMI_BOARD_NAME, "CB6363"),
416		},
417	},
418	{
419		.ident = "SIMATIC IPC227E",
420		.matches = {
421			DMI_MATCH(DMI_SYS_VENDOR, "SIEMENS AG"),
422			DMI_MATCH(DMI_PRODUCT_VERSION, "6ES7647-8B"),
423		},
424	},
425	{
426		.ident = "SIMATIC IPC277E",
427		.matches = {
428			DMI_MATCH(DMI_SYS_VENDOR, "SIEMENS AG"),
429			DMI_MATCH(DMI_PRODUCT_VERSION, "6AV7882-0"),
430		},
431	},
432	{ /*sentinel*/ }
433};
434
435static int pmc_setup_clks(struct pci_dev *pdev, void __iomem *pmc_regmap,
436			  const struct pmc_data *pmc_data)
437{
438	struct platform_device *clkdev;
439	struct pmc_clk_data *clk_data;
440	const struct dmi_system_id *d = dmi_first_match(critclk_systems);
441
442	clk_data = kzalloc(sizeof(*clk_data), GFP_KERNEL);
443	if (!clk_data)
444		return -ENOMEM;
445
446	clk_data->base = pmc_regmap; /* offset is added by client */
447	clk_data->clks = pmc_data->clks;
448	if (d) {
449		clk_data->critical = true;
450		pr_info("%s critclks quirk enabled\n", d->ident);
451	}
452
453	clkdev = platform_device_register_data(&pdev->dev, "clk-pmc-atom",
454					       PLATFORM_DEVID_NONE,
455					       clk_data, sizeof(*clk_data));
456	if (IS_ERR(clkdev)) {
457		kfree(clk_data);
458		return PTR_ERR(clkdev);
459	}
460
461	kfree(clk_data);
462
463	return 0;
464}
465
466static int pmc_setup_dev(struct pci_dev *pdev, const struct pci_device_id *ent)
467{
468	struct pmc_dev *pmc = &pmc_device;
469	const struct pmc_data *data = (struct pmc_data *)ent->driver_data;
470	const struct pmc_reg_map *map = data->map;
471	int ret;
472
473	/* Obtain ACPI base address */
474	pci_read_config_dword(pdev, ACPI_BASE_ADDR_OFFSET, &acpi_base_addr);
475	acpi_base_addr &= ACPI_BASE_ADDR_MASK;
476
477	/* Install power off function */
478	if (acpi_base_addr != 0 && pm_power_off == NULL)
479		pm_power_off = pmc_power_off;
480
481	pci_read_config_dword(pdev, PMC_BASE_ADDR_OFFSET, &pmc->base_addr);
482	pmc->base_addr &= PMC_BASE_ADDR_MASK;
483
484	pmc->regmap = ioremap_nocache(pmc->base_addr, PMC_MMIO_REG_LEN);
485	if (!pmc->regmap) {
486		dev_err(&pdev->dev, "error: ioremap failed\n");
487		return -ENOMEM;
488	}
489
490	pmc->map = map;
491
492	/* PMC hardware registers setup */
493	pmc_hw_reg_setup(pmc);
494
495	pmc_dbgfs_register(pmc);
496
497	/* Register platform clocks - PMC_PLT_CLK [0..5] */
498	ret = pmc_setup_clks(pdev, pmc->regmap, data);
499	if (ret)
500		dev_warn(&pdev->dev, "platform clocks register failed: %d\n",
501			 ret);
502
503	pmc->init = true;
504	return ret;
505}
506
507/*
508 * Data for PCI driver interface
509 *
510 * used by pci_match_id() call below.
511 */
512static const struct pci_device_id pmc_pci_ids[] = {
513	{ PCI_VDEVICE(INTEL, PCI_DEVICE_ID_VLV_PMC), (kernel_ulong_t)&byt_data },
514	{ PCI_VDEVICE(INTEL, PCI_DEVICE_ID_CHT_PMC), (kernel_ulong_t)&cht_data },
515	{ 0, },
516};
517
518static int __init pmc_atom_init(void)
519{
520	struct pci_dev *pdev = NULL;
521	const struct pci_device_id *ent;
522
523	/* We look for our device - PCU PMC
524	 * we assume that there is max. one device.
525	 *
526	 * We can't use plain pci_driver mechanism,
527	 * as the device is really a multiple function device,
528	 * main driver that binds to the pci_device is lpc_ich
529	 * and have to find & bind to the device this way.
530	 */
531	for_each_pci_dev(pdev) {
532		ent = pci_match_id(pmc_pci_ids, pdev);
533		if (ent)
534			return pmc_setup_dev(pdev, ent);
535	}
536	/* Device not found. */
537	return -ENODEV;
538}
539
540device_initcall(pmc_atom_init);
541
542/*
543MODULE_AUTHOR("Aubrey Li <aubrey.li@linux.intel.com>");
544MODULE_DESCRIPTION("Intel Atom SOC Power Management Controller Interface");
545MODULE_LICENSE("GPL v2");
546*/