server: Remove no longer needed server-side screen buffer ioctls.
Signed-off-by: Jacek Caban <jacek@codeweavers.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
dc6f6e9ef3
commit
2e74000537
694
server/console.c
694
server/console.c
|
@ -427,11 +427,6 @@ static struct list screen_buffer_list = LIST_INIT(screen_buffer_list);
|
|||
|
||||
static const char_info_t empty_char_info = { ' ', 0x000f }; /* white on black space */
|
||||
|
||||
static int console_input_is_bare( struct console_input* cin )
|
||||
{
|
||||
return cin->evt == NULL;
|
||||
}
|
||||
|
||||
static struct fd *console_input_get_fd( struct object* obj )
|
||||
{
|
||||
struct console_input *console_input = (struct console_input*)obj;
|
||||
|
@ -992,239 +987,6 @@ static int write_console_input( struct console_input* console, int count,
|
|||
return 1;
|
||||
}
|
||||
|
||||
/* resize a screen buffer */
|
||||
static int change_screen_buffer_size( struct screen_buffer *screen_buffer,
|
||||
int new_width, int new_height )
|
||||
{
|
||||
int i, old_width, old_height, copy_width, copy_height;
|
||||
char_info_t *new_data;
|
||||
|
||||
if (!(new_data = malloc( new_width * new_height * sizeof(*new_data) )))
|
||||
{
|
||||
set_error( STATUS_NO_MEMORY );
|
||||
return 0;
|
||||
}
|
||||
old_width = screen_buffer->width;
|
||||
old_height = screen_buffer->height;
|
||||
copy_width = min( old_width, new_width );
|
||||
copy_height = min( old_height, new_height );
|
||||
|
||||
/* copy all the rows */
|
||||
for (i = 0; i < copy_height; i++)
|
||||
{
|
||||
memcpy( &new_data[i * new_width], &screen_buffer->data[i * old_width],
|
||||
copy_width * sizeof(char_info_t) );
|
||||
}
|
||||
|
||||
/* clear the end of each row */
|
||||
if (new_width > old_width)
|
||||
{
|
||||
/* fill first row */
|
||||
for (i = old_width; i < new_width; i++) new_data[i] = empty_char_info;
|
||||
/* and blast it to the other rows */
|
||||
for (i = 1; i < copy_height; i++)
|
||||
memcpy( &new_data[i * new_width + old_width], &new_data[old_width],
|
||||
(new_width - old_width) * sizeof(char_info_t) );
|
||||
}
|
||||
|
||||
/* clear remaining rows */
|
||||
if (new_height > old_height)
|
||||
{
|
||||
/* fill first row */
|
||||
for (i = 0; i < new_width; i++) new_data[old_height * new_width + i] = empty_char_info;
|
||||
/* and blast it to the other rows */
|
||||
for (i = old_height+1; i < new_height; i++)
|
||||
memcpy( &new_data[i * new_width], &new_data[old_height * new_width],
|
||||
new_width * sizeof(char_info_t) );
|
||||
}
|
||||
free( screen_buffer->data );
|
||||
screen_buffer->data = new_data;
|
||||
screen_buffer->width = new_width;
|
||||
screen_buffer->height = new_height;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int set_output_info( struct screen_buffer *screen_buffer,
|
||||
const struct condrv_output_info_params *params, data_size_t extra_size )
|
||||
{
|
||||
const struct condrv_output_info *info = ¶ms->info;
|
||||
struct condrv_renderer_event evt;
|
||||
WCHAR *font_name;
|
||||
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_CURSOR_GEOM)
|
||||
{
|
||||
if (info->cursor_size < 1 || info->cursor_size > 100)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (screen_buffer->cursor_size != info->cursor_size ||
|
||||
screen_buffer->cursor_visible != info->cursor_visible)
|
||||
{
|
||||
screen_buffer->cursor_size = info->cursor_size;
|
||||
screen_buffer->cursor_visible = info->cursor_visible;
|
||||
evt.event = CONSOLE_RENDERER_CURSOR_GEOM_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.cursor_geom.size = info->cursor_size;
|
||||
evt.u.cursor_geom.visible = info->cursor_visible;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_CURSOR_POS)
|
||||
{
|
||||
if (info->cursor_x < 0 || info->cursor_x >= screen_buffer->width ||
|
||||
info->cursor_y < 0 || info->cursor_y >= screen_buffer->height)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (screen_buffer->cursor_x != info->cursor_x || screen_buffer->cursor_y != info->cursor_y)
|
||||
{
|
||||
screen_buffer->cursor_x = info->cursor_x;
|
||||
screen_buffer->cursor_y = info->cursor_y;
|
||||
evt.event = CONSOLE_RENDERER_CURSOR_POS_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.cursor_pos.x = info->cursor_x;
|
||||
evt.u.cursor_pos.y = info->cursor_y;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_SIZE)
|
||||
{
|
||||
unsigned cc;
|
||||
|
||||
/* new screen-buffer cannot be smaller than actual window */
|
||||
if (info->width < screen_buffer->win.right - screen_buffer->win.left + 1 ||
|
||||
info->height < screen_buffer->win.bottom - screen_buffer->win.top + 1)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
/* FIXME: there are also some basic minimum and max size to deal with */
|
||||
if (!change_screen_buffer_size( screen_buffer, info->width, info->height )) return 0;
|
||||
|
||||
evt.event = CONSOLE_RENDERER_SB_RESIZE_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.resize.width = info->width;
|
||||
evt.u.resize.height = info->height;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
|
||||
evt.event = CONSOLE_RENDERER_UPDATE_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.update.top = 0;
|
||||
evt.u.update.bottom = screen_buffer->height - 1;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
|
||||
/* scroll window to display sb */
|
||||
if (screen_buffer->win.right >= info->width)
|
||||
{
|
||||
screen_buffer->win.right -= screen_buffer->win.left;
|
||||
screen_buffer->win.left = 0;
|
||||
}
|
||||
if (screen_buffer->win.bottom >= info->height)
|
||||
{
|
||||
screen_buffer->win.bottom -= screen_buffer->win.top;
|
||||
screen_buffer->win.top = 0;
|
||||
}
|
||||
/* reset cursor if needed (normally, if cursor was outside of new sb, the
|
||||
* window has been shifted so that the new position of the cursor will be
|
||||
* visible */
|
||||
cc = 0;
|
||||
if (screen_buffer->cursor_x >= info->width)
|
||||
{
|
||||
screen_buffer->cursor_x = info->width - 1;
|
||||
cc++;
|
||||
}
|
||||
if (screen_buffer->cursor_y >= info->height)
|
||||
{
|
||||
screen_buffer->cursor_y = info->height - 1;
|
||||
cc++;
|
||||
}
|
||||
if (cc)
|
||||
{
|
||||
evt.event = CONSOLE_RENDERER_CURSOR_POS_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.cursor_pos.x = info->cursor_x;
|
||||
evt.u.cursor_pos.y = info->cursor_y;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
|
||||
if (screen_buffer == screen_buffer->input->active &&
|
||||
screen_buffer->input->mode & ENABLE_WINDOW_INPUT)
|
||||
{
|
||||
INPUT_RECORD ir;
|
||||
ir.EventType = WINDOW_BUFFER_SIZE_EVENT;
|
||||
ir.Event.WindowBufferSizeEvent.dwSize.X = info->width;
|
||||
ir.Event.WindowBufferSizeEvent.dwSize.Y = info->height;
|
||||
write_console_input( screen_buffer->input, 1, &ir );
|
||||
}
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_ATTR)
|
||||
{
|
||||
screen_buffer->attr = info->attr;
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_POPUP_ATTR)
|
||||
{
|
||||
screen_buffer->popup_attr = info->popup_attr;
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_DISPLAY_WINDOW)
|
||||
{
|
||||
if (info->win_left < 0 || info->win_left > info->win_right ||
|
||||
info->win_right >= screen_buffer->width ||
|
||||
info->win_top < 0 || info->win_top > info->win_bottom ||
|
||||
info->win_bottom >= screen_buffer->height)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (screen_buffer->win.left != info->win_left || screen_buffer->win.top != info->win_top ||
|
||||
screen_buffer->win.right != info->win_right || screen_buffer->win.bottom != info->win_bottom)
|
||||
{
|
||||
screen_buffer->win.left = info->win_left;
|
||||
screen_buffer->win.top = info->win_top;
|
||||
screen_buffer->win.right = info->win_right;
|
||||
screen_buffer->win.bottom = info->win_bottom;
|
||||
evt.event = CONSOLE_RENDERER_DISPLAY_EVENT;
|
||||
memset( &evt.u, 0, sizeof(evt.u) );
|
||||
evt.u.display.left = info->win_left;
|
||||
evt.u.display.top = info->win_top;
|
||||
evt.u.display.width = info->win_right - info->win_left + 1;
|
||||
evt.u.display.height = info->win_bottom - info->win_top + 1;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_MAX_SIZE)
|
||||
{
|
||||
screen_buffer->max_width = info->max_width;
|
||||
screen_buffer->max_height = info->max_height;
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_COLORTABLE)
|
||||
{
|
||||
memcpy( screen_buffer->color_map, info->color_map, sizeof(info->color_map) );
|
||||
}
|
||||
if (params->mask & SET_CONSOLE_OUTPUT_INFO_FONT)
|
||||
{
|
||||
screen_buffer->font.width = info->font_width;
|
||||
screen_buffer->font.height = info->font_height;
|
||||
screen_buffer->font.weight = info->font_weight;
|
||||
screen_buffer->font.pitch_family = info->font_pitch_family;
|
||||
if (extra_size)
|
||||
{
|
||||
extra_size = extra_size / sizeof(WCHAR) * sizeof(WCHAR);
|
||||
font_name = mem_alloc( extra_size );
|
||||
if (font_name)
|
||||
{
|
||||
memcpy( font_name, info + 1, extra_size );
|
||||
free( screen_buffer->font.face_name );
|
||||
screen_buffer->font.face_name = font_name;
|
||||
screen_buffer->font.face_len = extra_size;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* dumb dump */
|
||||
static void console_input_dump( struct object *obj, int verbose )
|
||||
{
|
||||
|
@ -1360,280 +1122,6 @@ static struct fd *screen_buffer_get_fd( struct object *obj )
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/* read data from a screen buffer */
|
||||
static void read_console_output( struct screen_buffer *screen_buffer, unsigned int x, unsigned int y,
|
||||
enum char_info_mode mode, unsigned int width )
|
||||
{
|
||||
unsigned int i, count;
|
||||
char_info_t *src;
|
||||
|
||||
if (x >= screen_buffer->width || y >= screen_buffer->height)
|
||||
{
|
||||
if (width) set_error( STATUS_INVALID_PARAMETER );
|
||||
return;
|
||||
}
|
||||
src = screen_buffer->data + y * screen_buffer->width + x;
|
||||
|
||||
switch(mode)
|
||||
{
|
||||
case CHAR_INFO_MODE_TEXT:
|
||||
{
|
||||
WCHAR *data;
|
||||
count = min( screen_buffer->data + screen_buffer->height * screen_buffer->width - src,
|
||||
get_reply_max_size() / sizeof(*data) );
|
||||
if ((data = set_reply_data_size( count * sizeof(*data) )))
|
||||
{
|
||||
for (i = 0; i < count; i++) data[i] = src[i].ch;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CHAR_INFO_MODE_ATTR:
|
||||
{
|
||||
unsigned short *data;
|
||||
count = min( screen_buffer->data + screen_buffer->height * screen_buffer->width - src,
|
||||
get_reply_max_size() / sizeof(*data) );
|
||||
if ((data = set_reply_data_size( count * sizeof(*data) )))
|
||||
{
|
||||
for (i = 0; i < count; i++) data[i] = src[i].attr;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CHAR_INFO_MODE_TEXTATTR:
|
||||
{
|
||||
char_info_t *data;
|
||||
SMALL_RECT *region;
|
||||
if (!width || get_reply_max_size() < sizeof(*region))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return;
|
||||
}
|
||||
count = min( (get_reply_max_size() - sizeof(*region)) / (width * sizeof(*data)), screen_buffer->height - y );
|
||||
width = min( width, screen_buffer->width - x );
|
||||
if (!(region = set_reply_data_size( sizeof(*region) + width * count * sizeof(*data) ))) return;
|
||||
region->Left = x;
|
||||
region->Top = y;
|
||||
region->Right = x + width - 1;
|
||||
region->Bottom = y + count - 1;
|
||||
data = (char_info_t *)(region + 1);
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
memcpy( &data[i * width], &src[i * screen_buffer->width], width * sizeof(*data) );
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* write data into a screen buffer */
|
||||
static void write_console_output( struct screen_buffer *screen_buffer, const struct condrv_output_params *params,
|
||||
data_size_t size )
|
||||
{
|
||||
unsigned int i, entry_size, entry_cnt, x, y;
|
||||
char_info_t *dest;
|
||||
char *src;
|
||||
|
||||
entry_size = params->mode == CHAR_INFO_MODE_TEXTATTR ? sizeof(char_info_t) : sizeof(WCHAR);
|
||||
if (size % entry_size)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return;
|
||||
}
|
||||
if (params->x >= screen_buffer->width) return;
|
||||
entry_cnt = size / entry_size;
|
||||
|
||||
for (i = 0, src = (char *)(params + 1); i < entry_cnt; i++, src += entry_size)
|
||||
{
|
||||
if (params->width)
|
||||
{
|
||||
x = params->x + i % params->width;
|
||||
y = params->y + i / params->width;
|
||||
if (x >= screen_buffer->width) continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
x = (params->x + i) % screen_buffer->width;
|
||||
y = params->y + (params->x + i) / screen_buffer->width;
|
||||
}
|
||||
if (y >= screen_buffer->height) break;
|
||||
|
||||
dest = &screen_buffer->data[y * screen_buffer->width + x];
|
||||
switch(params->mode)
|
||||
{
|
||||
case CHAR_INFO_MODE_TEXT:
|
||||
dest->ch = *(const WCHAR *)src;
|
||||
break;
|
||||
case CHAR_INFO_MODE_ATTR:
|
||||
dest->attr = *(const unsigned short *)src;
|
||||
break;
|
||||
case CHAR_INFO_MODE_TEXTATTR:
|
||||
*dest = *(const char_info_t *)src;
|
||||
break;
|
||||
case CHAR_INFO_MODE_TEXTSTDATTR:
|
||||
dest->ch = *(const WCHAR *)src;
|
||||
dest->attr = screen_buffer->attr;
|
||||
break;
|
||||
default:
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (i && screen_buffer == screen_buffer->input->active)
|
||||
{
|
||||
struct condrv_renderer_event evt;
|
||||
evt.event = CONSOLE_RENDERER_UPDATE_EVENT;
|
||||
memset(&evt.u, 0, sizeof(evt.u));
|
||||
evt.u.update.top = params->y;
|
||||
evt.u.update.bottom = params->width
|
||||
? min( params->y + entry_cnt / params->width, screen_buffer->height ) - 1
|
||||
: params->y + (params->x + i - 1) / screen_buffer->width;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
|
||||
if (get_reply_max_size() == sizeof(SMALL_RECT))
|
||||
{
|
||||
SMALL_RECT region;
|
||||
region.Left = params->x;
|
||||
region.Top = params->y;
|
||||
region.Right = min( params->x + params->width, screen_buffer->width ) - 1;
|
||||
region.Bottom = min( params->y + entry_cnt / params->width, screen_buffer->height ) - 1;
|
||||
set_reply_data( ®ion, sizeof(region) );
|
||||
}
|
||||
else set_reply_data( &i, sizeof(i) );
|
||||
}
|
||||
|
||||
/* fill a screen buffer with uniform data */
|
||||
static int fill_console_output( struct screen_buffer *screen_buffer, char_info_t data,
|
||||
enum char_info_mode mode, int x, int y, int count, int wrap )
|
||||
{
|
||||
int i;
|
||||
char_info_t *end, *dest = screen_buffer->data + y * screen_buffer->width + x;
|
||||
|
||||
if (y >= screen_buffer->height) return 0;
|
||||
|
||||
if (wrap)
|
||||
end = screen_buffer->data + screen_buffer->height * screen_buffer->width;
|
||||
else
|
||||
end = screen_buffer->data + (y+1) * screen_buffer->width;
|
||||
|
||||
if (count > end - dest) count = end - dest;
|
||||
|
||||
switch(mode)
|
||||
{
|
||||
case CHAR_INFO_MODE_TEXT:
|
||||
for (i = 0; i < count; i++) dest[i].ch = data.ch;
|
||||
break;
|
||||
case CHAR_INFO_MODE_ATTR:
|
||||
for (i = 0; i < count; i++) dest[i].attr = data.attr;
|
||||
break;
|
||||
case CHAR_INFO_MODE_TEXTATTR:
|
||||
for (i = 0; i < count; i++) dest[i] = data;
|
||||
break;
|
||||
case CHAR_INFO_MODE_TEXTSTDATTR:
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
dest[i].ch = data.ch;
|
||||
dest[i].attr = screen_buffer->attr;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (count && screen_buffer == screen_buffer->input->active)
|
||||
{
|
||||
struct condrv_renderer_event evt;
|
||||
evt.event = CONSOLE_RENDERER_UPDATE_EVENT;
|
||||
memset(&evt.u, 0, sizeof(evt.u));
|
||||
evt.u.update.top = y;
|
||||
evt.u.update.bottom = (y * screen_buffer->width + x + count - 1) / screen_buffer->width;
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
/* scroll parts of a screen buffer */
|
||||
static void scroll_console_output( struct screen_buffer *screen_buffer, int xsrc, int ysrc, int xdst, int ydst,
|
||||
int w, int h, const rectangle_t *clip, char_info_t fill )
|
||||
{
|
||||
struct condrv_renderer_event evt;
|
||||
rectangle_t src, dst;
|
||||
int x, y;
|
||||
|
||||
src.left = max( xsrc, clip->left );
|
||||
src.top = max( ysrc, clip->top );
|
||||
src.right = min( xsrc + w - 1, clip->right );
|
||||
src.bottom = min( ysrc + h - 1, clip->bottom );
|
||||
|
||||
dst.left = xdst;
|
||||
dst.top = ydst;
|
||||
dst.right = xdst + w - 1;
|
||||
dst.bottom = ydst + h - 1;
|
||||
|
||||
if (dst.left < clip->left)
|
||||
{
|
||||
xsrc += clip->left - dst.left;
|
||||
w -= clip->left - dst.left;
|
||||
dst.left = clip->left;
|
||||
}
|
||||
if (dst.top < clip->top)
|
||||
{
|
||||
ysrc += clip->top - dst.top;
|
||||
h -= clip->top - dst.top;
|
||||
dst.top = clip->top;
|
||||
}
|
||||
if (dst.right > clip->right) w -= dst.right - clip->right;
|
||||
if (dst.bottom > clip->bottom) h -= dst.bottom - clip->bottom;
|
||||
|
||||
if (w > 0 && h > 0)
|
||||
{
|
||||
if (ysrc < ydst)
|
||||
{
|
||||
for (y = h; y > 0; y--)
|
||||
{
|
||||
memcpy( &screen_buffer->data[(dst.top + y - 1) * screen_buffer->width + dst.left],
|
||||
&screen_buffer->data[(ysrc + y - 1) * screen_buffer->width + xsrc],
|
||||
w * sizeof(screen_buffer->data[0]) );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
/* we use memmove here because when psrc and pdst are the same,
|
||||
* copies are done on the same row, so the dst and src blocks
|
||||
* can overlap */
|
||||
memmove( &screen_buffer->data[(dst.top + y) * screen_buffer->width + dst.left],
|
||||
&screen_buffer->data[(ysrc + y) * screen_buffer->width + xsrc],
|
||||
w * sizeof(screen_buffer->data[0]) );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (y = src.top; y <= src.bottom; y++)
|
||||
{
|
||||
int left = src.left;
|
||||
int right = src.right;
|
||||
if (dst.top <= y && y <= dst.bottom)
|
||||
{
|
||||
if (dst.left <= src.left) left = max( left, dst.right + 1 );
|
||||
if (dst.left >= src.left) right = min( right, dst.left - 1 );
|
||||
}
|
||||
for (x = left; x <= right; x++) screen_buffer->data[y * screen_buffer->width + x] = fill;
|
||||
}
|
||||
|
||||
/* FIXME: this could be enhanced, by signalling scroll */
|
||||
evt.event = CONSOLE_RENDERER_UPDATE_EVENT;
|
||||
memset(&evt.u, 0, sizeof(evt.u));
|
||||
evt.u.update.top = min( src.top, dst.top );
|
||||
evt.u.update.bottom = max( src.bottom, dst.bottom );
|
||||
console_input_events_append( screen_buffer->input, &evt );
|
||||
}
|
||||
|
||||
static void console_server_dump( struct object *obj, int verbose )
|
||||
{
|
||||
assert( obj->ops == &console_server_ops );
|
||||
|
@ -1942,126 +1430,6 @@ static int screen_buffer_ioctl( struct fd *fd, ioctl_code_t code, struct async *
|
|||
|
||||
switch (code)
|
||||
{
|
||||
case IOCTL_CONDRV_GET_MODE:
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_reply_max_size() != sizeof(screen_buffer->mode))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
return set_reply_data( &screen_buffer->mode, sizeof(screen_buffer->mode) ) != NULL;
|
||||
|
||||
case IOCTL_CONDRV_SET_MODE:
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_req_data_size() != sizeof(screen_buffer->mode))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
screen_buffer->mode = *(unsigned int *)get_req_data();
|
||||
return 1;
|
||||
|
||||
case IOCTL_CONDRV_READ_OUTPUT:
|
||||
{
|
||||
const struct condrv_output_params *params = get_req_data();
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_req_data_size() != sizeof(*params))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (console_input_is_bare( screen_buffer->input ))
|
||||
{
|
||||
set_error( STATUS_OBJECT_TYPE_MISMATCH );
|
||||
return 0;
|
||||
}
|
||||
read_console_output( screen_buffer, params->x, params->y, params->mode, params->width );
|
||||
return !get_error();
|
||||
}
|
||||
|
||||
case IOCTL_CONDRV_WRITE_OUTPUT:
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_req_data_size() < sizeof(struct condrv_output_params) ||
|
||||
(get_reply_max_size() != sizeof(SMALL_RECT) && get_reply_max_size() != sizeof(unsigned int)))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (console_input_is_bare( screen_buffer->input ))
|
||||
{
|
||||
set_error( STATUS_OBJECT_TYPE_MISMATCH );
|
||||
return 0;
|
||||
}
|
||||
write_console_output( screen_buffer, get_req_data(), get_req_data_size() - sizeof(struct condrv_output_params) );
|
||||
return !get_error();
|
||||
|
||||
case IOCTL_CONDRV_GET_OUTPUT_INFO:
|
||||
{
|
||||
struct condrv_output_info *info;
|
||||
data_size_t size;
|
||||
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
size = min( sizeof(*info) + screen_buffer->font.face_len, get_reply_max_size() );
|
||||
if (size < sizeof(*info))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (!(info = set_reply_data_size( size ))) return 0;
|
||||
|
||||
info->cursor_size = screen_buffer->cursor_size;
|
||||
info->cursor_visible = screen_buffer->cursor_visible;
|
||||
info->cursor_x = screen_buffer->cursor_x;
|
||||
info->cursor_y = screen_buffer->cursor_y;
|
||||
info->width = screen_buffer->width;
|
||||
info->height = screen_buffer->height;
|
||||
info->attr = screen_buffer->attr;
|
||||
info->popup_attr = screen_buffer->popup_attr;
|
||||
info->win_left = screen_buffer->win.left;
|
||||
info->win_top = screen_buffer->win.top;
|
||||
info->win_right = screen_buffer->win.right;
|
||||
info->win_bottom = screen_buffer->win.bottom;
|
||||
info->max_width = screen_buffer->max_width;
|
||||
info->max_height = screen_buffer->max_height;
|
||||
info->font_width = screen_buffer->font.width;
|
||||
info->font_height = screen_buffer->font.height;
|
||||
info->font_weight = screen_buffer->font.weight;
|
||||
info->font_pitch_family = screen_buffer->font.pitch_family;
|
||||
memcpy( info->color_map, screen_buffer->color_map, sizeof(info->color_map) );
|
||||
size -= sizeof(*info);
|
||||
if (size) memcpy( info + 1, screen_buffer->font.face_name, size );
|
||||
return 1;
|
||||
}
|
||||
|
||||
case IOCTL_CONDRV_SET_OUTPUT_INFO:
|
||||
{
|
||||
const struct condrv_output_info_params *params = get_req_data();
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_req_data_size() < sizeof(*params))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (!screen_buffer->input)
|
||||
{
|
||||
set_error( STATUS_INVALID_HANDLE );
|
||||
return 0;
|
||||
}
|
||||
return set_output_info( screen_buffer, params, get_req_data_size() - sizeof(*params) );
|
||||
}
|
||||
|
||||
case IOCTL_CONDRV_ACTIVATE:
|
||||
if (!screen_buffer->input)
|
||||
{
|
||||
|
@ -2072,68 +1440,6 @@ static int screen_buffer_ioctl( struct fd *fd, ioctl_code_t code, struct async *
|
|||
set_active_screen_buffer( screen_buffer->input, screen_buffer );
|
||||
return 1;
|
||||
|
||||
case IOCTL_CONDRV_FILL_OUTPUT:
|
||||
{
|
||||
const struct condrv_fill_output_params *params = get_req_data();
|
||||
char_info_t data;
|
||||
DWORD written;
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
if (get_req_data_size() != sizeof(*params) ||
|
||||
(get_reply_max_size() && get_reply_max_size() != sizeof(written)))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
data.ch = params->ch;
|
||||
data.attr = params->attr;
|
||||
written = fill_console_output( screen_buffer, data, params->mode,
|
||||
params->x, params->y, params->count, params->wrap );
|
||||
if (written && get_reply_max_size() == sizeof(written))
|
||||
set_reply_data( &written, sizeof(written) );
|
||||
return !get_error();
|
||||
}
|
||||
|
||||
case IOCTL_CONDRV_SCROLL:
|
||||
{
|
||||
const struct condrv_scroll_params *params = get_req_data();
|
||||
rectangle_t clip;
|
||||
|
||||
if (screen_buffer->input && screen_buffer->input->server)
|
||||
return queue_host_ioctl( screen_buffer->input->server, code, screen_buffer->id,
|
||||
async, &screen_buffer->ioctl_q );
|
||||
|
||||
if (get_req_data_size() != sizeof(*params))
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
if (console_input_is_bare( screen_buffer->input ) || !screen_buffer->input)
|
||||
{
|
||||
set_error( STATUS_OBJECT_TYPE_MISMATCH );
|
||||
return 0;
|
||||
}
|
||||
clip.left = max( params->clip.Left, 0 );
|
||||
clip.top = max( params->clip.Top, 0 );
|
||||
clip.right = min( params->clip.Right, screen_buffer->width - 1 );
|
||||
clip.bottom = min( params->clip.Bottom, screen_buffer->height - 1 );
|
||||
if (clip.left > clip.right || clip.top > clip.bottom || params->scroll.Left < 0 || params->scroll.Top < 0 ||
|
||||
params->scroll.Right >= screen_buffer->width || params->scroll.Bottom >= screen_buffer->height ||
|
||||
params->scroll.Right < params->scroll.Left || params->scroll.Top > params->scroll.Bottom ||
|
||||
params->origin.X < 0 || params->origin.X >= screen_buffer->width || params->origin.Y < 0 ||
|
||||
params->origin.Y >= screen_buffer->height)
|
||||
{
|
||||
set_error( STATUS_INVALID_PARAMETER );
|
||||
return 0;
|
||||
}
|
||||
|
||||
scroll_console_output( screen_buffer, params->scroll.Left, params->scroll.Top, params->origin.X, params->origin.Y,
|
||||
params->scroll.Right - params->scroll.Left + 1, params->scroll.Bottom - params->scroll.Top + 1,
|
||||
&clip, params->fill );
|
||||
return !get_error();
|
||||
}
|
||||
|
||||
default:
|
||||
if (!screen_buffer->input || !screen_buffer->input->server || code >> 16 != FILE_DEVICE_CONSOLE)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue