1 /**
2  * xrdp: A Remote Desktop Protocol server.
3  *
4  * Copyright (C) Jay Sorg 2004-2014
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *     http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  * region
19  */
20 
21 #if defined(HAVE_CONFIG_H)
22 #include <config_ac.h>
23 #endif
24 
25 #include "xrdp.h"
26 
27 #if defined(XRDP_PIXMAN)
28 #include <pixman.h>
29 #else
30 #include "pixman-region.h"
31 #endif
32 
33 /*****************************************************************************/
34 struct xrdp_region *
xrdp_region_create(struct xrdp_wm * wm)35 xrdp_region_create(struct xrdp_wm *wm)
36 {
37     struct xrdp_region *self;
38 
39     self = (struct xrdp_region *)g_malloc(sizeof(struct xrdp_region), 1);
40     self->wm = wm;
41     self->reg = (struct pixman_region16 *)
42                 g_malloc(sizeof(struct pixman_region16), 1);
43     pixman_region_init(self->reg);
44     return self;
45 }
46 
47 /*****************************************************************************/
48 void
xrdp_region_delete(struct xrdp_region * self)49 xrdp_region_delete(struct xrdp_region *self)
50 {
51     if (self == 0)
52     {
53         return;
54     }
55     pixman_region_fini(self->reg);
56     g_free(self->reg);
57     g_free(self);
58 }
59 
60 /*****************************************************************************/
61 /* returns error */
62 int
xrdp_region_add_rect(struct xrdp_region * self,struct xrdp_rect * rect)63 xrdp_region_add_rect(struct xrdp_region *self, struct xrdp_rect *rect)
64 {
65     struct pixman_region16 lreg;
66 
67     pixman_region_init_rect(&lreg, rect->left, rect->top,
68                             rect->right - rect->left,
69                             rect->bottom - rect->top);
70     if (!pixman_region_union(self->reg, self->reg, &lreg))
71     {
72         pixman_region_fini(&lreg);
73         return 1;
74     }
75     pixman_region_fini(&lreg);
76     return 0;
77 }
78 
79 /*****************************************************************************/
80 /* returns error */
81 int
xrdp_region_subtract_rect(struct xrdp_region * self,struct xrdp_rect * rect)82 xrdp_region_subtract_rect(struct xrdp_region *self, struct xrdp_rect *rect)
83 {
84     struct pixman_region16 lreg;
85 
86     pixman_region_init_rect(&lreg, rect->left, rect->top,
87                             rect->right - rect->left,
88                             rect->bottom - rect->top);
89     if (!pixman_region_subtract(self->reg, self->reg, &lreg))
90     {
91         pixman_region_fini(&lreg);
92         return 1;
93     }
94     pixman_region_fini(&lreg);
95     return 0;
96 }
97 
98 /*****************************************************************************/
99 /* returns error */
100 int
xrdp_region_intersect_rect(struct xrdp_region * self,struct xrdp_rect * rect)101 xrdp_region_intersect_rect(struct xrdp_region *self, struct xrdp_rect *rect)
102 {
103     struct pixman_region16 lreg;
104 
105     pixman_region_init_rect(&lreg, rect->left, rect->top,
106                             rect->right - rect->left,
107                             rect->bottom - rect->top);
108     if (!pixman_region_intersect(self->reg, self->reg, &lreg))
109     {
110         pixman_region_fini(&lreg);
111         return 1;
112     }
113     pixman_region_fini(&lreg);
114     return 0;
115 }
116 
117 
118 /*****************************************************************************/
119 /* returns error */
120 int
xrdp_region_get_rect(struct xrdp_region * self,int index,struct xrdp_rect * rect)121 xrdp_region_get_rect(struct xrdp_region *self, int index,
122                      struct xrdp_rect *rect)
123 {
124     struct pixman_box16 *box;
125     int count;
126 
127     box = pixman_region_rectangles(self->reg, &count);
128     if ((box != 0) && (index >= 0) && (index < count))
129     {
130         rect->left = box[index].x1;
131         rect->top = box[index].y1;
132         rect->right = box[index].x2;
133         rect->bottom = box[index].y2;
134         return 0;
135     }
136     return 1;
137 }
138