From bd25d537c3f870cace43acded859bf16d8a1ea44 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C2=A8Rene=20Richarz?= <¨rene.richarz@bluewin.ch¨> Date: Fri, 29 Mar 2019 11:33:25 +0100 Subject: [PATCH] improved robustness against 4014 codes --- main.c | 33 +++++----- makefile | 3 + tek4010 | Bin 24412 -> 24620 bytes tek4010.c | 185 +++++++++++++++++++++++++++++++----------------------- tek4010.h | 2 +- 5 files changed, 128 insertions(+), 95 deletions(-) diff --git a/main.c b/main.c index 3eb3b52..f107269 100644 --- a/main.c +++ b/main.c @@ -44,7 +44,6 @@ extern FILE *putKeys; -static cairo_surface_t *global_surface, *global_surface2; static int global_firstcall; int globalClearPersistent; @@ -61,14 +60,14 @@ static gboolean on_draw_event(GtkWidget *widget, cairo_t *cr, static gboolean on_timer_event(GtkWidget *widget) { if (tek4010_on_timer_event()) - gtk_widget_queue_draw(widget); + gtk_widget_queue_draw(widget); return TRUE; } static gboolean clicked(GtkWidget *widget, GdkEventButton *event, gpointer user_data) { if (tek4010_clicked(event->button, event->x, event->y)) - gtk_widget_queue_draw(widget); + gtk_widget_queue_draw(widget); return TRUE; } @@ -81,28 +80,30 @@ static void on_quit_event() static void do_drawing(cairo_t *cr, GtkWidget *widget) { - int width = WINDOW_WIDTH; // we do not use actual window size here - int height = WINDOW_HEIGHT; // because global_surface does not change size + int width = WINDOW_WIDTH; // we do not use actual window size here + int height = WINDOW_HEIGHT; // because surfaces does not change size + + static cairo_surface_t *permanent_surface, *temporary_surface; if (global_firstcall) { - global_surface = cairo_surface_create_similar(cairo_get_target(cr), + permanent_surface = cairo_surface_create_similar(cairo_get_target(cr), CAIRO_CONTENT_COLOR_ALPHA, width, height); - global_surface2 = cairo_surface_create_similar(cairo_get_target(cr), + temporary_surface = cairo_surface_create_similar(cairo_get_target(cr), CAIRO_CONTENT_COLOR_ALPHA, width, height); } - cairo_t *surface_cr = cairo_create(global_surface); - cairo_t *surface2_cr = cairo_create(global_surface2); - tek4010_draw(surface_cr, surface2_cr, width, height, global_firstcall); + cairo_t *permanent_cr = cairo_create(permanent_surface); + cairo_t *temporary_cr = cairo_create(temporary_surface); + tek4010_draw(permanent_cr, temporary_cr, width, height, global_firstcall); global_firstcall = FALSE; - cairo_set_source_surface(cr, global_surface, 0, 0); + cairo_set_source_surface(cr, permanent_surface, 0, 0); cairo_paint(cr); - cairo_set_source_surface(cr, global_surface2, 0, 0); + cairo_set_source_surface(cr, temporary_surface, 0, 0); cairo_paint(cr); - cairo_destroy(surface_cr); - cairo_destroy(surface2_cr); + cairo_destroy(permanent_cr); + cairo_destroy(temporary_cr); } static void on_key_press(GtkWidget *widget, GdkEventKey *event, gpointer user_data) @@ -115,6 +116,7 @@ static void on_key_press(GtkWidget *widget, GdkEventKey *event, gpointer user_da (event->keyval == 0xFF56)) // "page down" key { globalClearPersistent = 1; + gtk_widget_queue_draw(widget); return; } @@ -125,6 +127,7 @@ static void on_key_press(GtkWidget *widget, GdkEventKey *event, gpointer user_da if ((event->keyval == 0xFF51) || // "left arrow" key (event->keyval == 0xFF52)) { // "up arrow" key globalClearPersistent = 1; + gtk_widget_queue_draw(widget); return; } else @@ -157,7 +160,7 @@ int main (int argc, char *argv[]) gtk_widget_add_events(window, GDK_BUTTON_PRESS_MASK); gtk_widget_add_events(window, GDK_KEY_PRESS_MASK); - g_signal_connect(G_OBJECT(darea), "draw", G_CALLBACK(on_draw_event), NULL); + g_signal_connect(G_OBJECT(darea), "draw", G_CALLBACK(on_draw_event), NULL); g_signal_connect(G_OBJECT(window), "destroy", G_CALLBACK(on_quit_event), NULL); g_signal_connect(G_OBJECT(window), "button-press-event", G_CALLBACK(clicked), NULL); g_signal_connect(G_OBJECT(window), "key_press_event", G_CALLBACK(on_key_press), NULL); diff --git a/makefile b/makefile index 8b594aa..725b721 100644 --- a/makefile +++ b/makefile @@ -6,3 +6,6 @@ all: tek4010 tek4010: main.c tek4010.c tek4010.h main.h gcc -o tek4010 main.c tek4010.c tek4010.h main.h $(LIBS) $(CFLAGS) + +install: + cp tek4010 ~/bin \ No newline at end of file diff --git a/tek4010 b/tek4010 index 10fd9e845a54e8f0bc045b6d85a788512a42547d..9cfaa6696c143274b206c3adb629bac7040ea891 100755 GIT binary patch delta 7953 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 EFV?nu^8f$< delta 7595 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 fKO+CS%o|% #include @@ -28,15 +26,13 @@ extern void gtk_main_quit(); extern int globalClearPersistent; -int noexit; -/* not yet used, for dsrk mode -int memx1[MEM], memy1[MEM], memx2[MEM], memy2[MEM]; -float memv[MEM]; -*/ +int noexit = 0; +int showCursor; +int isBrightSpot = 0; int count = 0; -static int x0,y0,x2,y2,xh,xl,yh,yl,xy2014; +static int x0,y0,x2,y2,xh,xl,yh,yl,xy4014; // mode handles the current state of the emulator: // @@ -69,14 +65,18 @@ int getDataPipe[2]; FILE *putKeys; int putKeysPipe[2]; -int getk() -// get a char, if available, otherwise return -1 -// When called for the first time, a child process for rsh is forked -// and communication between parent and child are established +int isInput() +// is char available on getDataPipe? { int bytesWaiting; ioctl(getDataPipe[0], FIONREAD, &bytesWaiting); - if (bytesWaiting > 0) + return bytesWaiting; +} + +int getInputChar() +// get a char from getDataPipe, if available, otherwise return -1 +{ + if (isInput()) return getc(getData); else return -1; @@ -96,8 +96,9 @@ void tek4010_init(int argc, char* argv[]) noexit = 1; argc--; } - else - noexit = 0; + + // A child process for rsh is forked ans communication + // between parent and child are established // expand argv[1] to full path and check, whether it exists char *str = (char *) malloc(bufsize * sizeof(char)); @@ -202,7 +203,11 @@ int tek4010_on_timer_event() // is called every TIMER-INTERVAL milliseconds // if the function returns 1, the window is redrawn by calling applicatin_draw { - return 1; + // if there is a char available on the imput stream + // or there is still a bright spot, return 1 to ask for + // one more redraw + + return (isBrightSpot || isInput); } int tek4010_clicked(int button, int x, int y) @@ -221,34 +226,40 @@ void tek4010_quit() pclose(getData); } +int checkExitFromGraphics(int ch) +// test for exit from graphics character +{ + if ((ch==31) || (ch==13) || (ch==27) || (ch==12)) { + mode = 0; + if (DEBUG) printf("Leaving graphics mode\n"); + showCursor = 0; + if (ch == 12) globalClearPersistent = 1; + return 1; + } + else return 0; +} void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) // draw onto the main window using cairo // width is the actual width of the main window // height is the actual height of the main window -// surface1 is used for persistent drawing, surface2 for faiding drawing +// cr is used for persistent drawing, cr2 for temporary drawing { int ch; int todo; char s[2]; - int showCursor = 1; + + showCursor = 1; + isBrightSpot = 0; -/* if (first) { - for (int i=0; i=1) && (mode <=9)) - if ((ch==31) || (ch==13) || (ch==27) || (ch==12)) { - mode = 0; // exit from graphics mode - if (DEBUG) printf("Leaving graphics mode\n"); - showCursor = 0; - ch = -1; - } if (mode == 31) { // printf("ANSI escape mode 31, ch=%02x\n",ch); if ((ch>='0') && (ch<='9')) mode = 30; } int tag = ch >> 5; - - // this overwrites the extra data byte of the 4014 for the - // first dark mode coordinates and stores it for further use - if ((mode == 3) && (tag == 3)) { - mode = 2; - xy2014 = yl; - if (DEBUG) printf("4014 coordinates, overwrite last value\n"); - } - if ((mode>=1)&&(mode<=8)) { + if ((mode >= 1) && (mode <= 8)) { + + checkExitFromGraphics(ch); + + // handle skipped coordinate bytes + // this cannot be done in switch(mode) below, because multiple bytes + // can be switched and the current byte must be executed after a mode change + + if ((mode == 3) && (tag == 3)) { + // this overwrites the extra data byte of the 4014 for the + // first dark mode coordinates and stores it for further use + mode = 2; + xy4014 = yl; + if (DEBUG) printf("4014 coordinates, overwrite last value\n"); + } + if ((mode == 5) && (ch == 29)) { mode = 1; return; } if (ch == 30) { - if (DEBUG) printf("Leaving graphics mode\n"); - mode = 0; return; - } - if (tag == 0) { - return; + if (DEBUG) printf("Starting incremental plot mode (4014)\n"); + mode = 40; return; } if (DEBUG) { @@ -326,39 +331,53 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) printf("mode=%d,tag=%d-L-val=%d\n", mode,tag, ch & 31); } - - if (tag > 0) { // bytes identified by tag, some can be skipped - if ((mode == 5) && (tag != 1)) mode = 6; - + + if (tag == 0) { + return; // each coordinate byte must have a tag. If not, ignore + } + + if ((mode == 5) && (tag != 1)) mode = 6; + + if ((mode == 7) && (tag == 3)) { // this overwrites the extra data byte of the 4014 for the // persistent mode ccordinates and stores it for further use - if ((mode == 7) && (tag == 3)) { - mode = 6; - xy2014 = yl; - if (DEBUG) - printf("4014 coordinates, overwrite last value\n"); - } - - if ((mode == 6) && (tag != 3)) mode = 7; - if ((mode == 7) && (tag != 1)) mode = 8; + mode = 6; + xy4014 = yl; + if (DEBUG) + printf("4014 coordinates, overwrite last value\n"); } + + if ((mode == 6) && (tag != 3)) mode = 7; + + if ((mode == 7) && (tag != 1)) mode = 8; + } - switch (mode) { - case 1: yh = 32 * (ch & 31); mode++; break; - case 2: yl = (ch & 31); y0 = yh + yl; mode++; break; - case 3: xh = 32 * (ch & 31); mode++; break; - case 4: xl = (ch & 31); x0= xh + xl; mode++; - if (DEBUG) printf("***** Moving to (%d,%d)\n",x0,y0); + switch (mode) { + case 1: yh = 32 * (ch & 31); mode++; + break; + case 2: yl = (ch & 31); y0 = yh + yl; mode++; + break; + case 3: xh = 32 * (ch & 31); mode++; + break; + case 4: xl = (ch & 31); x0= xh + xl; mode++; + if (DEBUG) printf("***** Moving to (%d,%d)\n",x0,y0); + break; + case 5: if (ch == 29) mode = 1; + else { + yh = 32 * (ch & 31); mode++; + } + break; + case 6: yl = (ch & 31); mode++; + break; + case 7: xh = 32 * (ch & 31); mode++; break; - case 5: yh = 32 * (ch & 31); mode++; break; - case 6: yl = (ch & 31); mode++; break; - case 7: xh = 32 * (ch & 31); mode++; break; case 8: xl = (ch & 31); x2 = xh + xl; y2 = yh + yl; - if (DEBUG) printf("tag=%d,***** Drawing vector to (%d,%d)\n",tag,x2,y2); + if (DEBUG) printf("tag=%d,***** Drawing vector to (%d,%d)\n", + tag, x2, y2); cairo_move_to(cr, x0, WINDOW_HEIGHT - y0); cairo_line_to(cr, x2, WINDOW_HEIGHT - y2); cairo_stroke (cr); @@ -366,6 +385,7 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) cairo_line_to(cr2, x2, WINDOW_HEIGHT - y2); cairo_stroke (cr2); showCursor = 0; + isBrightSpot = 1; // for speed reasons, do not update screen right away // if many very small verctors are drawn @@ -379,7 +399,7 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) y0 = y2; mode = 5; break; - case 30: // handle escape sequencies + case 30: // handle escape sequencies if (DEBUG) printf("Escape mode, ch=%02X\n",ch); switch (ch) { case 12: @@ -414,6 +434,9 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) break; } break; + case 40: // used to ignore certain 4014 sequencies + if (ch == 31) mode = 0; // leave this mode + break; default: switch (ch) { case 0: break; case EOF: break; @@ -446,6 +469,9 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) case 29: // group separator mode = 1; break; + case 30: // record separator + mode = 40; + break; case 31: // US, leave graphics mode mode = 0; break; @@ -459,6 +485,7 @@ void tek4010_draw(cairo_t *cr, cairo_t *cr2, int width, int height, int first) cairo_move_to(cr2, x0, WINDOW_HEIGHT - y0 + 4); cairo_show_text(cr2, s); x0 += hDotsPerChar; + isBrightSpot = 1; todo--; } break; diff --git a/tek4010.h b/tek4010.h index 97ecfc1..39f00e1 100644 --- a/tek4010.h +++ b/tek4010.h @@ -4,5 +4,5 @@ #define WINDOW_NAME "Tektronix 4010" // name of main window #define ICON_NAME "" // path to icon for window -#define TIME_INTERVAL 50 // time interval for timer function in msec +#define TIME_INTERVAL 25 // time interval for timer function in msec // 0 means no timer function