+#define con_write(tcb, y, x, str, n) con_write8(tcb, y, x, str, n)
+#endif
+
+#if EXP_OPTIMIZE
+/*
+ * Comparing new/current screens, determine the last column-index for a change
+ * beginning on the given row,col position. Unlike a serial terminal, there is
+ * no cost for "moving" the "cursor" on the line as we update it.
+ */
+static int
+find_end_of_change(SCREEN *sp, int row, int col)
+{
+ int result = col;
+ struct ldat *curdat = CurScreen(sp)->_line + row;
+ struct ldat *newdat = NewScreen(sp)->_line + row;
+
+ while (col <= newdat->lastchar) {
+#if USE_WIDEC_SUPPORT
+ if (isWidecExt(curdat->text[col]) || isWidecExt(newdat->text[col])) {
+ result = col;
+ } else if (memcmp(&curdat->text[col],
+ &newdat->text[col],
+ sizeof(curdat->text[0]))) {
+ result = col;
+ } else {
+ break;
+ }
+#else
+ if (curdat->text[col] != newdat->text[col]) {
+ result = col;
+ } else {
+ break;
+ }
+#endif
+ ++col;
+ }
+ return result;
+}
+
+/*
+ * Given a row,col position at the end of a change-chunk, look for the
+ * beginning of the next change-chunk.
+ */
+static int
+find_next_change(SCREEN *sp, int row, int col)
+{
+ struct ldat *curdat = CurScreen(sp)->_line + row;
+ struct ldat *newdat = NewScreen(sp)->_line + row;
+ int result = newdat->lastchar + 1;
+
+ while (++col <= newdat->lastchar) {
+#if USE_WIDEC_SUPPORT
+ if (isWidecExt(curdat->text[col]) != isWidecExt(newdat->text[col])) {
+ result = col;
+ break;
+ } else if (memcmp(&curdat->text[col],
+ &newdat->text[col],
+ sizeof(curdat->text[0]))) {
+ result = col;
+ break;
+ }
+#else
+ if (curdat->text[col] != newdat->text[col]) {
+ result = col;
+ break;
+ }
+#endif
+ }
+ return result;
+}
+
+#define EndChange(first) \
+ find_end_of_change(sp, y, first)
+#define NextChange(last) \
+ find_next_change(sp, y, last)
+
+#endif /* EXP_OPTIMIZE */