20 #include <linux/module.h>
28 #include <linux/pci.h>
60 #define ID_BIT_AUDIO 0x100
61 #define client_is_audio(c) ((c)->id & ID_BIT_AUDIO)
62 #define client_is_vga(c) ((c)->id == -1 || !client_is_audio(c))
63 #define client_id(c) ((c)->id & ~ID_BIT_AUDIO)
73 static bool vga_switcheroo_ready(
void)
76 return !vgasr_priv.
active &&
80 static void vga_switcheroo_enable(
void)
92 ret = vgasr_priv.
handler->get_client_id(client->
pdev);
98 vga_switcheroo_debugfs_init(&vgasr_priv);
111 if (vga_switcheroo_ready()) {
113 vga_switcheroo_enable();
125 pr_info(
"vga_switcheroo: disabled\n");
126 vga_switcheroo_debugfs_fini(&vgasr_priv);
127 vgasr_priv.
active =
false;
139 client = kzalloc(
sizeof(*client),
GFP_KERNEL);
154 if (vga_switcheroo_ready()) {
156 vga_switcheroo_enable();
165 return register_client(pdev, ops, -1,
174 return register_client(pdev, ops,
id |
ID_BIT_AUDIO, active);
183 if (client->pdev == pdev)
193 if (client->
id == client_id)
212 client = find_client_from_pci(&vgasr_priv.
clients, pdev);
226 client = find_client_from_pci(&vgasr_priv.
clients, pdev);
235 vga_switcheroo_debugfs_fini(&vgasr_priv);
236 vgasr_priv.
active =
false;
248 client = find_client_from_pci(&vgasr_priv.
clients, pdev);
255 static int vga_switcheroo_show(
struct seq_file *
m,
void *
v)
264 client->
active ?
'+' :
' ',
266 pci_name(client->
pdev));
275 return single_open(file, vga_switcheroo_show, NULL);
280 if (vgasr_priv.
handler->power_state)
292 if (vgasr_priv.
handler->power_state)
298 static void set_audio_state(
int id,
int state)
303 if (client && client->
pwr_state != state) {
304 client->
ops->set_gpu_state(client->
pdev, state);
314 active = find_active_client(&vgasr_priv.
clients);
319 vga_switchon(new_client);
331 active = find_active_client(&vgasr_priv.
clients);
341 event.info = new_client->
fb_info;
345 ret = vgasr_priv.
handler->switchto(new_client->
id);
349 if (new_client->
ops->reprobe)
350 new_client->
ops->reprobe(new_client->
pdev);
353 vga_switchoff(active);
357 new_client->
active =
true;
361 static bool check_can_switch(
void)
366 if (!client->
ops->can_switch(client->
pdev)) {
375 vga_switcheroo_debugfs_write(
struct file *filp,
const char __user *ubuf,
376 size_t cnt, loff_t *ppos)
379 const char *pdev_name;
381 bool delay =
false, can_switch;
382 bool just_mux =
false;
400 if (
strncmp(usercmd,
"OFF", 3) == 0) {
406 vga_switchoff(client);
411 if (
strncmp(usercmd,
"ON", 2) == 0) {
416 vga_switchon(client);
423 if (
strncmp(usercmd,
"DIGD", 4) == 0) {
428 if (
strncmp(usercmd,
"DDIS", 4) == 0) {
433 if (
strncmp(usercmd,
"IGD", 3) == 0)
436 if (
strncmp(usercmd,
"DIS", 3) == 0)
439 if (
strncmp(usercmd,
"MIGD", 4) == 0) {
443 if (
strncmp(usercmd,
"MDIS", 4) == 0) {
450 client = find_client_from_id(&vgasr_priv.
clients, client_id);
457 ret = vgasr_priv.
handler->switchto(client_id);
465 can_switch = check_can_switch();
467 if (can_switch ==
false && delay ==
false)
471 pdev_name = pci_name(client->
pdev);
472 ret = vga_switchto_stage1(client);
474 printk(
KERN_ERR "vga_switcheroo: switching failed stage 1 %d\n", ret);
476 ret = vga_switchto_stage2(client);
478 printk(
KERN_ERR "vga_switcheroo: switching failed stage 2 %d\n", ret);
481 printk(
KERN_INFO "vga_switcheroo: setting delayed switch to client %d\n", client->
id);
485 ret = vga_switchto_stage1(client);
487 printk(
KERN_ERR "vga_switcheroo: delayed switching stage 1 failed %d\n", ret);
497 .open = vga_switcheroo_debugfs_open,
498 .write = vga_switcheroo_debugfs_write,
504 static void vga_switcheroo_debugfs_fini(
struct vgasr_priv *
priv)
516 static int vga_switcheroo_debugfs_init(
struct vgasr_priv *priv)
524 printk(
KERN_ERR "vga_switcheroo: Cannot create /sys/kernel/debug/vgaswitcheroo\n");
529 priv->
debugfs_root, NULL, &vga_switcheroo_debugfs_fops);
531 printk(
KERN_ERR "vga_switcheroo: cannot create /sys/kernel/debug/vgaswitcheroo/switch\n");
536 vga_switcheroo_debugfs_fini(priv);
543 const char *pdev_name;
553 client = find_client_from_id(&vgasr_priv.
clients,
555 if (!client || !check_can_switch())
558 pdev_name = pci_name(client->
pdev);
559 ret = vga_switchto_stage2(client);
561 printk(
KERN_ERR "vga_switcheroo: delayed switching failed stage 2 %d\n", ret);