add more advances region support using pixman
This commit is contained in:
parent
660132a49d
commit
58c777783b
@ -1,3 +1,11 @@
|
||||
|
||||
EXTRA_FILES =
|
||||
|
||||
if XRDP_PIXMAN
|
||||
else
|
||||
EXTRA_FILES += pixman-region16.c pixman-region.h
|
||||
endif
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
-DXRDP_CFG_PATH=\"${sysconfdir}/xrdp\" \
|
||||
-DXRDP_SBIN_PATH=\"${sbindir}\" \
|
||||
@ -36,7 +44,8 @@ libcommon_la_SOURCES = \
|
||||
trans.h \
|
||||
xrdp_client_info.h \
|
||||
xrdp_constants.h \
|
||||
xrdp_rail.h
|
||||
xrdp_rail.h \
|
||||
$(EXTRA_FILES)
|
||||
|
||||
libcommon_la_LIBADD = \
|
||||
-lcrypto \
|
||||
|
2549
common/pixman-region.c
Normal file
2549
common/pixman-region.c
Normal file
File diff suppressed because it is too large
Load Diff
73
common/pixman-region.h
Normal file
73
common/pixman-region.h
Normal file
@ -0,0 +1,73 @@
|
||||
/**
|
||||
* xrdp: A Remote Desktop Protocol server.
|
||||
*
|
||||
* Copyright (C) Jay Sorg 2016
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* region, from pixman.h
|
||||
*/
|
||||
|
||||
#if !defined(PIXMAN_PIXMAN_H__)
|
||||
#define PIXMAN_PIXMAN_H__
|
||||
|
||||
typedef int pixman_bool_t;
|
||||
|
||||
struct pixman_region16_data
|
||||
{
|
||||
long size;
|
||||
long numRects;
|
||||
};
|
||||
|
||||
struct pixman_box16
|
||||
{
|
||||
signed short x1, y1, x2, y2;
|
||||
};
|
||||
|
||||
struct pixman_region16
|
||||
{
|
||||
struct pixman_box16 extents;
|
||||
struct pixman_region16_data *data;
|
||||
};
|
||||
|
||||
enum _pixman_region_overlap_t
|
||||
{
|
||||
PIXMAN_REGION_OUT,
|
||||
PIXMAN_REGION_IN,
|
||||
PIXMAN_REGION_PART
|
||||
};
|
||||
|
||||
typedef enum _pixman_region_overlap_t pixman_region_overlap_t;
|
||||
|
||||
typedef struct pixman_region16_data pixman_region16_data_t;
|
||||
typedef struct pixman_box16 pixman_box16_t;
|
||||
typedef struct pixman_region16 pixman_region16_t;
|
||||
|
||||
/* creation/destruction */
|
||||
void pixman_region_init (pixman_region16_t *region);
|
||||
void pixman_region_init_rect (pixman_region16_t *region,
|
||||
int x,
|
||||
int y,
|
||||
unsigned int width,
|
||||
unsigned int height);
|
||||
void pixman_region_fini (pixman_region16_t *region);
|
||||
pixman_bool_t pixman_region_union (pixman_region16_t *new_reg,
|
||||
pixman_region16_t *reg1,
|
||||
pixman_region16_t *reg2);
|
||||
pixman_bool_t pixman_region_subtract (pixman_region16_t *reg_d,
|
||||
pixman_region16_t *reg_m,
|
||||
pixman_region16_t *reg_s);
|
||||
pixman_box16_t * pixman_region_rectangles (pixman_region16_t *region,
|
||||
int *n_rects);
|
||||
|
||||
#endif
|
67
common/pixman-region16.c
Normal file
67
common/pixman-region16.c
Normal file
@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright © 2008 Red Hat, Inc.
|
||||
*
|
||||
* Permission to use, copy, modify, distribute, and sell this software
|
||||
* and its documentation for any purpose is hereby granted without
|
||||
* fee, provided that the above copyright notice appear in all copies
|
||||
* and that both that copyright notice and this permission notice
|
||||
* appear in supporting documentation, and that the name of
|
||||
* Red Hat, Inc. not be used in advertising or publicity pertaining to
|
||||
* distribution of the software without specific, written prior
|
||||
* permission. Red Hat, Inc. makes no representations about the
|
||||
* suitability of this software for any purpose. It is provided "as
|
||||
* is" without express or implied warranty.
|
||||
*
|
||||
* RED HAT, INC. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
|
||||
* SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS, IN NO EVENT SHALL RED HAT, INC. BE LIABLE FOR ANY SPECIAL,
|
||||
* INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
|
||||
* RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
|
||||
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
|
||||
* IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*
|
||||
* Author: Soren Sandmann <sandmann@redhat.com>
|
||||
*/
|
||||
|
||||
/* taken from pixman 0.34
|
||||
altered to compile without all of pixman */
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "pixman-region.h"
|
||||
|
||||
#define UINT32_MAX (4294967295U)
|
||||
#define INT16_MIN (-32767-1)
|
||||
#define INT16_MAX (32767)
|
||||
|
||||
#define PIXMAN_EXPORT
|
||||
#define FALSE 0
|
||||
#define TRUE 1
|
||||
|
||||
#define MIN(x1, x2) ((x1) < (x2) ? (x1) : (x2))
|
||||
#define MAX(x1, x2) ((x1) > (x2) ? (x1) : (x2))
|
||||
|
||||
typedef int pixman_bool_t;
|
||||
|
||||
typedef pixman_box16_t box_type_t;
|
||||
typedef pixman_region16_data_t region_data_type_t;
|
||||
typedef pixman_region16_t region_type_t;
|
||||
typedef signed int overflow_int_t;
|
||||
|
||||
#define PREFIX(x) pixman_region##x
|
||||
|
||||
#define PIXMAN_REGION_MAX INT16_MAX
|
||||
#define PIXMAN_REGION_MIN INT16_MIN
|
||||
|
||||
#define FUNC "func"
|
||||
|
||||
#define critical_if_fail(expr)
|
||||
|
||||
int _pixman_log_error(const char *func, const char *format, ...)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
#include "pixman-region.c"
|
||||
|
@ -112,6 +112,10 @@ AC_ARG_ENABLE(mp3lame, AS_HELP_STRING([--enable-mp3lame],
|
||||
[Build lame mp3(audio codec) (default: no)]),
|
||||
[], [enable_mp3lame=no])
|
||||
AM_CONDITIONAL(XRDP_MP3LAME, [test x$enable_mp3lame = xyes])
|
||||
AC_ARG_ENABLE(pixman, AS_HELP_STRING([--enable-pixman],
|
||||
[Use pixman library (default: no)]),
|
||||
[], [enable_pimanno])
|
||||
AM_CONDITIONAL(XRDP_PIXMAN, [test x$enable_pixman = xyes])
|
||||
|
||||
# checking for openssl
|
||||
AC_CHECK_HEADER([openssl/rc4.h], [],
|
||||
@ -191,6 +195,8 @@ then
|
||||
[AC_MSG_ERROR([please install libmp3lame-dev or lamemp3-devel])])
|
||||
fi
|
||||
|
||||
AS_IF( [test "x$enable_pixman" = "xyes"] , [PKG_CHECK_MODULES(XRDP_PIXMAN, pixman-1 >= 0.1.0)] )
|
||||
|
||||
# checking for TurboJPEG
|
||||
if test "x$enable_tjpeg" = "xyes"
|
||||
then
|
||||
|
@ -14,6 +14,12 @@ EXTRA_INCLUDES += -I$(top_srcdir)/librfxcodec/include
|
||||
EXTRA_LIBS += $(top_srcdir)/librfxcodec/src/librfxencode.a
|
||||
endif
|
||||
|
||||
if XRDP_PIXMAN
|
||||
EXTRA_DEFINES += -DXRDP_PIXMAN
|
||||
EXTRA_INCLUDES += $(XRDP_PIXMAN_CFLAGS)
|
||||
EXTRA_LIBS += $(XRDP_PIXMAN_LIBS)
|
||||
endif
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
-DXRDP_CFG_PATH=\"${sysconfdir}/xrdp\" \
|
||||
-DXRDP_SBIN_PATH=\"${sbindir}\" \
|
||||
|
@ -175,9 +175,6 @@ xrdp_region_delete(struct xrdp_region* self);
|
||||
int APP_CC
|
||||
xrdp_region_add_rect(struct xrdp_region* self, struct xrdp_rect* rect);
|
||||
int APP_CC
|
||||
xrdp_region_insert_rect(struct xrdp_region* self, int i, int left,
|
||||
int top, int right, int bottom);
|
||||
int APP_CC
|
||||
xrdp_region_subtract_rect(struct xrdp_region* self,
|
||||
struct xrdp_rect* rect);
|
||||
int APP_CC
|
||||
|
@ -20,6 +20,12 @@
|
||||
|
||||
#include "xrdp.h"
|
||||
|
||||
#if defined(XRDP_PIXMAN)
|
||||
#include <pixman.h>
|
||||
#else
|
||||
#include "pixman-region.h"
|
||||
#endif
|
||||
|
||||
/*****************************************************************************/
|
||||
struct xrdp_region *APP_CC
|
||||
xrdp_region_create(struct xrdp_wm *wm)
|
||||
@ -28,8 +34,9 @@ xrdp_region_create(struct xrdp_wm *wm)
|
||||
|
||||
self = (struct xrdp_region *)g_malloc(sizeof(struct xrdp_region), 1);
|
||||
self->wm = wm;
|
||||
self->rects = list_create();
|
||||
self->rects->auto_free = 1;
|
||||
self->reg = (struct pixman_region16 *)
|
||||
g_malloc(sizeof(struct pixman_region16), 1);
|
||||
pixman_region_init(self->reg);
|
||||
return self;
|
||||
}
|
||||
|
||||
@ -41,276 +48,66 @@ xrdp_region_delete(struct xrdp_region *self)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
list_delete(self->rects);
|
||||
pixman_region_fini(self->reg);
|
||||
g_free(self->reg);
|
||||
g_free(self);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* returns error */
|
||||
int APP_CC
|
||||
xrdp_region_add_rect(struct xrdp_region *self, struct xrdp_rect *rect)
|
||||
{
|
||||
struct xrdp_rect *r;
|
||||
struct pixman_region16 lreg;
|
||||
|
||||
r = (struct xrdp_rect *)g_malloc(sizeof(struct xrdp_rect), 1);
|
||||
*r = *rect;
|
||||
list_add_item(self->rects, (long)r);
|
||||
pixman_region_init_rect(&lreg, rect->left, rect->top,
|
||||
rect->right - rect->left,
|
||||
rect->bottom - rect->top);
|
||||
if (!pixman_region_union(self->reg, self->reg, &lreg))
|
||||
{
|
||||
pixman_region_fini(&lreg);
|
||||
return 1;
|
||||
}
|
||||
pixman_region_fini(&lreg);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* returns error */
|
||||
int APP_CC
|
||||
xrdp_region_insert_rect(struct xrdp_region *self, int i, int left,
|
||||
int top, int right, int bottom)
|
||||
xrdp_region_subtract_rect(struct xrdp_region *self, struct xrdp_rect *rect)
|
||||
{
|
||||
struct xrdp_rect *r;
|
||||
|
||||
r = (struct xrdp_rect *)g_malloc(sizeof(struct xrdp_rect), 1);
|
||||
r->left = left;
|
||||
r->top = top;
|
||||
r->right = right;
|
||||
r->bottom = bottom;
|
||||
list_insert_item(self->rects, i, (long)r);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
int APP_CC
|
||||
xrdp_region_subtract_rect(struct xrdp_region *self,
|
||||
struct xrdp_rect *rect)
|
||||
{
|
||||
struct xrdp_rect *r;
|
||||
struct xrdp_rect rect1;
|
||||
int i;
|
||||
|
||||
for (i = self->rects->count - 1; i >= 0; i--)
|
||||
{
|
||||
r = (struct xrdp_rect *)list_get_item(self->rects, i);
|
||||
rect1 = *r;
|
||||
r = &rect1;
|
||||
|
||||
if (rect->left <= r->left &&
|
||||
rect->top <= r->top &&
|
||||
rect->right >= r->right &&
|
||||
rect->bottom >= r->bottom)
|
||||
{
|
||||
/* rect is not visible */
|
||||
list_remove_item(self->rects, i);
|
||||
}
|
||||
else if (rect->right < r->left ||
|
||||
rect->bottom < r->top ||
|
||||
rect->top > r->bottom ||
|
||||
rect->left > r->right)
|
||||
{
|
||||
/* rect are not related */
|
||||
}
|
||||
else if (rect->left <= r->left &&
|
||||
rect->right >= r->right &&
|
||||
rect->bottom < r->bottom &&
|
||||
rect->top <= r->top)
|
||||
{
|
||||
/* partially covered(whole top) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->top <= r->top &&
|
||||
rect->bottom >= r->bottom &&
|
||||
rect->right < r->right &&
|
||||
rect->left <= r->left)
|
||||
{
|
||||
/* partially covered(left) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, rect->right, r->top,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left <= r->left &&
|
||||
rect->right >= r->right &&
|
||||
rect->top > r->top &&
|
||||
rect->bottom >= r->bottom)
|
||||
{
|
||||
/* partially covered(bottom) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
}
|
||||
else if (rect->top <= r->top &&
|
||||
rect->bottom >= r->bottom &&
|
||||
rect->left > r->left &&
|
||||
rect->right >= r->right)
|
||||
{
|
||||
/* partially covered(right) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
rect->left, r->bottom);
|
||||
}
|
||||
else if (rect->left <= r->left &&
|
||||
rect->top <= r->top &&
|
||||
rect->right < r->right &&
|
||||
rect->bottom < r->bottom)
|
||||
{
|
||||
/* partially covered(top left) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, rect->right, r->top,
|
||||
r->right, rect->bottom);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left <= r->left &&
|
||||
rect->bottom >= r->bottom &&
|
||||
rect->right < r->right &&
|
||||
rect->top > r->top)
|
||||
{
|
||||
/* partially covered(bottom left) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, rect->right, rect->top,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->right >= r->right &&
|
||||
rect->top <= r->top &&
|
||||
rect->bottom < r->bottom)
|
||||
{
|
||||
/* partially covered(top right) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
rect->left, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->right >= r->right &&
|
||||
rect->top > r->top &&
|
||||
rect->bottom >= r->bottom)
|
||||
{
|
||||
/* partially covered(bottom right) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->top,
|
||||
rect->left, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->top <= r->top &&
|
||||
rect->right < r->right &&
|
||||
rect->bottom >= r->bottom)
|
||||
{
|
||||
/* 2 rects, one on each end */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
rect->left, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->right, r->top,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left <= r->left &&
|
||||
rect->top > r->top &&
|
||||
rect->right >= r->right &&
|
||||
rect->bottom < r->bottom)
|
||||
{
|
||||
/* 2 rects, one on each end */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->right < r->right &&
|
||||
rect->top <= r->top &&
|
||||
rect->bottom < r->bottom)
|
||||
{
|
||||
/* partially covered(top) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
rect->left, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->left, rect->bottom,
|
||||
rect->right, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->right, r->top,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->top > r->top &&
|
||||
rect->bottom < r->bottom &&
|
||||
rect->left <= r->left &&
|
||||
rect->right < r->right)
|
||||
{
|
||||
/* partially covered(left) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, rect->right, rect->top,
|
||||
r->right, rect->bottom);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->right < r->right &&
|
||||
rect->bottom >= r->bottom &&
|
||||
rect->top > r->top)
|
||||
{
|
||||
/* partially covered(bottom) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
rect->left, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->left, r->top,
|
||||
rect->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, rect->right, r->top,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->top > r->top &&
|
||||
rect->bottom < r->bottom &&
|
||||
rect->right >= r->right &&
|
||||
rect->left > r->left)
|
||||
{
|
||||
/* partially covered(right) */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->top,
|
||||
rect->left, rect->bottom);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
}
|
||||
else if (rect->left > r->left &&
|
||||
rect->top > r->top &&
|
||||
rect->right < r->right &&
|
||||
rect->bottom < r->bottom)
|
||||
{
|
||||
/* totally contained, 4 rects */
|
||||
list_remove_item(self->rects, i);
|
||||
xrdp_region_insert_rect(self, i, r->left, r->top,
|
||||
r->right, rect->top);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->top,
|
||||
rect->left, rect->bottom);
|
||||
xrdp_region_insert_rect(self, i, r->left, rect->bottom,
|
||||
r->right, r->bottom);
|
||||
xrdp_region_insert_rect(self, i, rect->right, rect->top,
|
||||
r->right, rect->bottom);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_writeln("error in xrdp_region_subtract_rect");
|
||||
}
|
||||
}
|
||||
struct pixman_region16 lreg;
|
||||
|
||||
pixman_region_init_rect(&lreg, rect->left, rect->top,
|
||||
rect->right - rect->left,
|
||||
rect->bottom - rect->top);
|
||||
if (!pixman_region_subtract(self->reg, self->reg, &lreg))
|
||||
{
|
||||
pixman_region_fini(&lreg);
|
||||
return 1;
|
||||
}
|
||||
pixman_region_fini(&lreg);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* returns error */
|
||||
int APP_CC
|
||||
xrdp_region_get_rect(struct xrdp_region *self, int index,
|
||||
struct xrdp_rect *rect)
|
||||
{
|
||||
struct xrdp_rect *r;
|
||||
struct pixman_box16 *box;
|
||||
int count;
|
||||
|
||||
r = (struct xrdp_rect *)list_get_item(self->rects, index);
|
||||
|
||||
if (r == 0)
|
||||
box = pixman_region_rectangles(self->reg, &count);
|
||||
if ((box != 0) && (index >= 0) && (index < count))
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
*rect = *r;
|
||||
rect->left = box[index].x1;
|
||||
rect->top = box[index].y1;
|
||||
rect->right = box[index].x2;
|
||||
rect->bottom = box[index].y2;
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
@ -411,7 +411,7 @@ struct xrdp_listen
|
||||
struct xrdp_region
|
||||
{
|
||||
struct xrdp_wm* wm; /* owner */
|
||||
struct list* rects;
|
||||
struct pixman_region16 *reg;
|
||||
};
|
||||
|
||||
/* painter */
|
||||
|
Loading…
Reference in New Issue
Block a user