File: | randr/rrproviderproperty.c |
Location: | line 448, column 17 |
Description: | Result of 'malloc' is converted to a pointer of type 'char', which is incompatible with sizeof operand type 'INT32' |
1 | /* |
2 | * Copyright © 2006 Keith Packard |
3 | * |
4 | * Permission to use, copy, modify, distribute, and sell this software and its |
5 | * documentation for any purpose is hereby granted without fee, provided that |
6 | * the above copyright notice appear in all copies and that both that copyright |
7 | * notice and this permission notice appear in supporting documentation, and |
8 | * that the name of the copyright holders not be used in advertising or |
9 | * publicity pertaining to distribution of the software without specific, |
10 | * written prior permission. The copyright holders make no representations |
11 | * about the suitability of this software for any purpose. It is provided "as |
12 | * is" without express or implied warranty. |
13 | * |
14 | * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, |
15 | * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO |
16 | * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR |
17 | * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, |
18 | * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER |
19 | * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE |
20 | * OF THIS SOFTWARE. |
21 | */ |
22 | |
23 | #include "randrstr.h" |
24 | #include "propertyst.h" |
25 | #include "swaprep.h" |
26 | |
27 | static int |
28 | DeliverPropertyEvent(WindowPtr pWin, void *value) |
29 | { |
30 | xRRProviderPropertyNotifyEvent *event = value; |
31 | RREventPtr *pHead, pRREvent; |
32 | |
33 | dixLookupResourceByType((void **) &pHead, pWin->drawable.id, |
34 | RREventType, serverClient, DixReadAccess(1<<0)); |
35 | if (!pHead) |
36 | return WT_WALKCHILDREN1; |
37 | |
38 | for (pRREvent = *pHead; pRREvent; pRREvent = pRREvent->next) { |
39 | if (!(pRREvent->mask & RRProviderPropertyNotifyMask(1L << 5))) |
40 | continue; |
41 | |
42 | event->window = pRREvent->window->drawable.id; |
43 | WriteEventsToClient(pRREvent->client, 1, (xEvent *) event); |
44 | } |
45 | |
46 | return WT_WALKCHILDREN1; |
47 | } |
48 | |
49 | static void |
50 | RRDeliverPropertyEvent(ScreenPtr pScreen, xEvent *event) |
51 | { |
52 | if (!(dispatchException & (DE_RESET1 | DE_TERMINATE2))) |
53 | WalkTree(pScreen, DeliverPropertyEvent, event); |
54 | } |
55 | |
56 | static void |
57 | RRDestroyProviderProperty(RRPropertyPtr prop) |
58 | { |
59 | free(prop->valid_values); |
60 | free(prop->current.data); |
61 | free(prop->pending.data); |
62 | free(prop); |
63 | } |
64 | |
65 | static void |
66 | RRDeleteProperty(RRProviderRec * provider, RRPropertyRec * prop) |
67 | { |
68 | xRRProviderPropertyNotifyEvent event = { |
69 | .type = RREventBase + RRNotify1, |
70 | .subCode = RRNotify_ProviderProperty4, |
71 | .provider = provider->id, |
72 | .state = PropertyDelete1, |
73 | .atom = prop->propertyName, |
74 | .timestamp = currentTime.milliseconds |
75 | }; |
76 | |
77 | RRDeliverPropertyEvent(provider->pScreen, (xEvent *) &event); |
78 | |
79 | RRDestroyProviderProperty(prop); |
80 | } |
81 | |
82 | void |
83 | RRDeleteAllProviderProperties(RRProviderPtr provider) |
84 | { |
85 | RRPropertyPtr prop, next; |
86 | |
87 | for (prop = provider->properties; prop; prop = next) { |
88 | next = prop->next; |
89 | RRDeleteProperty(provider, prop); |
90 | } |
91 | } |
92 | |
93 | static void |
94 | RRInitProviderPropertyValue(RRPropertyValuePtr property_value) |
95 | { |
96 | property_value->type = None0L; |
97 | property_value->format = 0; |
98 | property_value->size = 0; |
99 | property_value->data = NULL((void*)0); |
100 | } |
101 | |
102 | static RRPropertyPtr |
103 | RRCreateProviderProperty(Atom property) |
104 | { |
105 | RRPropertyPtr prop; |
106 | |
107 | prop = (RRPropertyPtr) malloc(sizeof(RRPropertyRec)); |
108 | if (!prop) |
109 | return NULL((void*)0); |
110 | prop->next = NULL((void*)0); |
111 | prop->propertyName = property; |
112 | prop->is_pending = FALSE0; |
113 | prop->range = FALSE0; |
114 | prop->immutable = FALSE0; |
115 | prop->num_valid = 0; |
116 | prop->valid_values = NULL((void*)0); |
117 | RRInitProviderPropertyValue(&prop->current); |
118 | RRInitProviderPropertyValue(&prop->pending); |
119 | return prop; |
120 | } |
121 | |
122 | void |
123 | RRDeleteProviderProperty(RRProviderPtr provider, Atom property) |
124 | { |
125 | RRPropertyRec *prop, **prev; |
126 | |
127 | for (prev = &provider->properties; (prop = *prev); prev = &(prop->next)) |
128 | if (prop->propertyName == property) { |
129 | *prev = prop->next; |
130 | RRDeleteProperty(provider, prop); |
131 | return; |
132 | } |
133 | } |
134 | |
135 | int |
136 | RRChangeProviderProperty(RRProviderPtr provider, Atom property, Atom type, |
137 | int format, int mode, unsigned long len, |
138 | void *value, Bool sendevent, Bool pending) |
139 | { |
140 | RRPropertyPtr prop; |
141 | rrScrPrivPtr pScrPriv = rrGetScrPriv(provider->pScreen)((rrScrPrivPtr)dixLookupPrivate(&(provider->pScreen)-> devPrivates, (&rrPrivKeyRec))); |
142 | int size_in_bytes; |
143 | int total_size; |
144 | unsigned long total_len; |
145 | RRPropertyValuePtr prop_value; |
146 | RRPropertyValueRec new_value; |
147 | Bool add = FALSE0; |
148 | |
149 | size_in_bytes = format >> 3; |
150 | |
151 | /* first see if property already exists */ |
152 | prop = RRQueryProviderProperty(provider, property); |
153 | if (!prop) { /* just add to list */ |
154 | prop = RRCreateProviderProperty(property); |
155 | if (!prop) |
156 | return BadAlloc11; |
157 | add = TRUE1; |
158 | mode = PropModeReplace0; |
159 | } |
160 | if (pending && prop->is_pending) |
161 | prop_value = &prop->pending; |
162 | else |
163 | prop_value = &prop->current; |
164 | |
165 | /* To append or prepend to a property the request format and type |
166 | must match those of the already defined property. The |
167 | existing format and type are irrelevant when using the mode |
168 | "PropModeReplace" since they will be written over. */ |
169 | |
170 | if ((format != prop_value->format) && (mode != PropModeReplace0)) |
171 | return BadMatch8; |
172 | if ((prop_value->type != type) && (mode != PropModeReplace0)) |
173 | return BadMatch8; |
174 | new_value = *prop_value; |
175 | if (mode == PropModeReplace0) |
176 | total_len = len; |
177 | else |
178 | total_len = prop_value->size + len; |
179 | |
180 | if (mode == PropModeReplace0 || len > 0) { |
181 | void *new_data = NULL((void*)0), *old_data = NULL((void*)0); |
182 | |
183 | total_size = total_len * size_in_bytes; |
184 | new_value.data = (void *) malloc(total_size); |
185 | if (!new_value.data && total_size) { |
186 | if (add) |
187 | RRDestroyProviderProperty(prop); |
188 | return BadAlloc11; |
189 | } |
190 | new_value.size = len; |
191 | new_value.type = type; |
192 | new_value.format = format; |
193 | |
194 | switch (mode) { |
195 | case PropModeReplace0: |
196 | new_data = new_value.data; |
197 | old_data = NULL((void*)0); |
198 | break; |
199 | case PropModeAppend2: |
200 | new_data = (void *) (((char *) new_value.data) + |
201 | (prop_value->size * size_in_bytes)); |
202 | old_data = new_value.data; |
203 | break; |
204 | case PropModePrepend1: |
205 | new_data = new_value.data; |
206 | old_data = (void *) (((char *) new_value.data) + |
207 | (prop_value->size * size_in_bytes)); |
208 | break; |
209 | } |
210 | if (new_data) |
211 | memcpy((char *) new_data, (char *) value, len * size_in_bytes)__builtin___memcpy_chk ((char *) new_data, (char *) value, len * size_in_bytes, __builtin_object_size ((char *) new_data, 0 )); |
212 | if (old_data) |
213 | memcpy((char *) old_data, (char *) prop_value->data,__builtin___memcpy_chk ((char *) old_data, (char *) prop_value ->data, prop_value->size * size_in_bytes, __builtin_object_size ((char *) old_data, 0)) |
214 | prop_value->size * size_in_bytes)__builtin___memcpy_chk ((char *) old_data, (char *) prop_value ->data, prop_value->size * size_in_bytes, __builtin_object_size ((char *) old_data, 0)); |
215 | |
216 | if (pending && pScrPriv->rrProviderSetProperty && |
217 | !pScrPriv->rrProviderSetProperty(provider->pScreen, provider, |
218 | prop->propertyName, &new_value)) { |
219 | if (add) |
220 | RRDestroyProviderProperty(prop); |
221 | free(new_value.data); |
222 | return BadValue2; |
223 | } |
224 | free(prop_value->data); |
225 | *prop_value = new_value; |
226 | } |
227 | |
228 | else if (len == 0) { |
229 | /* do nothing */ |
230 | } |
231 | |
232 | if (add) { |
233 | prop->next = provider->properties; |
234 | provider->properties = prop; |
235 | } |
236 | |
237 | if (pending && prop->is_pending) |
238 | provider->pendingProperties = TRUE1; |
239 | |
240 | if (sendevent) { |
241 | xRRProviderPropertyNotifyEvent event = { |
242 | .type = RREventBase + RRNotify1, |
243 | .subCode = RRNotify_ProviderProperty4, |
244 | .provider = provider->id, |
245 | .state = PropertyNewValue0, |
246 | .atom = prop->propertyName, |
247 | .timestamp = currentTime.milliseconds |
248 | }; |
249 | RRDeliverPropertyEvent(provider->pScreen, (xEvent *) &event); |
250 | } |
251 | return Success0; |
252 | } |
253 | |
254 | Bool |
255 | RRPostProviderPendingProperties(RRProviderPtr provider) |
256 | { |
257 | RRPropertyValuePtr pending_value; |
258 | RRPropertyValuePtr current_value; |
259 | RRPropertyPtr property; |
260 | Bool ret = TRUE1; |
261 | |
262 | if (!provider->pendingProperties) |
263 | return TRUE1; |
264 | |
265 | provider->pendingProperties = FALSE0; |
266 | for (property = provider->properties; property; property = property->next) { |
267 | /* Skip non-pending properties */ |
268 | if (!property->is_pending) |
269 | continue; |
270 | |
271 | pending_value = &property->pending; |
272 | current_value = &property->current; |
273 | |
274 | /* |
275 | * If the pending and current values are equal, don't mark it |
276 | * as changed (which would deliver an event) |
277 | */ |
278 | if (pending_value->type == current_value->type && |
279 | pending_value->format == current_value->format && |
280 | pending_value->size == current_value->size && |
281 | !memcmp(pending_value->data, current_value->data, |
282 | pending_value->size * (pending_value->format / 8))) |
283 | continue; |
284 | |
285 | if (RRChangeProviderProperty(provider, property->propertyName, |
286 | pending_value->type, pending_value->format, |
287 | PropModeReplace0, pending_value->size, |
288 | pending_value->data, TRUE1, FALSE0) != Success0) |
289 | ret = FALSE0; |
290 | } |
291 | return ret; |
292 | } |
293 | |
294 | RRPropertyPtr |
295 | RRQueryProviderProperty(RRProviderPtr provider, Atom property) |
296 | { |
297 | RRPropertyPtr prop; |
298 | |
299 | for (prop = provider->properties; prop; prop = prop->next) |
300 | if (prop->propertyName == property) |
301 | return prop; |
302 | return NULL((void*)0); |
303 | } |
304 | |
305 | RRPropertyValuePtr |
306 | RRGetProviderProperty(RRProviderPtr provider, Atom property, Bool pending) |
307 | { |
308 | RRPropertyPtr prop = RRQueryProviderProperty(provider, property); |
309 | rrScrPrivPtr pScrPriv = rrGetScrPriv(provider->pScreen)((rrScrPrivPtr)dixLookupPrivate(&(provider->pScreen)-> devPrivates, (&rrPrivKeyRec))); |
310 | |
311 | if (!prop) |
312 | return NULL((void*)0); |
313 | if (pending && prop->is_pending) |
314 | return &prop->pending; |
315 | else { |
316 | #if RANDR_13_INTERFACE1 |
317 | /* If we can, try to update the property value first */ |
318 | if (pScrPriv->rrProviderGetProperty) |
319 | pScrPriv->rrProviderGetProperty(provider->pScreen, provider, |
320 | prop->propertyName); |
321 | #endif |
322 | return &prop->current; |
323 | } |
324 | } |
325 | |
326 | int |
327 | RRConfigureProviderProperty(RRProviderPtr provider, Atom property, |
328 | Bool pending, Bool range, Bool immutable, |
329 | int num_values, INT32 *values) |
330 | { |
331 | RRPropertyPtr prop = RRQueryProviderProperty(provider, property); |
332 | Bool add = FALSE0; |
333 | INT32 *new_values; |
334 | |
335 | if (!prop) { |
336 | prop = RRCreateProviderProperty(property); |
337 | if (!prop) |
338 | return BadAlloc11; |
339 | add = TRUE1; |
340 | } |
341 | else if (prop->immutable && !immutable) |
342 | return BadAccess10; |
343 | |
344 | /* |
345 | * ranges must have even number of values |
346 | */ |
347 | if (range && (num_values & 1)) { |
348 | if (add) |
349 | RRDestroyProviderProperty(prop); |
350 | return BadMatch8; |
351 | } |
352 | |
353 | new_values = malloc(num_values * sizeof(INT32)); |
354 | if (!new_values && num_values) { |
355 | if (add) |
356 | RRDestroyProviderProperty(prop); |
357 | return BadAlloc11; |
358 | } |
359 | if (num_values) |
360 | memcpy(new_values, values, num_values * sizeof(INT32))__builtin___memcpy_chk (new_values, values, num_values * sizeof (INT32), __builtin_object_size (new_values, 0)); |
361 | |
362 | /* |
363 | * Property moving from pending to non-pending |
364 | * loses any pending values |
365 | */ |
366 | if (prop->is_pending && !pending) { |
367 | free(prop->pending.data); |
368 | RRInitProviderPropertyValue(&prop->pending); |
369 | } |
370 | |
371 | prop->is_pending = pending; |
372 | prop->range = range; |
373 | prop->immutable = immutable; |
374 | prop->num_valid = num_values; |
375 | free(prop->valid_values); |
376 | prop->valid_values = new_values; |
377 | |
378 | if (add) { |
379 | prop->next = provider->properties; |
380 | provider->properties = prop; |
381 | } |
382 | |
383 | return Success0; |
384 | } |
385 | |
386 | int |
387 | ProcRRListProviderProperties(ClientPtr client) |
388 | { |
389 | REQUEST(xRRListProviderPropertiesReq)xRRListProviderPropertiesReq *stuff = (xRRListProviderPropertiesReq *)client->requestBuffer; |
390 | Atom *pAtoms = NULL((void*)0), *temppAtoms; |
391 | xRRListProviderPropertiesReply rep; |
392 | int numProps = 0; |
393 | RRProviderPtr provider; |
394 | RRPropertyPtr prop; |
395 | |
396 | REQUEST_SIZE_MATCH(xRRListProviderPropertiesReq)if ((sizeof(xRRListProviderPropertiesReq) >> 2) != client ->req_len) return(16); |
397 | |
398 | VERIFY_RR_PROVIDER(stuff->provider, provider, DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, (1<<0)); if (rc != 0) { client->errorValue = stuff->provider; return rc; } }; |
399 | |
400 | for (prop = provider->properties; prop; prop = prop->next) |
401 | numProps++; |
402 | if (numProps) |
403 | if (!(pAtoms = (Atom *) malloc(numProps * sizeof(Atom)))) |
404 | return BadAlloc11; |
405 | |
406 | rep = (xRRListProviderPropertiesReply) { |
407 | .type = X_Reply1, |
408 | .sequenceNumber = client->sequence, |
409 | .length = bytes_to_int32(numProps * sizeof(Atom)), |
410 | .nAtoms = numProps |
411 | }; |
412 | if (client->swapped) { |
413 | swaps(&rep.sequenceNumber)do { if (sizeof(*(&rep.sequenceNumber)) != 2) wrong_size( ); if (__builtin_constant_p((uintptr_t)(&rep.sequenceNumber ) & 1) && ((uintptr_t)(&rep.sequenceNumber) & 1) == 0) *(&rep.sequenceNumber) = lswaps(*(&rep.sequenceNumber )); else swap_uint16((uint16_t *)(&rep.sequenceNumber)); } while (0); |
414 | swapl(&rep.length)do { if (sizeof(*(&rep.length)) != 4) wrong_size(); if (__builtin_constant_p ((uintptr_t)(&rep.length) & 3) && ((uintptr_t )(&rep.length) & 3) == 0) *(&rep.length) = lswapl (*(&rep.length)); else swap_uint32((uint32_t *)(&rep. length)); } while (0); |
415 | swaps(&rep.nAtoms)do { if (sizeof(*(&rep.nAtoms)) != 2) wrong_size(); if (__builtin_constant_p ((uintptr_t)(&rep.nAtoms) & 1) && ((uintptr_t )(&rep.nAtoms) & 1) == 0) *(&rep.nAtoms) = lswaps (*(&rep.nAtoms)); else swap_uint16((uint16_t *)(&rep. nAtoms)); } while (0); |
416 | } |
417 | temppAtoms = pAtoms; |
418 | for (prop = provider->properties; prop; prop = prop->next) |
419 | *temppAtoms++ = prop->propertyName; |
420 | |
421 | WriteToClient(client, sizeof(xRRListProviderPropertiesReply), (char *) &rep); |
422 | if (numProps) { |
423 | client->pSwapReplyFunc = (ReplySwapPtr) Swap32Write; |
424 | WriteSwappedDataToClient(client, numProps * sizeof(Atom), pAtoms)if ((client)->swapped) (*(client)->pSwapReplyFunc)(client , (int)(numProps * sizeof(Atom)), pAtoms); else WriteToClient (client, (int)(numProps * sizeof(Atom)), (pAtoms));; |
425 | free(pAtoms); |
426 | } |
427 | return Success0; |
428 | } |
429 | |
430 | int |
431 | ProcRRQueryProviderProperty(ClientPtr client) |
432 | { |
433 | REQUEST(xRRQueryProviderPropertyReq)xRRQueryProviderPropertyReq *stuff = (xRRQueryProviderPropertyReq *)client->requestBuffer; |
434 | xRRQueryProviderPropertyReply rep; |
435 | RRProviderPtr provider; |
436 | RRPropertyPtr prop; |
437 | char *extra = NULL((void*)0); |
438 | |
439 | REQUEST_SIZE_MATCH(xRRQueryProviderPropertyReq)if ((sizeof(xRRQueryProviderPropertyReq) >> 2) != client ->req_len) return(16); |
440 | |
441 | VERIFY_RR_PROVIDER(stuff->provider, provider, DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, (1<<0)); if (rc != 0) { client->errorValue = stuff->provider; return rc; } }; |
442 | |
443 | prop = RRQueryProviderProperty(provider, stuff->property); |
444 | if (!prop) |
445 | return BadName15; |
446 | |
447 | if (prop->num_valid) { |
448 | extra = malloc(prop->num_valid * sizeof(INT32)); |
Result of 'malloc' is converted to a pointer of type 'char', which is incompatible with sizeof operand type 'INT32' | |
449 | if (!extra) |
450 | return BadAlloc11; |
451 | } |
452 | rep = (xRRQueryProviderPropertyReply) { |
453 | .type = X_Reply1, |
454 | .sequenceNumber = client->sequence, |
455 | .length = prop->num_valid, |
456 | .pending = prop->is_pending, |
457 | .range = prop->range, |
458 | .immutable = prop->immutable |
459 | }; |
460 | if (client->swapped) { |
461 | swaps(&rep.sequenceNumber)do { if (sizeof(*(&rep.sequenceNumber)) != 2) wrong_size( ); if (__builtin_constant_p((uintptr_t)(&rep.sequenceNumber ) & 1) && ((uintptr_t)(&rep.sequenceNumber) & 1) == 0) *(&rep.sequenceNumber) = lswaps(*(&rep.sequenceNumber )); else swap_uint16((uint16_t *)(&rep.sequenceNumber)); } while (0); |
462 | swapl(&rep.length)do { if (sizeof(*(&rep.length)) != 4) wrong_size(); if (__builtin_constant_p ((uintptr_t)(&rep.length) & 3) && ((uintptr_t )(&rep.length) & 3) == 0) *(&rep.length) = lswapl (*(&rep.length)); else swap_uint32((uint32_t *)(&rep. length)); } while (0); |
463 | } |
464 | WriteToClient(client, sizeof(xRRQueryProviderPropertyReply), (char *) &rep); |
465 | if (prop->num_valid) { |
466 | memcpy(extra, prop->valid_values, prop->num_valid * sizeof(INT32))__builtin___memcpy_chk (extra, prop->valid_values, prop-> num_valid * sizeof(INT32), __builtin_object_size (extra, 0)); |
467 | client->pSwapReplyFunc = (ReplySwapPtr) Swap32Write; |
468 | WriteSwappedDataToClient(client, prop->num_valid * sizeof(INT32),if ((client)->swapped) (*(client)->pSwapReplyFunc)(client , (int)(prop->num_valid * sizeof(INT32)), extra); else WriteToClient (client, (int)(prop->num_valid * sizeof(INT32)), (extra)); |
469 | extra)if ((client)->swapped) (*(client)->pSwapReplyFunc)(client , (int)(prop->num_valid * sizeof(INT32)), extra); else WriteToClient (client, (int)(prop->num_valid * sizeof(INT32)), (extra));; |
470 | free(extra); |
471 | } |
472 | return Success0; |
473 | } |
474 | |
475 | int |
476 | ProcRRConfigureProviderProperty(ClientPtr client) |
477 | { |
478 | REQUEST(xRRConfigureProviderPropertyReq)xRRConfigureProviderPropertyReq *stuff = (xRRConfigureProviderPropertyReq *)client->requestBuffer; |
479 | RRProviderPtr provider; |
480 | int num_valid; |
481 | |
482 | REQUEST_AT_LEAST_SIZE(xRRConfigureProviderPropertyReq)if ((sizeof(xRRConfigureProviderPropertyReq) >> 2) > client->req_len ) return(16); |
483 | |
484 | VERIFY_RR_PROVIDER(stuff->provider, provider, DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, (1<<0)); if (rc != 0) { client->errorValue = stuff->provider; return rc; } }; |
485 | |
486 | num_valid = |
487 | stuff->length - bytes_to_int32(sizeof(xRRConfigureProviderPropertyReq)); |
488 | return RRConfigureProviderProperty(provider, stuff->property, stuff->pending, |
489 | stuff->range, FALSE0, num_valid, |
490 | (INT32 *) (stuff + 1)); |
491 | } |
492 | |
493 | int |
494 | ProcRRChangeProviderProperty(ClientPtr client) |
495 | { |
496 | REQUEST(xRRChangeProviderPropertyReq)xRRChangeProviderPropertyReq *stuff = (xRRChangeProviderPropertyReq *)client->requestBuffer; |
497 | RRProviderPtr provider; |
498 | char format, mode; |
499 | unsigned long len; |
500 | int sizeInBytes; |
501 | int totalSize; |
502 | int err; |
503 | |
504 | REQUEST_AT_LEAST_SIZE(xRRChangeProviderPropertyReq)if ((sizeof(xRRChangeProviderPropertyReq) >> 2) > client ->req_len ) return(16); |
505 | UpdateCurrentTime(); |
506 | format = stuff->format; |
507 | mode = stuff->mode; |
508 | if ((mode != PropModeReplace0) && (mode != PropModeAppend2) && |
509 | (mode != PropModePrepend1)) { |
510 | client->errorValue = mode; |
511 | return BadValue2; |
512 | } |
513 | if ((format != 8) && (format != 16) && (format != 32)) { |
514 | client->errorValue = format; |
515 | return BadValue2; |
516 | } |
517 | len = stuff->nUnits; |
518 | if (len > bytes_to_int32((0xffffffff - sizeof(xChangePropertyReq)))) |
519 | return BadLength16; |
520 | sizeInBytes = format >> 3; |
521 | totalSize = len * sizeInBytes; |
522 | REQUEST_FIXED_SIZE(xRRChangeProviderPropertyReq, totalSize)if (((sizeof(xRRChangeProviderPropertyReq) >> 2) > client ->req_len) || (((totalSize) >> 2) >= client->req_len ) || ((((uint64_t) sizeof(xRRChangeProviderPropertyReq) + (totalSize ) + 3) >> 2) != (uint64_t) client->req_len)) return( 16); |
523 | |
524 | VERIFY_RR_PROVIDER(stuff->provider, provider, DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, (1<<0)); if (rc != 0) { client->errorValue = stuff->provider; return rc; } }; |
525 | |
526 | if (!ValidAtom(stuff->property)) { |
527 | client->errorValue = stuff->property; |
528 | return BadAtom5; |
529 | } |
530 | if (!ValidAtom(stuff->type)) { |
531 | client->errorValue = stuff->type; |
532 | return BadAtom5; |
533 | } |
534 | |
535 | err = RRChangeProviderProperty(provider, stuff->property, |
536 | stuff->type, (int) format, |
537 | (int) mode, len, (void *) &stuff[1], TRUE1, |
538 | TRUE1); |
539 | if (err != Success0) |
540 | return err; |
541 | else |
542 | return Success0; |
543 | } |
544 | |
545 | int |
546 | ProcRRDeleteProviderProperty(ClientPtr client) |
547 | { |
548 | REQUEST(xRRDeleteProviderPropertyReq)xRRDeleteProviderPropertyReq *stuff = (xRRDeleteProviderPropertyReq *)client->requestBuffer; |
549 | RRProviderPtr provider; |
550 | RRPropertyPtr prop; |
551 | |
552 | REQUEST_SIZE_MATCH(xRRDeleteProviderPropertyReq)if ((sizeof(xRRDeleteProviderPropertyReq) >> 2) != client ->req_len) return(16); |
553 | UpdateCurrentTime(); |
554 | VERIFY_RR_PROVIDER(stuff->provider, provider, DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, (1<<0)); if (rc != 0) { client->errorValue = stuff->provider; return rc; } }; |
555 | |
556 | if (!ValidAtom(stuff->property)) { |
557 | client->errorValue = stuff->property; |
558 | return BadAtom5; |
559 | } |
560 | |
561 | prop = RRQueryProviderProperty(provider, stuff->property); |
562 | if (!prop) { |
563 | client->errorValue = stuff->property; |
564 | return BadName15; |
565 | } |
566 | |
567 | if (prop->immutable) { |
568 | client->errorValue = stuff->property; |
569 | return BadAccess10; |
570 | } |
571 | |
572 | RRDeleteProviderProperty(provider, stuff->property); |
573 | return Success0; |
574 | } |
575 | |
576 | int |
577 | ProcRRGetProviderProperty(ClientPtr client) |
578 | { |
579 | REQUEST(xRRGetProviderPropertyReq)xRRGetProviderPropertyReq *stuff = (xRRGetProviderPropertyReq *)client->requestBuffer; |
580 | RRPropertyPtr prop, *prev; |
581 | RRPropertyValuePtr prop_value; |
582 | unsigned long n, len, ind; |
583 | RRProviderPtr provider; |
584 | xRRGetProviderPropertyReply reply = { |
585 | .type = X_Reply1, |
586 | .sequenceNumber = client->sequence |
587 | }; |
588 | char *extra = NULL((void*)0); |
589 | |
590 | REQUEST_SIZE_MATCH(xRRGetProviderPropertyReq)if ((sizeof(xRRGetProviderPropertyReq) >> 2) != client-> req_len) return(16); |
591 | if (stuff->delete) |
592 | UpdateCurrentTime(); |
593 | VERIFY_RR_PROVIDER(stuff->provider, provider,{ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, stuff->delete ? (1<< 1) : (1<<0)); if (rc != 0) { client->errorValue = stuff ->provider; return rc; } } |
594 | stuff->delete ? DixWriteAccess : DixReadAccess){ int rc = dixLookupResourceByType((void **)&(provider), stuff ->provider, RRProviderType, client, stuff->delete ? (1<< 1) : (1<<0)); if (rc != 0) { client->errorValue = stuff ->provider; return rc; } }; |
595 | |
596 | if (!ValidAtom(stuff->property)) { |
597 | client->errorValue = stuff->property; |
598 | return BadAtom5; |
599 | } |
600 | if ((stuff->delete != xTrue1) && (stuff->delete != xFalse0)) { |
601 | client->errorValue = stuff->delete; |
602 | return BadValue2; |
603 | } |
604 | if ((stuff->type != AnyPropertyType0L) && !ValidAtom(stuff->type)) { |
605 | client->errorValue = stuff->type; |
606 | return BadAtom5; |
607 | } |
608 | |
609 | for (prev = &provider->properties; (prop = *prev); prev = &prop->next) |
610 | if (prop->propertyName == stuff->property) |
611 | break; |
612 | |
613 | if (!prop) { |
614 | reply.nItems = 0; |
615 | reply.length = 0; |
616 | reply.bytesAfter = 0; |
617 | reply.propertyType = None0L; |
618 | reply.format = 0; |
619 | if (client->swapped) { |
620 | swaps(&reply.sequenceNumber)do { if (sizeof(*(&reply.sequenceNumber)) != 2) wrong_size (); if (__builtin_constant_p((uintptr_t)(&reply.sequenceNumber ) & 1) && ((uintptr_t)(&reply.sequenceNumber) & 1) == 0) *(&reply.sequenceNumber) = lswaps(*(& reply.sequenceNumber)); else swap_uint16((uint16_t *)(&reply .sequenceNumber)); } while (0); |
621 | swapl(&reply.length)do { if (sizeof(*(&reply.length)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.length) & 3) && ((uintptr_t)(&reply.length) & 3) == 0) *(&reply. length) = lswapl(*(&reply.length)); else swap_uint32((uint32_t *)(&reply.length)); } while (0); |
622 | swapl(&reply.propertyType)do { if (sizeof(*(&reply.propertyType)) != 4) wrong_size( ); if (__builtin_constant_p((uintptr_t)(&reply.propertyType ) & 3) && ((uintptr_t)(&reply.propertyType) & 3) == 0) *(&reply.propertyType) = lswapl(*(&reply.propertyType )); else swap_uint32((uint32_t *)(&reply.propertyType)); } while (0); |
623 | swapl(&reply.bytesAfter)do { if (sizeof(*(&reply.bytesAfter)) != 4) wrong_size(); if (__builtin_constant_p((uintptr_t)(&reply.bytesAfter) & 3) && ((uintptr_t)(&reply.bytesAfter) & 3) == 0) *(&reply.bytesAfter) = lswapl(*(&reply.bytesAfter )); else swap_uint32((uint32_t *)(&reply.bytesAfter)); } while (0); |
624 | swapl(&reply.nItems)do { if (sizeof(*(&reply.nItems)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.nItems) & 3) && ((uintptr_t)(&reply.nItems) & 3) == 0) *(&reply. nItems) = lswapl(*(&reply.nItems)); else swap_uint32((uint32_t *)(&reply.nItems)); } while (0); |
625 | } |
626 | WriteToClient(client, sizeof(xRRGetProviderPropertyReply), &reply); |
627 | return Success0; |
628 | } |
629 | |
630 | if (prop->immutable && stuff->delete) |
631 | return BadAccess10; |
632 | |
633 | prop_value = RRGetProviderProperty(provider, stuff->property, stuff->pending); |
634 | if (!prop_value) |
635 | return BadAtom5; |
636 | |
637 | /* If the request type and actual type don't match. Return the |
638 | property information, but not the data. */ |
639 | |
640 | if (((stuff->type != prop_value->type) && (stuff->type != AnyPropertyType0L)) |
641 | ) { |
642 | reply.bytesAfter = prop_value->size; |
643 | reply.format = prop_value->format; |
644 | reply.length = 0; |
645 | reply.nItems = 0; |
646 | reply.propertyType = prop_value->type; |
647 | if (client->swapped) { |
648 | swaps(&reply.sequenceNumber)do { if (sizeof(*(&reply.sequenceNumber)) != 2) wrong_size (); if (__builtin_constant_p((uintptr_t)(&reply.sequenceNumber ) & 1) && ((uintptr_t)(&reply.sequenceNumber) & 1) == 0) *(&reply.sequenceNumber) = lswaps(*(& reply.sequenceNumber)); else swap_uint16((uint16_t *)(&reply .sequenceNumber)); } while (0); |
649 | swapl(&reply.length)do { if (sizeof(*(&reply.length)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.length) & 3) && ((uintptr_t)(&reply.length) & 3) == 0) *(&reply. length) = lswapl(*(&reply.length)); else swap_uint32((uint32_t *)(&reply.length)); } while (0); |
650 | swapl(&reply.propertyType)do { if (sizeof(*(&reply.propertyType)) != 4) wrong_size( ); if (__builtin_constant_p((uintptr_t)(&reply.propertyType ) & 3) && ((uintptr_t)(&reply.propertyType) & 3) == 0) *(&reply.propertyType) = lswapl(*(&reply.propertyType )); else swap_uint32((uint32_t *)(&reply.propertyType)); } while (0); |
651 | swapl(&reply.bytesAfter)do { if (sizeof(*(&reply.bytesAfter)) != 4) wrong_size(); if (__builtin_constant_p((uintptr_t)(&reply.bytesAfter) & 3) && ((uintptr_t)(&reply.bytesAfter) & 3) == 0) *(&reply.bytesAfter) = lswapl(*(&reply.bytesAfter )); else swap_uint32((uint32_t *)(&reply.bytesAfter)); } while (0); |
652 | swapl(&reply.nItems)do { if (sizeof(*(&reply.nItems)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.nItems) & 3) && ((uintptr_t)(&reply.nItems) & 3) == 0) *(&reply. nItems) = lswapl(*(&reply.nItems)); else swap_uint32((uint32_t *)(&reply.nItems)); } while (0); |
653 | } |
654 | WriteToClient(client, sizeof(xRRGetProviderPropertyReply), &reply); |
655 | return Success0; |
656 | } |
657 | |
658 | /* |
659 | * Return type, format, value to client |
660 | */ |
661 | n = (prop_value->format / 8) * prop_value->size; /* size (bytes) of prop */ |
662 | ind = stuff->longOffset << 2; |
663 | |
664 | /* If longOffset is invalid such that it causes "len" to |
665 | be negative, it's a value error. */ |
666 | |
667 | if (n < ind) { |
668 | client->errorValue = stuff->longOffset; |
669 | return BadValue2; |
670 | } |
671 | |
672 | len = min(n - ind, 4 * stuff->longLength)(((n - ind) < (4 * stuff->longLength)) ? (n - ind) : (4 * stuff->longLength)); |
673 | |
674 | if (len) { |
675 | extra = malloc(len); |
676 | if (!extra) |
677 | return BadAlloc11; |
678 | } |
679 | reply.bytesAfter = n - (ind + len); |
680 | reply.format = prop_value->format; |
681 | reply.length = bytes_to_int32(len); |
682 | if (prop_value->format) |
683 | reply.nItems = len / (prop_value->format / 8); |
684 | else |
685 | reply.nItems = 0; |
686 | reply.propertyType = prop_value->type; |
687 | |
688 | if (stuff->delete && (reply.bytesAfter == 0)) { |
689 | xRRProviderPropertyNotifyEvent event = { |
690 | .type = RREventBase + RRNotify1, |
691 | .subCode = RRNotify_ProviderProperty4, |
692 | .provider = provider->id, |
693 | .state = PropertyDelete1, |
694 | .atom = prop->propertyName, |
695 | .timestamp = currentTime.milliseconds |
696 | }; |
697 | RRDeliverPropertyEvent(provider->pScreen, (xEvent *) &event); |
698 | } |
699 | |
700 | if (client->swapped) { |
701 | swaps(&reply.sequenceNumber)do { if (sizeof(*(&reply.sequenceNumber)) != 2) wrong_size (); if (__builtin_constant_p((uintptr_t)(&reply.sequenceNumber ) & 1) && ((uintptr_t)(&reply.sequenceNumber) & 1) == 0) *(&reply.sequenceNumber) = lswaps(*(& reply.sequenceNumber)); else swap_uint16((uint16_t *)(&reply .sequenceNumber)); } while (0); |
702 | swapl(&reply.length)do { if (sizeof(*(&reply.length)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.length) & 3) && ((uintptr_t)(&reply.length) & 3) == 0) *(&reply. length) = lswapl(*(&reply.length)); else swap_uint32((uint32_t *)(&reply.length)); } while (0); |
703 | swapl(&reply.propertyType)do { if (sizeof(*(&reply.propertyType)) != 4) wrong_size( ); if (__builtin_constant_p((uintptr_t)(&reply.propertyType ) & 3) && ((uintptr_t)(&reply.propertyType) & 3) == 0) *(&reply.propertyType) = lswapl(*(&reply.propertyType )); else swap_uint32((uint32_t *)(&reply.propertyType)); } while (0); |
704 | swapl(&reply.bytesAfter)do { if (sizeof(*(&reply.bytesAfter)) != 4) wrong_size(); if (__builtin_constant_p((uintptr_t)(&reply.bytesAfter) & 3) && ((uintptr_t)(&reply.bytesAfter) & 3) == 0) *(&reply.bytesAfter) = lswapl(*(&reply.bytesAfter )); else swap_uint32((uint32_t *)(&reply.bytesAfter)); } while (0); |
705 | swapl(&reply.nItems)do { if (sizeof(*(&reply.nItems)) != 4) wrong_size(); if ( __builtin_constant_p((uintptr_t)(&reply.nItems) & 3) && ((uintptr_t)(&reply.nItems) & 3) == 0) *(&reply. nItems) = lswapl(*(&reply.nItems)); else swap_uint32((uint32_t *)(&reply.nItems)); } while (0); |
706 | } |
707 | WriteToClient(client, sizeof(xGenericReply), &reply); |
708 | if (len) { |
709 | memcpy(extra, (char *) prop_value->data + ind, len)__builtin___memcpy_chk (extra, (char *) prop_value->data + ind, len, __builtin_object_size (extra, 0)); |
710 | switch (reply.format) { |
711 | case 32: |
712 | client->pSwapReplyFunc = (ReplySwapPtr) CopySwap32Write; |
713 | break; |
714 | case 16: |
715 | client->pSwapReplyFunc = (ReplySwapPtr) CopySwap16Write; |
716 | break; |
717 | default: |
718 | client->pSwapReplyFunc = (ReplySwapPtr) WriteToClient; |
719 | break; |
720 | } |
721 | WriteSwappedDataToClient(client, len, extra)if ((client)->swapped) (*(client)->pSwapReplyFunc)(client , (int)(len), extra); else WriteToClient(client, (int)(len), ( extra));; |
722 | free(extra); |
723 | } |
724 | |
725 | if (stuff->delete && (reply.bytesAfter == 0)) { /* delete the Property */ |
726 | *prev = prop->next; |
727 | RRDestroyProviderProperty(prop); |
728 | } |
729 | return Success0; |
730 | } |