1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  *  NEC VR4100 series RTC platform device.
4  *
5  *  Copyright (C) 2007	Yoichi Yuasa <yuasa@linux-mips.org>
6  */
7 #include <linux/errno.h>
8 #include <linux/init.h>
9 #include <linux/smp.h>
10 #include <linux/ioport.h>
11 #include <linux/platform_device.h>
12 
13 #include <asm/cpu.h>
14 #include <asm/vr41xx/irq.h>
15 
16 static struct resource rtc_type1_resource[] __initdata = {
17 	{
18 		.start	= 0x0b0000c0,
19 		.end	= 0x0b0000df,
20 		.flags	= IORESOURCE_MEM,
21 	},
22 	{
23 		.start	= 0x0b0001c0,
24 		.end	= 0x0b0001df,
25 		.flags	= IORESOURCE_MEM,
26 	},
27 	{
28 		.start	= ELAPSEDTIME_IRQ,
29 		.end	= ELAPSEDTIME_IRQ,
30 		.flags	= IORESOURCE_IRQ,
31 	},
32 	{
33 		.start	= RTCLONG1_IRQ,
34 		.end	= RTCLONG1_IRQ,
35 		.flags	= IORESOURCE_IRQ,
36 	},
37 };
38 
39 static struct resource rtc_type2_resource[] __initdata = {
40 	{
41 		.start	= 0x0f000100,
42 		.end	= 0x0f00011f,
43 		.flags	= IORESOURCE_MEM,
44 	},
45 	{
46 		.start	= 0x0f000120,
47 		.end	= 0x0f00013f,
48 		.flags	= IORESOURCE_MEM,
49 	},
50 	{
51 		.start	= ELAPSEDTIME_IRQ,
52 		.end	= ELAPSEDTIME_IRQ,
53 		.flags	= IORESOURCE_IRQ,
54 	},
55 	{
56 		.start	= RTCLONG1_IRQ,
57 		.end	= RTCLONG1_IRQ,
58 		.flags	= IORESOURCE_IRQ,
59 	},
60 };
61 
vr41xx_rtc_add(void)62 static int __init vr41xx_rtc_add(void)
63 {
64 	struct platform_device *pdev;
65 	struct resource *res;
66 	unsigned int num;
67 	int retval;
68 
69 	pdev = platform_device_alloc("RTC", -1);
70 	if (!pdev)
71 		return -ENOMEM;
72 
73 	switch (current_cpu_type()) {
74 	case CPU_VR4111:
75 	case CPU_VR4121:
76 		res = rtc_type1_resource;
77 		num = ARRAY_SIZE(rtc_type1_resource);
78 		break;
79 	case CPU_VR4122:
80 	case CPU_VR4131:
81 	case CPU_VR4133:
82 		res = rtc_type2_resource;
83 		num = ARRAY_SIZE(rtc_type2_resource);
84 		break;
85 	default:
86 		retval = -ENODEV;
87 		goto err_free_device;
88 	}
89 
90 	retval = platform_device_add_resources(pdev, res, num);
91 	if (retval)
92 		goto err_free_device;
93 
94 	retval = platform_device_add(pdev);
95 	if (retval)
96 		goto err_free_device;
97 
98 	return 0;
99 
100 err_free_device:
101 	platform_device_put(pdev);
102 
103 	return retval;
104 }
105 device_initcall(vr41xx_rtc_add);
106