ps2: migration support for command reply queue
[qemu/ar7.git] / ui / clipboard.c
blobd7b008d62a07735b07f8ed85e820f5ce2f090351
1 #include "qemu/osdep.h"
2 #include "ui/clipboard.h"
4 static NotifierList clipboard_notifiers =
5 NOTIFIER_LIST_INITIALIZER(clipboard_notifiers);
7 static QemuClipboardInfo *cbinfo[QEMU_CLIPBOARD_SELECTION__COUNT];
9 void qemu_clipboard_peer_register(QemuClipboardPeer *peer)
11 notifier_list_add(&clipboard_notifiers, &peer->update);
14 void qemu_clipboard_peer_unregister(QemuClipboardPeer *peer)
16 int i;
18 for (i = 0; i < QEMU_CLIPBOARD_SELECTION__COUNT; i++) {
19 qemu_clipboard_peer_release(peer, i);
22 notifier_remove(&peer->update);
25 bool qemu_clipboard_peer_owns(QemuClipboardPeer *peer,
26 QemuClipboardSelection selection)
28 QemuClipboardInfo *info = qemu_clipboard_info(selection);
30 return info && info->owner == peer;
33 void qemu_clipboard_peer_release(QemuClipboardPeer *peer,
34 QemuClipboardSelection selection)
36 g_autoptr(QemuClipboardInfo) info = NULL;
38 if (qemu_clipboard_peer_owns(peer, selection)) {
39 /* set empty clipboard info */
40 info = qemu_clipboard_info_new(NULL, selection);
41 qemu_clipboard_update(info);
45 void qemu_clipboard_update(QemuClipboardInfo *info)
47 g_autoptr(QemuClipboardInfo) old = NULL;
48 assert(info->selection < QEMU_CLIPBOARD_SELECTION__COUNT);
50 notifier_list_notify(&clipboard_notifiers, info);
52 old = cbinfo[info->selection];
53 cbinfo[info->selection] = qemu_clipboard_info_ref(info);
56 QemuClipboardInfo *qemu_clipboard_info(QemuClipboardSelection selection)
58 assert(selection < QEMU_CLIPBOARD_SELECTION__COUNT);
60 return cbinfo[selection];
63 QemuClipboardInfo *qemu_clipboard_info_new(QemuClipboardPeer *owner,
64 QemuClipboardSelection selection)
66 QemuClipboardInfo *info = g_new0(QemuClipboardInfo, 1);
68 info->owner = owner;
69 info->selection = selection;
70 info->refcount = 1;
72 return info;
75 QemuClipboardInfo *qemu_clipboard_info_ref(QemuClipboardInfo *info)
77 info->refcount++;
78 return info;
81 void qemu_clipboard_info_unref(QemuClipboardInfo *info)
83 uint32_t type;
85 if (!info) {
86 return;
89 info->refcount--;
90 if (info->refcount > 0) {
91 return;
94 for (type = 0; type < QEMU_CLIPBOARD_TYPE__COUNT; type++) {
95 g_free(info->types[type].data);
97 g_free(info);
100 void qemu_clipboard_request(QemuClipboardInfo *info,
101 QemuClipboardType type)
103 if (info->types[type].data ||
104 info->types[type].requested ||
105 !info->types[type].available ||
106 !info->owner)
107 return;
109 info->types[type].requested = true;
110 info->owner->request(info, type);
113 void qemu_clipboard_set_data(QemuClipboardPeer *peer,
114 QemuClipboardInfo *info,
115 QemuClipboardType type,
116 uint32_t size,
117 const void *data,
118 bool update)
120 if (!info ||
121 info->owner != peer) {
122 return;
125 g_free(info->types[type].data);
126 info->types[type].data = g_memdup(data, size);
127 info->types[type].size = size;
128 info->types[type].available = true;
130 if (update) {
131 qemu_clipboard_update(info);