xref: /kvmtool/framebuffer.c (revision 48d9e01a8cfb8541c32c1dd46fa9d34fc687b031)
1 #include "kvm/framebuffer.h"
2 
3 #include <linux/kernel.h>
4 #include <linux/list.h>
5 #include <stdlib.h>
6 #include <sys/mman.h>
7 #include <errno.h>
8 
9 static LIST_HEAD(framebuffers);
10 
11 struct framebuffer *fb__register(struct framebuffer *fb)
12 {
13 	INIT_LIST_HEAD(&fb->node);
14 	list_add(&fb->node, &framebuffers);
15 
16 	return fb;
17 }
18 
19 int fb__attach(struct framebuffer *fb, struct fb_target_operations *ops)
20 {
21 	if (fb->nr_targets >= FB_MAX_TARGETS)
22 		return -ENOSPC;
23 
24 	fb->targets[fb->nr_targets++] = ops;
25 
26 	return 0;
27 }
28 
29 static int start_targets(struct framebuffer *fb)
30 {
31 	unsigned long i;
32 
33 	for (i = 0; i < fb->nr_targets; i++) {
34 		struct fb_target_operations *ops = fb->targets[i];
35 		int err = 0;
36 
37 		if (ops->start)
38 			err = ops->start(fb);
39 
40 		if (err)
41 			return err;
42 	}
43 
44 	return 0;
45 }
46 
47 int fb__start(void)
48 {
49 	struct framebuffer *fb;
50 
51 	list_for_each_entry(fb, &framebuffers, node) {
52 		int err;
53 
54 		err = start_targets(fb);
55 		if (err)
56 			return err;
57 	}
58 
59 	return 0;
60 }
61 
62 void fb__stop(void)
63 {
64 	struct framebuffer *fb;
65 
66 	list_for_each_entry(fb, &framebuffers, node) {
67 		u32 i;
68 
69 		for (i = 0; i < fb->nr_targets; i++)
70 			if (fb->targets[i]->stop)
71 				fb->targets[i]->stop(fb);
72 
73 		munmap(fb->mem, fb->mem_size);
74 	}
75 }
76