summaryrefslogtreecommitdiffhomepage
path: root/src/console
diff options
context:
space:
mode:
authormidipix <writeonce@midipix.org>2016-07-12 12:34:03 -0400
committermidipix <writeonce@midipix.org>2016-07-21 03:47:27 -0400
commit029664574763aa7725e490b2754aa00e74d8fdce (patch)
treeffc14a8b0c69d58ac0b000bd290b2ae8bef8563c /src/console
parent4219632f84a58b413477e2d82b5768a42036d7cd (diff)
downloadptycon-029664574763aa7725e490b2754aa00e74d8fdce.tar.bz2
ptycon-029664574763aa7725e490b2754aa00e74d8fdce.tar.xz
console: added initial reader (terminal-to-client) logic.
Diffstat (limited to 'src/console')
-rw-r--r--src/console/ptyc_console_reader.c158
1 files changed, 156 insertions, 2 deletions
diff --git a/src/console/ptyc_console_reader.c b/src/console/ptyc_console_reader.c
index 3afab13..0ce4900 100644
--- a/src/console/ptyc_console_reader.c
+++ b/src/console/ptyc_console_reader.c
@@ -12,8 +12,162 @@
#include <ptycon/ptycon.h>
#include "ptycon_driver_impl.h"
+typedef nt_unicode_conversion_params_utf16_to_utf8 uc_conv_params;
+
+static size_t ptyc_translate_keyboard_event(
+ nt_input_record * rec,
+ unsigned char * ch,
+ wchar16_t * wch)
+{
+ wchar16_t src[2];
+ wchar16_t recwch;
+ uint32_t nbytes;
+ uc_conv_params params = {0,0,0,0,0,0,0,0,0};
+
+ if (!rec->key_event.key_down)
+ return 0;
+
+ if (!(recwch = rec->key_event.unicode_char))
+ return 0;
+
+ if (*wch) {
+ if ((recwch < 0xDC00) || (recwch >= 0xE000)) {
+ *wch = 0;
+ return 0;
+ } else {
+ src[0] = *wch;
+ src[1] = recwch;
+ *wch = 0;
+ nbytes = 2*sizeof(wchar16_t);
+ }
+ } else if ((recwch >= 0xD800) && (recwch < 0xDC00)) {
+ *wch = recwch;
+ return 0;
+
+ } else {
+ src[0] = recwch;
+ nbytes = sizeof(wchar16_t);
+ }
+
+ params.src = src;
+ params.src_size_in_bytes = nbytes;
+ params.dst = ch;
+ params.dst_size_in_bytes = 4;
+
+ ntapi->uc_convert_unicode_stream_utf16_to_utf8(
+ &params);
+
+ return params.bytes_written;
+}
+
+static size_t ptyc_translate_mouse_event(
+ nt_input_record * rec,
+ unsigned char * ch)
+{
+ (void)rec;
+ (void)ch;
+ return 0;
+}
+
+static size_t ptyc_translate_window_event(nt_input_record * rec)
+{
+ (void)rec;
+ return 0;
+}
+
+static size_t ptyc_translate_menu_event(nt_input_record * rec)
+{
+ (void)rec;
+ return 0;
+}
+
+static size_t ptyc_translate_focus_event(nt_input_record * rec)
+{
+ (void)rec;
+ return 0;
+}
+
+static size_t ptyc_translate_event(
+ nt_input_record * rec,
+ unsigned char * ch,
+ wchar16_t * wch)
+{
+ switch (rec->event_type) {
+ case NT_KEY_EVENT:
+ return ptyc_translate_keyboard_event(
+ rec,ch,wch);
+
+ case NT_MOUSE_EVENT:
+ return ptyc_translate_mouse_event(
+ rec,ch);
+
+ case NT_WINDOW_BUFFER_SIZE_EVENT:
+ return ptyc_translate_window_event(rec);
+
+ case NT_MENU_EVENT:
+ return ptyc_translate_menu_event(rec);
+
+ case NT_FOCUS_EVENT:
+ return ptyc_translate_focus_event(rec);
+ }
+
+ return 0;
+}
+
int ptyc_console_reader(struct ptyc_driver_ctx_impl * ictx)
{
- (void)ictx;
- return ntapi->tt_wait_for_dummy_event();
+ int32_t status;
+ void * hwait;
+ nt_iosb iosb;
+ uint32_t nevents;
+ size_t nbytes;
+ wchar16_t wch;
+ unsigned char * ch;
+ unsigned i;
+
+ if ((status = ntapi->tt_create_private_event(
+ &hwait,
+ NT_NOTIFICATION_EVENT,
+ NT_EVENT_NOT_SIGNALED)))
+ return status;
+
+ do {
+ if (!(ntcon->read_console_input_utf16(
+ ictx->tctx.hin,
+ ictx->tctx.input.events,
+ PTYC_RAW_EVENTS,
+ &nevents)))
+ return NT_STATUS_ALREADY_DISCONNECTED;
+
+ for (ch=ictx->tctx.input.stream, i=0; i<nevents; i++)
+ ch += ptyc_translate_event(
+ &ictx->tctx.input.events[i],
+ ch,&wch);
+
+ nbytes = ch - ictx->tctx.input.stream;
+ ch = ictx->tctx.input.stream;
+
+ for (; nbytes; ) {
+ status = ntapi->pty_write(
+ ictx->cctx.hptm,
+ hwait,0,0,
+ &iosb,
+ ch,nbytes,
+ 0,0);
+
+ if (status == NT_STATUS_PENDING)
+ status = ntapi->zw_wait_for_single_object(
+ hwait,NT_SYNC_ALERTABLE,0);
+
+ if (status || iosb.status) {
+ ntapi->zw_close(hwait);
+ return status ? status : iosb.status;
+ }
+
+ ch += iosb.info;
+ nbytes -= iosb.info;
+ }
+ } while (1);
+
+ return NT_STATUS_INTERNAL_ERROR;
}