initial import
[ps3linux_kernel_patches_41.git] / 0070-ps3dispmgr.patch
bloba74b1a3aacef71449adfd438458a64a2f08e050e
1 --- a/drivers/ps3/ps3-vuart.c 2012-01-12 20:42:45.000000000 +0100
2 +++ b/drivers/ps3/ps3-vuart.c 2012-01-26 18:13:18.981200186 +0100
3 @@ -39,6 +39,7 @@
4 * vuart - An inter-partition data link service.
5 * port 0: PS3 AV Settings.
6 * port 2: PS3 System Manager.
7 + * port 10: PS3 Dispatcher Manager.
9 * The vuart provides a bi-directional byte stream data link between logical
10 * partitions. Its primary role is as a communications link between the guest
11 @@ -46,7 +47,7 @@
12 * connections other than those listed.
15 -enum {PORT_COUNT = 3,};
16 +enum {PORT_COUNT = 11,};
18 enum vuart_param {
19 PARAM_TX_TRIGGER = 0,
20 @@ -926,7 +927,7 @@
22 vuart_bus_priv.use_count++;
24 - BUG_ON(vuart_bus_priv.use_count > 2);
25 + BUG_ON(vuart_bus_priv.use_count > 3);
27 if (vuart_bus_priv.use_count != 1)
28 return 0;
29 --- a/arch/powerpc/include/asm/ps3.h 2012-01-26 14:09:41.132438036 +0100
30 +++ b/arch/powerpc/include/asm/ps3.h 2012-01-26 14:11:27.368200391 +0100
31 @@ -327,6 +327,7 @@
32 PS3_MATCH_ID_GPU = 10,
33 PS3_MATCH_ID_LPM = 11,
34 PS3_MATCH_ID_STOR_NOR_FLASH = 12,
35 + PS3_MATCH_ID_DISP_MANAGER = 13,
38 enum ps3_match_sub_id {
39 @@ -347,6 +348,7 @@
40 #define PS3_MODULE_ALIAS_GPU_RAMDISK "ps3:10:2"
41 #define PS3_MODULE_ALIAS_LPM "ps3:11:0"
42 #define PS3_MODULE_ALIAS_STOR_NOR_FLASH "ps3:12:0"
43 +#define PS3_MODULE_ALIAS_DISP_MANAGER "ps3:13:0"
45 enum ps3_system_bus_device_type {
46 PS3_DEVICE_TYPE_IOC0 = 1,
47 --- a/arch/powerpc/platforms/ps3/system-bus.c 2012-01-26 14:09:41.144403930 +0100
48 +++ b/arch/powerpc/platforms/ps3/system-bus.c 2012-01-26 14:17:05.896702636 +0100
49 @@ -183,6 +183,7 @@
51 case PS3_MATCH_ID_AV_SETTINGS:
52 case PS3_MATCH_ID_SYSTEM_MANAGER:
53 + case PS3_MATCH_ID_DISP_MANAGER:
54 pr_debug("%s:%d: unsupported match_id: %u\n", __func__,
55 __LINE__, dev->match_id);
56 pr_debug("%s:%d: bus_id: %llu\n", __func__, __LINE__,
57 @@ -222,6 +223,7 @@
59 case PS3_MATCH_ID_AV_SETTINGS:
60 case PS3_MATCH_ID_SYSTEM_MANAGER:
61 + case PS3_MATCH_ID_DISP_MANAGER:
62 pr_debug("%s:%d: unsupported match_id: %u\n", __func__,
63 __LINE__, dev->match_id);
64 pr_debug("%s:%d: bus_id: %llu\n", __func__, __LINE__,
65 --- a/arch/powerpc/platforms/ps3/device-init.c 2012-01-26 14:09:41.144403930 +0100
66 +++ b/arch/powerpc/platforms/ps3/device-init.c 2012-01-26 14:25:10.440202587 +0100
67 @@ -426,6 +426,7 @@
69 int result;
70 unsigned int port_number;
71 + u64 lpar_id, laid, junk;
73 pr_debug(" -> %s:%d\n", __func__, __LINE__);
75 @@ -444,6 +445,27 @@
76 port_number);
77 WARN_ON(result);
79 + result = lv1_get_logical_partition_id(&lpar_id);
80 + if (result)
81 + goto out;
83 + result = lv1_read_repository_node(1, 0x0000000073730000ul /* ss */,
84 + 0x6c61696400000000ul /* laid */,
85 + lpar_id,
86 + 0, &laid, &junk);
87 + if (result)
88 + goto out;
90 + if (laid == 0x1070000002000001ul) {
91 + port_number = 10;
92 + result = ps3_setup_vuart_device(PS3_MATCH_ID_DISP_MANAGER,
93 + port_number);
94 + }
96 +out:
98 + WARN_ON(result);
100 pr_debug(" <- %s:%d\n", __func__, __LINE__);
101 return result;
103 --- a/drivers/ps3/Makefile 2012-01-12 20:42:45.000000000 +0100
104 +++ b/drivers/ps3/Makefile 2012-01-26 17:40:36.400861141 +0100
105 @@ -5,3 +5,4 @@
106 obj-$(CONFIG_PS3_SYS_MANAGER) += ps3-sys-manager.o
107 obj-$(CONFIG_PS3_STORAGE) += ps3stor_lib.o
108 obj-$(CONFIG_PS3_LPM) += ps3-lpm.o
109 +obj-$(CONFIG_PS3_DISP_MANAGER) += ps3-disp-manager.o
110 --- a/arch/powerpc/platforms/ps3/Kconfig 2012-01-26 17:37:55.331589081 +0100
111 +++ b/arch/powerpc/platforms/ps3/Kconfig 2012-01-26 17:42:48.049593001 +0100
112 @@ -88,6 +88,17 @@
113 This support is required for system control. In
114 general, all users will say Y or M.
116 +config PS3_DISP_MANAGER
117 + depends on PPC_PS3
118 + tristate "PS3 Dispatcher Manager driver" if PS3_ADVANCED
119 + select PS3_VUART
120 + default y
121 + help
122 + Include support for the PS3 Dispatcher Manager.
124 + This support is required to access the PS3 SS services.
125 + In general, all users will say Y or M.
127 config PS3_STORAGE
128 depends on PPC_PS3
129 tristate
130 --- /dev/null 2011-11-07 10:16:29.227396409 +0100
131 +++ b/drivers/ps3/ps3-disp-manager.c 2012-01-26 15:08:35.100453068 +0100
132 @@ -0,0 +1,196 @@
134 + * PS3 Dispatcher Manager.
136 + * Copyright (C) 2011 graf_chokolo <grafchokolo@gmail.com>.
137 + * Copyright (C) 2011, 2012 glevand <geoffrey.levand@mail.ru>.
139 + * This program is free software; you can redistribute it and/or modify
140 + * it under the terms of the GNU General Public License as published by
141 + * the Free Software Foundation; version 2 of the License.
143 + * This program is distributed in the hope that it will be useful,
144 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
145 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
146 + * GNU General Public License for more details.
148 + * You should have received a copy of the GNU General Public License
149 + * along with this program; if not, write to the Free Software
150 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
151 + */
153 +#include <linux/kernel.h>
154 +#include <linux/module.h>
155 +#include <linux/slab.h>
156 +#include <linux/uaccess.h>
157 +#include <linux/fs.h>
158 +#include <linux/miscdevice.h>
160 +#include <asm/firmware.h>
161 +#include <asm/lv1call.h>
162 +#include <asm/ps3.h>
164 +#include "vuart.h"
166 +#define DEVICE_NAME "ps3dispmngr"
168 +static struct ps3dm {
169 + struct ps3_system_bus_device *dev;
170 + struct miscdevice misc;
171 +} *ps3dm;
173 +static ssize_t ps3_disp_manager_read(struct file *file, char __user *usrbuf,
174 + size_t count, loff_t *pos)
176 + char *buf;
177 + int result;
179 + buf = kmalloc(count, GFP_KERNEL);
180 + if (!buf)
181 + return -ENOMEM;
183 + result = ps3_vuart_read(ps3dm->dev, buf, count);
184 + if (result)
185 + goto out;
187 + if (copy_to_user(usrbuf, buf, count)) {
188 + result = -EFAULT;
189 + goto out;
192 + result = count;
194 +out:
196 + kfree(buf);
198 + return result;
201 +static ssize_t ps3_disp_manager_write(struct file *file, const char __user *usrbuf,
202 + size_t count, loff_t *pos)
204 + char *buf;
205 + int result;
207 + buf = kmalloc(count, GFP_KERNEL);
208 + if (!buf)
209 + return -ENOMEM;
211 + if (copy_from_user(buf, usrbuf, count)) {
212 + result = -EFAULT;
213 + goto out;
216 + result = ps3_vuart_write(ps3dm->dev, buf, count);
217 + if (result)
218 + goto out;
220 + result = count;
222 +out:
224 + kfree(buf);
226 + return result;
229 +static const struct file_operations ps3_disp_manager_fops = {
230 + .owner = THIS_MODULE,
231 + .read = ps3_disp_manager_read,
232 + .write = ps3_disp_manager_write,
235 +static int ps3_disp_manager_probe(struct ps3_system_bus_device *dev)
237 + int result;
239 + dev_dbg(&dev->core, "%s:%d\n", __func__, __LINE__);
241 + if (ps3dm) {
242 + dev_err(&dev->core, "Only one Dispatcher Manager is supported\n");
243 + return -EBUSY;
246 + ps3dm = kzalloc(sizeof(*ps3dm), GFP_KERNEL);
247 + if (!ps3dm)
248 + return -ENOMEM;
250 + ps3dm->dev = dev;
252 + ps3dm->misc.parent = &dev->core;
253 + ps3dm->misc.minor = MISC_DYNAMIC_MINOR,
254 + ps3dm->misc.name = DEVICE_NAME,
255 + ps3dm->misc.fops = &ps3_disp_manager_fops,
257 + result = misc_register(&ps3dm->misc);
258 + if (result) {
259 + dev_err(&dev->core, "%s:%u: misc_register failed %d\n",
260 + __func__, __LINE__, result);
261 + goto fail;
264 + dev_info(&dev->core, "%s:%u: registered misc device %d\n",
265 + __func__, __LINE__, ps3dm->misc.minor);
267 + dev_dbg(&dev->core, "%s:%d\n", __func__, __LINE__);
269 + return 0;
271 +fail:
273 + kfree(ps3dm);
274 + ps3dm = NULL;
276 + return result;
279 +static int ps3_disp_manager_remove(struct ps3_system_bus_device *dev)
281 + dev_dbg(&dev->core, "%s:%d\n", __func__, __LINE__);
283 + if (ps3dm) {
284 + misc_deregister(&ps3dm->misc);
285 + kfree(ps3dm);
286 + ps3dm = NULL;
289 + return 0;
292 +static void ps3_disp_manager_shutdown(struct ps3_system_bus_device *dev)
294 + dev_dbg(&dev->core, "%s:%d\n", __func__, __LINE__);
297 +static struct ps3_vuart_port_driver ps3_disp_manager = {
298 + .core.match_id = PS3_MATCH_ID_DISP_MANAGER,
299 + .core.core.name = "ps3_disp_manager",
300 + .probe = ps3_disp_manager_probe,
301 + .remove = ps3_disp_manager_remove,
302 + .shutdown = ps3_disp_manager_shutdown,
305 +static int __init ps3_disp_manager_init(void)
307 + if (!firmware_has_feature(FW_FEATURE_PS3_LV1))
308 + return -ENODEV;
310 + return ps3_vuart_port_driver_register(&ps3_disp_manager);
313 +static void __exit ps3_disp_manager_exit(void)
315 + pr_debug(" -> %s:%d\n", __func__, __LINE__);
317 + ps3_vuart_port_driver_unregister(&ps3_disp_manager);
319 + pr_debug(" <- %s:%d\n", __func__, __LINE__);
322 +module_init(ps3_disp_manager_init);
323 +module_exit(ps3_disp_manager_exit);
325 +MODULE_AUTHOR("glevand");
326 +MODULE_LICENSE("GPL v2");
327 +MODULE_DESCRIPTION("PS3 Dispatcher Manager");
328 +MODULE_ALIAS(PS3_MODULE_ALIAS_DISP_MANAGER);