Scandum 5 سال پیش
والد
کامیت
b36056b325
33فایلهای تغییر یافته به همراه1054 افزوده شده و 1256 حذف شده
  1. 2 3
      NEWS
  2. 32 0
      SCRIPTS
  3. 15 57
      TODO
  4. 12 3
      mods/igr.mods
  5. 1 1
      src/buffer.c
  6. 39 176
      src/chat.c
  7. 39 0
      src/class.c
  8. 60 1
      src/command.c
  9. 97 0
      src/draw.c
  10. 14 9
      src/files.c
  11. 19 44
      src/gui.h
  12. 10 6
      src/help.c
  13. 13 1
      src/input.c
  14. 127 99
      src/list.c
  15. 11 7
      src/main.c
  16. 3 3
      src/mapper.c
  17. 13 1
      src/misc.c
  18. 44 15
      src/nest.c
  19. 6 6
      src/net.c
  20. 36 0
      src/scan.c
  21. 266 4
      src/screen.c
  22. 6 0
      src/session.c
  23. 0 1
      src/split.c
  24. 23 23
      src/substitute.c
  25. 0 340
      src/tables.c
  26. 29 91
      src/text.c
  27. 27 322
      src/tintin.h
  28. 2 2
      src/tokenize.c
  29. 1 1
      src/update.c
  30. 41 13
      src/utf8.c
  31. 1 1
      src/utils.c
  32. 55 10
      src/variable.c
  33. 10 16
      src/vt102.c

+ 2 - 3
NEWS

@@ -97,7 +97,7 @@ TinTin++ 2.01.90
 
 
     #prompt {text} {substitution} will stay the same.
     #prompt {text} {substitution} will stay the same.
     #prompt {text} {substitution} {0} will become invalid.
     #prompt {text} {substitution} {0} will become invalid.
-    #prompt {test] {substitution} {1} will write to the top line.
+    #prompt {text] {substitution} {1} will write to the top line.
     #prompt {text} {substitution} {-1} will write to the bottom / input line.
     #prompt {text} {substitution} {-1} will write to the bottom / input line.
     #prompt {text} {substitution} {-2} will write to the 2nd line from the
     #prompt {text} {substitution} {-2} will write to the 2nd line from the
        bottom, which is the default split line.
        bottom, which is the default split line.
@@ -216,7 +216,7 @@ TinTin++ 1.99.1
 TinTin++ 1.96.6
 TinTin++ 1.96.6
 ---------------
 ---------------
 
 
-    #PATHDIR is now specificly designed to hold a direction, the opposite
+    #PATHDIR is now specifically designed to hold a direction, the opposite
     direction, and the vector of said direction for the #MAP command.
     direction, and the vector of said direction for the #MAP command.
 
 
 
 
@@ -289,7 +289,6 @@ TinTin++ 1.88.0
 
 
 01) #FORMAT has been introduced and replaces a wide variety of commands.
 01) #FORMAT has been introduced and replaces a wide variety of commands.
 
 
-
 02) #MESSAGE, #CONFIG, #IGNORE, #DEBUG are all you need to configure tintin,
 02) #MESSAGE, #CONFIG, #IGNORE, #DEBUG are all you need to configure tintin,
     changes made with #CONFIG are written to file with #WRITE.
     changes made with #CONFIG are written to file with #WRITE.
 
 

+ 32 - 0
SCRIPTS

@@ -313,6 +313,38 @@
 
 
 #substitute {{\b[a-zA-Z]+\b}} {@spellcheck{%1}}
 #substitute {{\b[a-zA-Z]+\b}} {@spellcheck{%1}}
 
 
+#nop -------------------------------------------------------------------------
+#nop This function and substitution will add a speed reader to the split line
+#nop -------------------------------------------------------------------------
+
+#split
+
+#function spellcheck
+{
+        #format result %S %1;
+        #if {$result == 0}
+        {
+                #var result %1
+        };
+        #else
+        {
+                #var result <118>%1<900>
+        };
+        #list speedread ins -1 {$result}
+}
+
+#substitute {{\b[a-zA-Z]+\b}} {@spellcheck{%1}}
+
+#tick {speedread}
+{
+        #if {&{speedread[]}}
+        {
+                #draw tile -2 1 -2 20 {$speedread[1]};
+                #list speedread delete 1
+        }
+}
+{0.1}
+
 #nop -------------------------------------------------------------------------
 #nop -------------------------------------------------------------------------
 #nop This function tests the random number engine
 #nop This function tests the random number engine
 #nop -------------------------------------------------------------------------
 #nop -------------------------------------------------------------------------

+ 15 - 57
TODO

@@ -1,17 +1,17 @@
 * BUGS
 * BUGS
 
 
-  - might be \ handling issues in #format %w
+  - Look into escaped color codes in zmp, possibly msdp
+
+  - See about making @$var{} work.
+
+  - See about turning window close into a program termination event.
 
 
   - finish BUFFER_SIZE replacement.
   - finish BUFFER_SIZE replacement.
 
 
   - WSL faq: #system cmd.exe /c start notepad
   - WSL faq: #system cmd.exe /c start notepad
 
 
-  - str_ify ses->more_output
-
   - update msdp scripts with #line msdp feature
   - update msdp scripts with #line msdp feature
 
 
-  - update the FAQ, and online manual
-
   - refresh input on session switch
   - refresh input on session switch
 
 
   - swap arg1, arg2, arg for do_port
   - swap arg1, arg2, arg for do_port
@@ -27,8 +27,6 @@
 
 
 * STUFF THAT IS PROBABLY GONNA GET DONE
 * STUFF THAT IS PROBABLY GONNA GET DONE
 
 
-  - Editor
-
   - Finish port proxy support: resizing, input, security
   - Finish port proxy support: resizing, input, security
 
 
   - look into transparent drawing
   - look into transparent drawing
@@ -53,10 +51,7 @@
   - tabbing on directory structure.
   - tabbing on directory structure.
   - tabbing on dictionary
   - tabbing on dictionary
 
 
-  - Enhance #scan with a scan of the directory structure.
-
   - #map list {<exits>} breaks on rooms that have e mapped to eu.
   - #map list {<exits>} breaks on rooms that have e mapped to eu.
-
   - finish landmarks
   - finish landmarks
   - map sandbox mode support (flags to disable saving?)
   - map sandbox mode support (flags to disable saving?)
   - add ghosting to fix #map flag nofollow exit cmd issues?
   - add ghosting to fix #map flag nofollow exit cmd issues?
@@ -88,16 +83,13 @@
     #draw titanic
     #draw titanic
 
 
   - proper vt100 skip detection for improper color codes.
   - proper vt100 skip detection for improper color codes.
-  - look into VT100 / #split hybrid mode.
 
 
-  - I'll look and see if I can make { match both a { and \x7B as it's an annoying issue to debug.
+  - Make { match both a { and \x7B as it's an annoying issue to debug.
 
 
   - Add VT100 filter to make outside sources respect terminal size constraints, also needed to run bash in vsplit mode.
   - Add VT100 filter to make outside sources respect terminal size constraints, also needed to run bash in vsplit mode.
 
 
   - Remote script loading
   - Remote script loading
 
 
-  - make #path load bi-directional.
-
   - add class specific debug
   - add class specific debug
   - better class event and class size handling ?
   - better class event and class size handling ?
 
 
@@ -109,8 +101,6 @@
 
 
   - Add #log delete/remove option.
   - Add #log delete/remove option.
 
 
-  - See about filling COMMAND_LIST table.
-
   - See about adding SESSIONS to the list table.
   - See about adding SESSIONS to the list table.
 
 
   - Add debugger to syntax highlighter, substitution highlighing, 256 color support, and variable expansion.
   - Add debugger to syntax highlighter, substitution highlighing, 256 color support, and variable expansion.
@@ -130,16 +120,8 @@
 
 
   - Add JSON support to #scan
   - Add JSON support to #scan
 
 
-  - fix \x00 showme
-
-  - support strikethrough html logging.
-
   - see if #break 2 is possible, maybe #continue 2 as well.
   - see if #break 2 is possible, maybe #continue 2 as well.
 
 
-  - Add options to #cursor to implement custom behaviour.
-
-  - toggle global flags with #message all on, #debug all on, etc.
-
   - http://tintin.sourceforge.net/board/viewtopic.php?p=9625 (map undo issue) (not a big issue)
   - http://tintin.sourceforge.net/board/viewtopic.php?p=9625 (map undo issue) (not a big issue)
 
 
   - http://tintin.sourceforge.net/board/viewtopic.php?t=2339 (map area data)
   - http://tintin.sourceforge.net/board/viewtopic.php?t=2339 (map area data)
@@ -194,6 +176,8 @@
 
 
   - Allow converting tt++ scripts to C.
   - Allow converting tt++ scripts to C.
 
 
+  - session proxies
+
 --------------------------------------------------------------------------------
 --------------------------------------------------------------------------------
 
 
 * STUFF THAT MIGHT BE IMPLEMENTED
 * STUFF THAT MIGHT BE IMPLEMENTED
@@ -210,13 +194,9 @@
 
 
   - SGA disabling
   - SGA disabling
 
 
-  - CHARSET TELOPT support.
-
   - BINARY TELOPT support.
   - BINARY TELOPT support.
 
 
-  - Split pane scrollback (event system?)
-
-  - add #line gag {lines} option or #lines {lines} {gag}.
+  - add #line gag {lines} option
 
 
   - Add something like #log append $dir/logs/log.txt {%D %H:%M:%S}
   - Add something like #log append $dir/logs/log.txt {%D %H:%M:%S}
 
 
@@ -243,8 +223,6 @@
 
 
   - There's a bug with prompt repetitions with packet patch set.
   - There's a bug with prompt repetitions with packet patch set.
 
 
-  - garbage collection for deleted nodes.
-
   - Deal with escaping { } / ; in #script variables.
   - Deal with escaping { } / ; in #script variables.
 
 
   - Make tintin char setting by session instead of global.
   - Make tintin char setting by session instead of global.
@@ -291,36 +269,21 @@
 
 
 --------------------------------------------------------------------------------
 --------------------------------------------------------------------------------
 
 
-
-* MISCELANEOUS
-
-- look into Launchpad PPA
-
---------------------------------------------------------------------------------
-
 * STUFF FOR A RAINY DAY
 * STUFF FOR A RAINY DAY
 
 
-- nestable functions
-
-- Buffer safe strings.
-
 - Fix up ipv6 support in chat.
 - Fix up ipv6 support in chat.
 
 
 - Look into packet defragmentation for chat.
 - Look into packet defragmentation for chat.
 
 
-- Color code compression, particularly useful with vt map drawing.
-
-- Events for prompt lines.
-
-- Lua scripting
-
 - Look into using speech-dispatcher for text to speech.
 - Look into using speech-dispatcher for text to speech.
 
 
-- MXP script http://tintin.sourceforge.net/board/viewtopic.php?t=1396
-
 - Add %U (upper) %L (lower) support.
 - Add %U (upper) %L (lower) support.
   check https://www.boost.org/doc/libs/1_50_0/libs/regex/doc/html/boost_regex/syntax/basic_extended.html
   check https://www.boost.org/doc/libs/1_50_0/libs/regex/doc/html/boost_regex/syntax/basic_extended.html
 
 
+- cursor extension for vim
+
+- interactive script tutorial
+
 -------------------------------------------------------------------------------
 -------------------------------------------------------------------------------
 
 
 * STUFF I'M NOT SURE ABOUT
 * STUFF I'M NOT SURE ABOUT
@@ -331,14 +294,9 @@
 
 
 -------------------------------------------------------------------------------
 -------------------------------------------------------------------------------
 
 
-* NEW STUFF
+* STUFF THAT WON'T BE IMPLEMENTED
 
 
-- xterm mouse
-- path improvements
-- remote session
-- map sharing
-- cursor extension for vim
-- interactive script tutorial
+- Lua or any other scripting language, focus is on developing tintin scripting.
 
 
 -------------------------------------------------------------------------------
 -------------------------------------------------------------------------------
 
 

+ 12 - 3
mods/igr.mods

@@ -1,3 +1,15 @@
+Oct 2020        2.02.05
+------------------------------------------------------------------------------
+
+variables.c     Added the #unlocal command.
+
+files.c         Table variables are now written to file with indentation.
+
+utf8.c          Decreased the memory footprint of BIG-5 / GBK-1 support.
+
+variable.c      The VARIABLE UPDATE event now reports the path in the %2
+                argument.
+
 May 2020        2.02.04
 May 2020        2.02.04
 ------------------------------------------------------------------------------
 ------------------------------------------------------------------------------
 
 
@@ -151,9 +163,6 @@ draw.c          Added the SCALED drawing option. When used the size of the
                 square is increased depending on the size of the inputted
                 square is increased depending on the size of the inputted
                 text.
                 text.
 
 
-documentation   Added docs/link.txt file with the initial documentation for
-                link handling.
-
 buffer.c        #buffer find now places the found keyword at the top instead
 buffer.c        #buffer find now places the found keyword at the top instead
                 of at the bottom of the page.
                 of at the bottom of the page.
 
 

+ 1 - 1
src/buffer.c

@@ -355,7 +355,7 @@ void buffer_print(struct session *ses, int index, int start, int end)
 	{
 	{
 		if (HAS_BIT(ses->flags, SES_FLAG_PRINTBUFFER) || ses->scroll->line == ses->scroll->used - 1)
 		if (HAS_BIT(ses->flags, SES_FLAG_PRINTBUFFER) || ses->scroll->line == ses->scroll->used - 1)
 		{
 		{
-			word_wrap_split(ses, ses->scroll->input, temp, ses->wrap, 0, 1, WRAP_FLAG_NONE, &height, &width);
+			word_wrap_split(ses, ses->scroll->input, temp, ses->wrap, 0, 1, WRAP_FLAG_SPLIT, &height, &width);
 		}
 		}
 		else
 		else
 		{
 		{

+ 39 - 176
src/chat.c

@@ -70,9 +70,11 @@ extern struct chat_data *find_group(char *arg);
 
 
 DO_COMMAND(do_chat)
 DO_COMMAND(do_chat)
 {
 {
-	char cmd[BUFFER_SIZE];
+	char *cmd;
 	int cnt;
 	int cnt;
 
 
+	cmd = str_alloc_stack(0);
+
 	arg = get_arg_in_braces(ses, arg, cmd, GET_ONE);
 	arg = get_arg_in_braces(ses, arg, cmd, GET_ONE);
 
 
 	if (*cmd == 0)
 	if (*cmd == 0)
@@ -262,12 +264,12 @@ int chat_new(int s)
 	return 0;
 	return 0;
 }
 }
 
 
-// getaddrinfo should be universally supported anno 2019, if not, let me know.
+// getaddrinfo should be universally supported anno 2020
 
 
 void *threaded_chat_call(void *arg)
 void *threaded_chat_call(void *arg)
 {
 {
 	int sock, error;
 	int sock, error;
-	char host[BUFFER_SIZE], port[BUFFER_SIZE], name[BUFFER_SIZE];
+	char host[NAME_SIZE], port[NAME_SIZE], name[NAME_SIZE];
 	struct addrinfo *address;
 	struct addrinfo *address;
 	static struct addrinfo hints;
 	static struct addrinfo hints;
 	struct chat_data *new_buddy;
 	struct chat_data *new_buddy;
@@ -437,165 +439,6 @@ void *threaded_chat_call(void *arg)
 	return NULL;
 	return NULL;
 }
 }
 
 
-/*
-void *threaded_chat_call(void *arg)
-{
-	int sock, dig;
-	char host[BUFFER_SIZE], port[BUFFER_SIZE], name[BUFFER_SIZE];
-	struct sockaddr_in dest_addr;
-	struct chat_data *new_buddy;
-	struct timeval to;
-	fd_set wds, rds;
-
-	chat_printf("Attempting to call %s ...", arg);
-
-	to.tv_sec = CALL_TIMEOUT;
-	to.tv_usec = 0;
-
-	arg = (void *) get_arg_in_braces(gtd->ses, (char *) arg, host, GET_ONE);
-	arg = (void *) get_arg_in_braces(gtd->ses, (char *) arg, port, GET_ONE);
-
-	if (*port == 0)
-	{
-		sprintf(port, "%d", DEFAULT_PORT);
-	}
-
-	if (sscanf(host, "%d.%d.%d.%d", &dig, &dig, &dig, &dig) == 4)
-	{
-		dest_addr.sin_addr.s_addr = inet_addr(host);
-	}
-	else
-	{
-		struct hostent *hp;
-		int addr, address[4];
-
-		if ((hp = gethostbyname(host)) == NULL)
-		{
-			chat_printf("Failed to call %s, unknown host.", host);
-
-			return NULL;
-		}
-		memcpy((char *)&dest_addr.sin_addr, hp->h_addr, sizeof(dest_addr.sin_addr));
-
-		addr = ntohl(dest_addr.sin_addr.s_addr);
-
-		address[0] = ( addr >> 24 ) & 0xFF ; 
-		address[1] = ( addr >> 16 ) & 0xFF ;
-		address[2] = ( addr >>  8 ) & 0xFF ;
-		address[3] = ( addr       ) & 0xFF ;
-
-		sprintf(host, "%d.%d.%d.%d", address[0], address[1], address[2], address[3]);
-	}
-
-	if (is_number(port))
-	{
-		dest_addr.sin_port = htons(atoi(port));
-	}
-	else
-	{
-		chat_printf("The port should be a number.");
-
-		return NULL;
-	}
-
-	if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0)
-	{
-		syserr_printf(gtd->ses, "old_threaded_chat_call: socket");
-
-		return NULL;
-	}
-
-	dest_addr.sin_family = AF_INET;
-
-	if (connect(sock, (struct sockaddr *)&dest_addr, sizeof(dest_addr)) != 0)
-	{
-		chat_printf("Failed to connect to %s:%s", host, port);
-
-		close(sock);
-
-		return NULL;
-	}
-
-	FD_ZERO(&wds);
-
-	FD_SET(sock, &wds);
-
-	if (select(FD_SETSIZE, NULL, &wds, NULL, &to) == -1)
-	{
-		chat_printf("Failed to connect to %s %s", host, port);
-
-		close(sock);
-
-		return NULL;
-	}
-
-	if (!FD_ISSET(sock, &wds))
-	{
-		chat_printf("Connection timed out.");
-
-		close(sock);
-
-		return NULL;
-	}
-
-	new_buddy = (struct chat_data *) calloc(1, sizeof(struct chat_data));
-
-	new_buddy->fd       = sock;
-	new_buddy->port     = atoi(port);
-
-	new_buddy->download = strdup("");
-	new_buddy->group    = strdup("");
-	new_buddy->ip       = strdup(host);
-	new_buddy->name     = strdup("");
-	new_buddy->version  = strdup("");
-
-	strip_vt102_codes(gtd->chat->name, name);
-
-	chat_socket_printf(new_buddy, "CHAT:%s\n%s%-5u", name, gtd->chat->ip, gtd->chat->port);
-
-	chat_printf("Socket connected, negotiating protocol...");
-
-	FD_ZERO(&rds);
-	FD_SET(sock, &rds);
-
-	to.tv_sec  = CALL_TIMEOUT;
-	to.tv_usec = 0;
-
-	if (select(FD_SETSIZE, &rds, NULL, NULL, &to) == -1)
-	{
-		close_chat(new_buddy, FALSE);
-
-		return NULL;
-	}
-
-	if (process_chat_input(new_buddy) == -1)
-	{
-		FD_CLR(new_buddy->fd, &rds);
-		close_chat(new_buddy, FALSE);
-
-		return NULL;
-	}
-
-	if (gtd->chat == NULL || *new_buddy->name == 0)
-	{
-		close_chat(new_buddy, FALSE);
-	}
-	else
-	{
-		if (fcntl(sock, F_SETFL, O_NDELAY|O_NONBLOCK) == -1)
-		{
-			syserr_printf(gtd->ses, "chat_new: fcntl O_NDELAY|O_NONBLOCK");
-		}
-
-		LINK(new_buddy, gtd->chat->next, gtd->chat->prev);
-		chat_printf("Connection made to %s.", new_buddy->name);
-	}
-
-	return NULL;
-}
-
-*/
-
 #ifdef HAVE_LIBPTHREAD
 #ifdef HAVE_LIBPTHREAD
 
 
 DO_CHAT(chat_call)
 DO_CHAT(chat_call)
@@ -624,8 +467,14 @@ DO_CHAT(chat_call)
 
 
 DO_CHAT(chat_call)
 DO_CHAT(chat_call)
 {
 {
-	char buf[BUFFER_SIZE];
+	char buf[NAME_SIZE];
+
+	if (strlen(arg1) + strlen(arg2) + 5 >= 200)
+	{
+		chat_printf("The call arguments {%s} and {%s} exceed the maximum length of 200 characters.", arg1, arg2);
 
 
+		return;
+	}
 	sprintf(buf, "{%s} {%s}", arg1, arg2);
 	sprintf(buf, "{%s} {%s}", arg1, arg2);
 
 
 	threaded_chat_call((void *) buf);
 	threaded_chat_call((void *) buf);
@@ -711,22 +560,26 @@ void process_chat_connections(fd_set *read_set, fd_set *write_set, fd_set *exc_s
 
 
 void chat_socket_printf(struct chat_data *buddy, char *format, ...)
 void chat_socket_printf(struct chat_data *buddy, char *format, ...)
 {
 {
-	char buf[BUFFER_SIZE];
+	char *buf;
+	int len;
 	va_list args;
 	va_list args;
 
 
 	va_start(args, format);
 	va_start(args, format);
-	vsnprintf(buf, BUFFER_SIZE / 3, format, args);
+
+	len = vasprintf(&buf, format, args);
+
 	va_end(args);
 	va_end(args);
 
 
 	if (!HAS_BIT(buddy->flags, CHAT_FLAG_LINKLOST))
 	if (!HAS_BIT(buddy->flags, CHAT_FLAG_LINKLOST))
 	{
 	{
-		if (write(buddy->fd, buf, strlen(buf)) < 0)
+		if (write(buddy->fd, buf, len) < 0)
 		{
 		{
 			chat_printf("%s went link lost.", buddy->name);
 			chat_printf("%s went link lost.", buddy->name);
 
 
 			SET_BIT(buddy->flags, CHAT_FLAG_LINKLOST);
 			SET_BIT(buddy->flags, CHAT_FLAG_LINKLOST);
 		}
 		}
 	}
 	}
+	free(buf);
 }
 }
 
 
 void chat_printf(char *format, ...)
 void chat_printf(char *format, ...)
@@ -782,12 +635,13 @@ void chat_printf(char *format, ...)
 int process_chat_input(struct chat_data *buddy)
 int process_chat_input(struct chat_data *buddy)
 {
 {
 	struct chat_data *node;
 	struct chat_data *node;
-
-	char buf[BUFFER_SIZE], name[BUFFER_SIZE], temp[BUFFER_SIZE], ip[BUFFER_SIZE], *sep;
+	char *buf, *name, *temp, *ip, *sep;
 	int size;
 	int size;
 
 
 	push_call("process_chat_input(%p)",buddy);
 	push_call("process_chat_input(%p)",buddy);
 
 
+	buf = str_alloc_stack(0);
+
 	size = read(buddy->fd, buf, BUFFER_SIZE / 3);
 	size = read(buddy->fd, buf, BUFFER_SIZE / 3);
 
 
 	if (size <= 0)
 	if (size <= 0)
@@ -796,6 +650,10 @@ int process_chat_input(struct chat_data *buddy)
 		return -1;
 		return -1;
 	}
 	}
 
 
+	name = str_alloc_stack(0);
+	temp = str_alloc_stack(0);
+	ip   = str_alloc_stack(0);
+
 	buf[size] = 0;
 	buf[size] = 0;
 
 
 	if (!strncmp(buf, "CHAT:", 5))
 	if (!strncmp(buf, "CHAT:", 5))
@@ -915,12 +773,14 @@ int process_chat_input(struct chat_data *buddy)
 
 
 void get_chat_commands(struct chat_data *buddy, char *buf, int len)
 void get_chat_commands(struct chat_data *buddy, char *buf, int len)
 {
 {
-	char txt[BUFFER_SIZE];
+	char *txt;
 	unsigned char *pto, *pti, ptc;
 	unsigned char *pto, *pti, ptc;
 	int size;
 	int size;
 
 
 	push_call("get_chat_commands(%s,%d,%s)",buddy->name,len,buf);
 	push_call("get_chat_commands(%s,%d,%s)",buddy->name,len,buf);
 
 
+	txt = str_alloc_stack(0);
+
 	pti = (unsigned char *) buf;
 	pti = (unsigned char *) buf;
 	pto = (unsigned char *) txt;
 	pto = (unsigned char *) txt;
 
 
@@ -1094,14 +954,12 @@ void get_chat_commands(struct chat_data *buddy, char *buf, int len)
 
 
 void chat_name_change(struct chat_data *buddy, char *txt)
 void chat_name_change(struct chat_data *buddy, char *txt)
 {
 {
-	char temp[BUFFER_SIZE], name[BUFFER_SIZE];
+	char name[BUFFER_SIZE];
 	struct chat_data *node;
 	struct chat_data *node;
 
 
-	strip_vt102_codes(txt, name);
-
 	if (strlen(name) > 20)
 	if (strlen(name) > 20)
 	{
 	{
-		chat_socket_printf(buddy, "%c\n%s has refused your name change because your name is too long.\n%c", CHAT_MESSAGE, gtd->chat->name, name, CHAT_END_OF_COMMAND);
+		chat_socket_printf(buddy, "%c\n%s has refused your name change because your name is too long.\n%c", CHAT_MESSAGE, gtd->chat->name, CHAT_END_OF_COMMAND);
 
 
 		chat_printf("Refusing connection from %.21s:%d, name too long. (%d characters)", buddy->ip, buddy->port, strlen(name));
 		chat_printf("Refusing connection from %.21s:%d, name too long. (%d characters)", buddy->ip, buddy->port, strlen(name));
 
 
@@ -1137,11 +995,9 @@ void chat_name_change(struct chat_data *buddy, char *txt)
 
 
 	if (strcmp(name, buddy->name))
 	if (strcmp(name, buddy->name))
 	{
 	{
-		strcpy(temp, buddy->name);
+		chat_printf("%s changed their name to %s.", buddy->name, name);
 
 
 		RESTRING(buddy->name, name);
 		RESTRING(buddy->name, name);
-
-		chat_printf("%s is now %s.", temp, txt);
 	}
 	}
 }
 }
 
 
@@ -1535,6 +1391,13 @@ DO_CHAT(chat_name)
 		return;
 		return;
 	}
 	}
 
 
+	if (strlen(arg1) > 200)
+	{
+		chat_printf("Your name cannot be longer than 200 bytes.");
+
+		return;
+	}
+
 	RESTRING(gtd->chat->name, arg1);
 	RESTRING(gtd->chat->name, arg1);
 
 
 	for (buddy = gtd->chat->next ; buddy ; buddy = buddy->next)
 	for (buddy = gtd->chat->next ; buddy ; buddy = buddy->next)

+ 39 - 0
src/class.c

@@ -26,6 +26,45 @@
 
 
 #include "tintin.h"
 #include "tintin.h"
 
 
+#define DO_CLASS(class) struct session *class(struct session *ses, struct listnode *node, char *arg1, char *arg2)
+
+extern DO_CLASS(class_assign);
+extern DO_CLASS(class_clear);
+extern DO_CLASS(class_close);
+extern DO_CLASS(class_kill);
+extern DO_CLASS(class_list);
+extern DO_CLASS(class_load);
+extern DO_CLASS(class_open);
+extern DO_CLASS(class_read);
+extern DO_CLASS(class_save);
+extern DO_CLASS(class_size);
+extern DO_CLASS(class_write);
+
+typedef struct session *CLASS(struct session *ses, struct listnode *node, char *arg1, char *arg2);
+
+struct class_type
+{
+	char                  * name;
+	CLASS                 * fun;
+};
+
+struct class_type class_table[] =
+{
+	{    "ASSIGN",            class_assign           },
+	{    "CLEAR",             class_clear            },
+	{    "CLOSE",             class_close            },
+	{    "KILL",              class_kill             },
+	{    "LIST",              class_list             },
+	{    "LOAD",              class_load             },
+	{    "OPEN",              class_open             },
+	{    "READ",              class_read             },
+	{    "SAVE",              class_save             },
+	{    "SIZE",              class_size             },
+	{    "WRITE",             class_write            },
+	{    "",                  NULL                   },
+};
+
+int count_class(struct session *ses, struct listnode *group);
 
 
 DO_COMMAND(do_class)
 DO_COMMAND(do_class)
 {
 {

+ 60 - 1
src/command.c

@@ -25,7 +25,7 @@
 
 
 #include "tintin.h"
 #include "tintin.h"
 
 
-extern struct command_type command_table[];
+struct command_type command_table[];
 
 
 DO_COMMAND(do_commands)
 DO_COMMAND(do_commands)
 {
 {
@@ -159,6 +159,64 @@ struct session *command(struct session *ses, COMMAND *cmd, char *format, ...)
 	return ses;
 	return ses;
 }
 }
 
 
+extern DO_COMMAND(do_action);
+extern DO_COMMAND(do_alias);
+extern DO_COMMAND(do_all);
+extern DO_COMMAND(do_bell);
+extern DO_COMMAND(do_button);
+extern DO_COMMAND(do_cat);
+extern DO_COMMAND(do_class);
+extern DO_COMMAND(do_commands);
+extern DO_COMMAND(do_cr);
+extern DO_COMMAND(do_debug);
+extern DO_COMMAND(do_echo);
+extern DO_COMMAND(do_event);
+extern DO_COMMAND(do_format);
+extern DO_COMMAND(do_function);
+extern DO_COMMAND(do_gag);
+extern DO_COMMAND(do_highlight);
+extern DO_COMMAND(do_ignore);
+extern DO_COMMAND(do_info);
+extern DO_COMMAND(do_killall);
+extern DO_COMMAND(do_log);
+extern DO_COMMAND(do_local);
+extern DO_COMMAND(do_list);
+extern DO_COMMAND(do_macro);
+extern DO_COMMAND(do_math);
+extern DO_COMMAND(do_message);
+extern DO_COMMAND(do_path);
+extern DO_COMMAND(do_port);
+extern DO_COMMAND(do_prompt);
+extern DO_COMMAND(do_replace);
+extern DO_COMMAND(do_run);
+extern DO_COMMAND(do_scan);
+extern DO_COMMAND(do_script);
+extern DO_COMMAND(do_send);
+extern DO_COMMAND(do_showme);
+extern DO_COMMAND(do_ssl);
+extern DO_COMMAND(do_substitute);
+extern DO_COMMAND(do_system);
+extern DO_COMMAND(do_tab);
+extern DO_COMMAND(do_textin);
+extern DO_COMMAND(do_tick);
+extern DO_COMMAND(do_unaction);
+extern DO_COMMAND(do_unalias);
+extern DO_COMMAND(do_unbutton);
+extern DO_COMMAND(do_undelay);
+extern DO_COMMAND(do_unevent);
+extern DO_COMMAND(do_unfunction);
+extern DO_COMMAND(do_ungag);
+extern DO_COMMAND(do_unhighlight);
+extern DO_COMMAND(do_unlocal);
+extern DO_COMMAND(do_unmacro);
+extern DO_COMMAND(do_unpathdir);
+extern DO_COMMAND(do_unprompt);
+extern DO_COMMAND(do_unsubstitute);
+extern DO_COMMAND(do_untab);
+extern DO_COMMAND(do_untick);
+extern DO_COMMAND(do_unvariable);
+extern DO_COMMAND(do_variable);
+
 struct command_type command_table[] =
 struct command_type command_table[] =
 {
 {
 	{    "action",            do_action,            3, TOKEN_TYPE_COMMAND },
 	{    "action",            do_action,            3, TOKEN_TYPE_COMMAND },
@@ -247,6 +305,7 @@ struct command_type command_table[] =
 	{    "unfunction",        do_unfunction,        0, TOKEN_TYPE_COMMAND },
 	{    "unfunction",        do_unfunction,        0, TOKEN_TYPE_COMMAND },
 	{    "ungag",             do_ungag,             0, TOKEN_TYPE_COMMAND },
 	{    "ungag",             do_ungag,             0, TOKEN_TYPE_COMMAND },
 	{    "unhighlight",       do_unhighlight,       0, TOKEN_TYPE_COMMAND },
 	{    "unhighlight",       do_unhighlight,       0, TOKEN_TYPE_COMMAND },
+	{    "unlocal",           do_unlocal,           1, TOKEN_TYPE_COMMAND },
 	{    "unmacro",           do_unmacro,           0, TOKEN_TYPE_COMMAND },
 	{    "unmacro",           do_unmacro,           0, TOKEN_TYPE_COMMAND },
 	{    "unpathdir",         do_unpathdir,         1, TOKEN_TYPE_COMMAND },
 	{    "unpathdir",         do_unpathdir,         1, TOKEN_TYPE_COMMAND },
 	{    "unprompt",          do_unprompt,          0, TOKEN_TYPE_COMMAND },
 	{    "unprompt",          do_unprompt,          0, TOKEN_TYPE_COMMAND },

+ 97 - 0
src/draw.c

@@ -28,6 +28,101 @@ static int  draw_cnt;
 
 
 #include "tintin.h"
 #include "tintin.h"
 
 
+#define DRAW_FLAG_NONE                   0
+#define DRAW_FLAG_ASCII               BV01
+#define DRAW_FLAG_BLANKED             BV02
+#define DRAW_FLAG_BOT                 BV03
+#define DRAW_FLAG_BOXED               BV04
+#define DRAW_FLAG_BUMP                BV05
+#define DRAW_FLAG_CIRCLED             BV06
+#define DRAW_FLAG_COLOR1              BV07
+#define DRAW_FLAG_COLOR2              BV08
+#define DRAW_FLAG_CONVERT             BV09
+#define DRAW_FLAG_CORNERED            BV10
+#define DRAW_FLAG_CROSSED             BV11
+#define DRAW_FLAG_FILLED              BV12
+#define DRAW_FLAG_FOREGROUND          BV13
+#define DRAW_FLAG_GRID                BV14
+#define DRAW_FLAG_HOR                 BV15
+#define DRAW_FLAG_HUGE                BV16
+#define DRAW_FLAG_JEWELED             BV17
+#define DRAW_FLAG_LEFT                BV18
+//#define DRAW_FLAG_LINED               BV19 unused / obsolete
+#define DRAW_FLAG_NUMBERED            BV20
+#define DRAW_FLAG_PRUNED              BV21
+#define DRAW_FLAG_RIGHT               BV22
+#define DRAW_FLAG_ROUNDED             BV23
+#define DRAW_FLAG_SCALED              BV24
+#define DRAW_FLAG_SCROLL              BV25
+#define DRAW_FLAG_SHADOWED            BV26
+#define DRAW_FLAG_TEED                BV27
+#define DRAW_FLAG_TOP                 BV28
+#define DRAW_FLAG_TRACED              BV29
+#define DRAW_FLAG_TUBED               BV30
+#define DRAW_FLAG_UTF8                BV31
+#define DRAW_FLAG_VER                 BV32
+
+#define DRAW_FLAG_CURSIVE             BV33
+#define DRAW_FLAG_FAT                 BV34
+#define DRAW_FLAG_SANSSERIF           BV35
+#define DRAW_FLAG_CALIGN              BV36
+#define DRAW_FLAG_LALIGN              BV37
+#define DRAW_FLAG_RALIGN              BV38
+#define DRAW_FLAG_TALIGN              BV39
+#define DRAW_FLAG_UALIGN              BV40
+
+#define DRAW_FLAG_APPENDIX            DRAW_FLAG_CIRCLED|DRAW_FLAG_CORNERED|DRAW_FLAG_CROSSED|DRAW_FLAG_JEWELED|DRAW_FLAG_PRUNED|DRAW_FLAG_ROUNDED|DRAW_FLAG_TEED
+
+
+
+#define DO_DRAW(draw) void draw (struct session *ses, int top_row, int top_col, int bot_row, int bot_col, int rows, int cols, long long flags, char *color, char *arg, char *arg1, char *arg2, char *arg3)
+
+extern DO_DRAW(draw_blank);
+extern DO_DRAW(draw_bot_side);
+//extern DO_DRAW(draw_arg);
+extern DO_DRAW(draw_box);
+extern DO_DRAW(draw_buffer);
+extern DO_DRAW(draw_corner);
+extern DO_DRAW(draw_horizontal_line);
+extern DO_DRAW(draw_left_side);
+extern DO_DRAW(draw_line);
+extern DO_DRAW(draw_map);
+extern DO_DRAW(draw_right_side);
+extern DO_DRAW(draw_side);
+extern DO_DRAW(draw_square);
+extern DO_DRAW(draw_rain);
+extern DO_DRAW(draw_table_grid);
+extern DO_DRAW(draw_text);
+extern DO_DRAW(draw_top_side);
+extern DO_DRAW(draw_vertical_lines);
+
+typedef void DRAW(struct session *ses, int top_row, int top_col, int bot_row, int bot_col, int rows, int cols, long long flags, char *color, char *arg, char *arg1, char *arg2, char *arg3);
+
+struct draw_type
+{
+	char                  * name;
+	char                  * desc;
+	int                     flags;
+	DRAW                  * fun;
+};
+
+struct draw_type draw_table[] =
+{
+	{       "BOX",       "Draw four sides of a box.",         DRAW_FLAG_BOXED|DRAW_FLAG_LEFT|DRAW_FLAG_RIGHT|DRAW_FLAG_TOP|DRAW_FLAG_BOT, draw_box },
+	{       "BUFFER",    "Draw the scrollback buffer.",       DRAW_FLAG_NONE, draw_buffer },
+	{       "CORNER",    "Draw a corner",                     DRAW_FLAG_CORNERED, draw_corner },
+	{       "LINE",      "Draw a line.",                      DRAW_FLAG_NONE, draw_line },
+	{       "MAP",       "Draw the map.",                     DRAW_FLAG_NONE, draw_map },
+	{       "RAIN",      "Draw digital rain.",                DRAW_FLAG_NONE, draw_rain },
+	{       "SIDE",      "Draw a line with corners.",         DRAW_FLAG_BOXED, draw_side },
+	{       "TABLE",     "Draw a table.",                     DRAW_FLAG_BOXED|DRAW_FLAG_LEFT|DRAW_FLAG_RIGHT|DRAW_FLAG_TOP|DRAW_FLAG_BOT, draw_table_grid },
+	{       "TILE",      "Draw a tile.",                      DRAW_FLAG_NONE, draw_square },
+	{       "",          "",                                  DRAW_FLAG_NONE, NULL }
+};
+
+
+void scale_drawing(struct session *ses, int *top_row, int *top_col, int *bot_row, int *bot_col, int *rows, int *cols, int index, long long flags, char *arg);
+
 DO_COMMAND(do_draw)
 DO_COMMAND(do_draw)
 {
 {
 	char *color, *code1, *code2, *input;
 	char *color, *code1, *code2, *input;
@@ -1292,6 +1387,7 @@ DO_DRAW(draw_bot_side)
 	}
 	}
 }
 }
 
 
+/*
 DO_DRAW(draw_arg)
 DO_DRAW(draw_arg)
 {
 {
 	arg = get_arg_in_braces(ses, arg, arg1, GET_ONE);
 	arg = get_arg_in_braces(ses, arg, arg1, GET_ONE);
@@ -1315,6 +1411,7 @@ DO_DRAW(draw_arg)
 
 
 	restore_pos(ses);
 	restore_pos(ses);
 }
 }
+*/
 
 
 DO_DRAW(draw_box)
 DO_DRAW(draw_box)
 {
 {

+ 14 - 9
src/files.c

@@ -499,8 +499,6 @@ void write_node(struct session *ses, int list, struct listnode *node, FILE *file
 {
 {
 	char *result, *str;
 	char *result, *str;
 	int val = 0;
 	int val = 0;
-	int llen = UMAX(20, strlen(node->arg1));
-	int rlen = UMAX(25, strlen(node->arg2));
 
 
 	push_call("write_node(%d,%p,%p)",list,node,file);
 	push_call("write_node(%d,%p,%p)",list,node,file);
 
 
@@ -528,10 +526,17 @@ void write_node(struct session *ses, int list, struct listnode *node, FILE *file
 		case LIST_VARIABLE:
 		case LIST_VARIABLE:
 			str = str_alloc_stack(0);
 			str = str_alloc_stack(0);
 
 
-			show_nest_node(node, &str, 1);
-
-			val = asprintf(&result, "%c%-16s {%s} %*s {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, 20 - llen, "", str);
+//			show_nest_node(node, &str, 1);
+			view_nest_node(node, &str, 0, TRUE, FALSE);
 
 
+			if (node->root)
+			{
+				val = asprintf(&result, "%c%s {%s}\n{\n%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, str);
+			}
+			else
+			{
+				val = asprintf(&result, "%c%s {%s} {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, str);
+			}
 			break;
 			break;
 
 
 		default:
 		default:
@@ -541,16 +546,16 @@ void write_node(struct session *ses, int list, struct listnode *node, FILE *file
 					result = strdup("");
 					result = strdup("");
 					break;
 					break;
 				case 1:
 				case 1:
-					val = asprintf(&result, "%c%-16s {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1);
+					val = asprintf(&result, "%c%s {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1);
 					break;
 					break;
 				case 2:
 				case 2:
-					val = asprintf(&result, "%c%-16s {%s} %*s {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, 20 - llen, "", node->arg2);
+					val = asprintf(&result, "%c%s {%s} {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, node->arg2);
 					break;
 					break;
 				case 3:
 				case 3:
-					val = asprintf(&result, "%c%-16s {%s} %*s {%s} %*s {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, 20 - llen, "", node->arg2, 25 - rlen, "", node->arg3);
+					val = asprintf(&result, "%c%s {%s} {%s} {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, node->arg2, node->arg3);
 					break;
 					break;
 				case 4:
 				case 4:
-					val = asprintf(&result, "%c%-16s {%s} %*s {%s} %*s {%s} {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, 20 - llen, "", node->arg2, 25 - rlen, "", node->arg3, node->arg4);
+					val = asprintf(&result, "%c%s {%s} {%s} {%s} {%s}\n", gtd->tintin_char, list_table[list].name, node->arg1, node->arg2, node->arg3, node->arg4);
 					break;
 					break;
 			}
 			}
 			break;
 			break;

+ 19 - 44
src/gui.h

@@ -1,4 +1,4 @@
-char *tt_gui = "#line QUIET #port INIT gui 0\n"
+char *tt_gui = "#line quiet #port init gui 0\n"
 "\n"
 "\n"
 "#function gui_link\n"
 "#function gui_link\n"
 "{\n"
 "{\n"
@@ -16,30 +16,6 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "	#return $gui[link]\n"
 "	#return $gui[link]\n"
 "}\n"
 "}\n"
 "\n"
 "\n"
-"/*\n"
-"#function input_link\n"
-"{\n"
-"	#line sub esc\n"
-"	{\n"
-"		#var result\n"
-"		{\n"
-"			\e]68;2;INPUT;{{top_row}{%1}{top_col}{%2}{bot_row}{%3}{bot_col}{%4}{name}{%5}{data}{%6}}\a\e[4;24m%7\e[24m\n"
-"		}\n"
-"	}\n"
-"}\n"
-"\n"
-"#event {PRESSED SECURE LINK INPUT MOUSE BUTTON ONE}\n"
-"{\n"
-"	#local link %4;\n"
-"\n"
-"	#screen inputregion {$link[top_row]} {$link[bot_row]} {$link[bot_row]} {$link[bot_col]} {$link[name]};\n"
-"\n"
-"	#cursor clear;\n"
-"\n"
-"	#cursor set {$link[data]}\n"
-"}\n"
-"*/\n"
-"\n"
 "#event {PRESSED SECURE LINK COMMAND MOUSE BUTTON ONE} {%4}\n"
 "#event {PRESSED SECURE LINK COMMAND MOUSE BUTTON ONE} {%4}\n"
 "\n"
 "\n"
 "#event {PRESSED SECURE LINK COMMAND MOUSE BUTTON THREE}\n"
 "#event {PRESSED SECURE LINK COMMAND MOUSE BUTTON THREE}\n"
@@ -79,13 +55,13 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "\n"
 "\n"
 "	#if {{$gui[world_tab]} == {worlds}}\n"
 "	#if {{$gui[world_tab]} == {worlds}}\n"
 "	{\n"
 "	{\n"
-"		#draw jade Azure  rounded calign box 1  1 3 13 {@gui_link{COMMAND;{profile_tab_cancel;world_tab worlds;draw_worlds 0};worlds}};\n"
-"		#draw jade Silver rounded calign box 1 14 3 26 {@gui_link{COMMAND;{profile_tab_cancel;world_tab sponsors;draw_sponsors 0};sponsors}}\n"
+"		#draw jade Yellow rounded calign box 1  1 3 13 {@gui_link{COMMAND;{profile_tab_cancel;world_tab worlds;draw_worlds 0};worlds}};\n"
+"		#draw jade Azure  rounded calign box 1 14 3 26 {@gui_link{COMMAND;{profile_tab_cancel;world_tab sponsors;draw_sponsors 0};sponsors}}\n"
 "	};\n"
 "	};\n"
 "	#else\n"
 "	#else\n"
 "	{\n"
 "	{\n"
-"		#draw jade Silver rounded calign box 1  1 3 13 {@gui_link{COMMAND;{profile_tab_cancel;world_tab worlds;draw_worlds 0};worlds}};\n"
-"		#draw jade Azure  rounded calign box 1 14 3 26 {@gui_link{COMMAND;{profile_tab_cancel;world_tab sponsors;draw_sponsors 0};sponsors}}\n"
+"		#draw jade Azure  rounded calign box 1  1 3 13 {@gui_link{COMMAND;{profile_tab_cancel;world_tab worlds;draw_worlds 0};worlds}};\n"
+"		#draw jade Yellow rounded calign box 1 14 3 26 {@gui_link{COMMAND;{profile_tab_cancel;world_tab sponsors;draw_sponsors 0};sponsors}}\n"
 "	};\n"
 "	};\n"
 "\n"
 "\n"
 "	#draw jade Green rounded calign box -3  1 -1 13 {@gui_link{COMMAND;gui_new;new}};\n"
 "	#draw jade Green rounded calign box -3  1 -1 13 {@gui_link{COMMAND;gui_new;new}};\n"
@@ -586,13 +562,12 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "\n"
 "\n"
 "#alias {gui_reload}\n"
 "#alias {gui_reload}\n"
 "{\n"
 "{\n"
-"	#nop gts #SPLIT 1 3 27 27;\n"
-"	#SPLIT 1 3 27 27;\n"
+"	#split 1 3 27 27;\n"
 "	#screen clear split;\n"
 "	#screen clear split;\n"
 "	#screen inputregion -2 28 -2 -28 profile_tab_INPUT;\n"
 "	#screen inputregion -2 28 -2 -28 profile_tab_INPUT;\n"
 "\n"
 "\n"
-"	#screen get ROWS gui[rows];\n"
-"	#screen get COLS gui[cols];\n"
+"	#screen get rows gui[rows];\n"
+"	#screen get cols gui[cols];\n"
 "\n"
 "\n"
 "	#math gui[cols] $gui[cols] - 54;\n"
 "	#math gui[cols] $gui[cols] - 54;\n"
 "\n"
 "\n"
@@ -617,16 +592,16 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "\n"
 "\n"
 "#alias {gui_init}\n"
 "#alias {gui_init}\n"
 "{\n"
 "{\n"
-"	#config MOUSE ON;\n"
-"	#config SCROLL_LOCK OFF;\n"
+"	#config mouse on;\n"
+"	#config scroll_lock off;\n"
 "\n"
 "\n"
-"	#class WORLDS ASSIGN #VARIABLE {worldlist} {};\n"
+"	#class WORLDS assign #variable {worldlist} {};\n"
 "\n"
 "\n"
-"	#info SYSTEM SAVE;\n"
+"	#info system save;\n"
 "\n"
 "\n"
 "	#banner save;\n"
 "	#banner save;\n"
 "\n"
 "\n"
-"	#line QUIET #read $info[SYSTEM][TINTIN]/worlds.tin;\n"
+"	#line quiet #read $info[SYSTEM][TINTIN]/worlds.tin;\n"
 "\n"
 "\n"
 "	#var gui[pause] 0;\n"
 "	#var gui[pause] 0;\n"
 "	#var gui[profile_tab] 0;\n"
 "	#var gui[profile_tab] 0;\n"
@@ -641,18 +616,18 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "	#if {$gui[cols] > 75}\n"
 "	#if {$gui[cols] > 75}\n"
 "	{\n"
 "	{\n"
 "		#draw Silver huge traced scroll tile 1 1 6 73 { TINTIN++};\n"
 "		#draw Silver huge traced scroll tile 1 1 6 73 { TINTIN++};\n"
-"		#draw Silver calign scroll tile 1 1 2 75 {\n\n$info[SYSTEM][CLIENT_VERSION]};\n"
-"		#draw Silver calign scroll tile 1 1 3 75 {\n\nCode by Peter Unold, Bill Reiss, and Igor van den Hoven\n}\n"
+"		#draw Silver calign scroll tile 1 1 2 75 {}{$info[SYSTEM][CLIENT_VERSION]};\n"
+"		#draw Silver calign scroll tile 1 1 3 75 {}{Code by Peter Unold, Bill Reiss, and Igor van den Hoven}\n"
 "	};\n"
 "	};\n"
 "	#elseif {$gui[cols] > 40}\n"
 "	#elseif {$gui[cols] > 40}\n"
 "	{\n"
 "	{\n"
 "		#draw Silver huge traced scroll tile 1 1 6 40 { TT++};\n"
 "		#draw Silver huge traced scroll tile 1 1 6 40 { TT++};\n"
-"		#draw Silver calign scroll tile 1 1 2 40 {\n\n$info[SYSTEM][CLIENT_VERSION]};\n"
-"		#draw Silver calign scroll tile 1 1 3 40 {\n\nCode by Peter Unold, Bill Reiss,\nand Igor van den Hoven\n}\n"
+"		#draw Silver calign scroll tile 1 1 2 40 {}{$info[SYSTEM][CLIENT_VERSION]};\n"
+"		#draw Silver calign scroll tile 1 1 4 40 {}{Code by Peter Unold, Bill Reiss,}{}{and Igor van den Hoven}\n"
 "	};\n"
 "	};\n"
 "	#elseif {$gui[cols] > 18}\n"
 "	#elseif {$gui[cols] > 18}\n"
 "	{\n"
 "	{\n"
-"		#draw Silver calign scroll tile 1 1 14 $gui[cols] {T I N T I N + +\n\n$info[SYSTEM][CLIENT_VERSION]\n\nCode by\n\nPeter Unold\n\nBill Reiss\n\nand\n\nIgor van den Hoven\n};\n"
+"		#draw Silver calign scroll tile 1 1 14 $gui[cols] {T I N T I N + +}{}{$info[SYSTEM][CLIENT_VERSION]}{}{Code by}{}{Peter Unold}{}{Bill Reiss}{}{and}{}{Igor van den Hoven};\n"
 "	};\n"
 "	};\n"
 "	#elseif {$gui[cols] > 8}\n"
 "	#elseif {$gui[cols] > 8}\n"
 "	{\n"
 "	{\n"
@@ -664,7 +639,7 @@ char *tt_gui = "#line QUIET #port INIT gui 0\n"
 "	};\n"
 "	};\n"
 "	#elseif {$gui[cols] > 1}\n"
 "	#elseif {$gui[cols] > 1}\n"
 "	{\n"
 "	{\n"
-"		#draw Silver calign scroll tile 1 1 8 $gui[cols] {T\ni\nn\nT\ni\nn\n+\n+}\n"
+"		#draw Silver calign scroll tile 1 1 8 $gui[cols] {T}{i}{n}{T}{i}{n}{+}{+}\n"
 "	}\n"
 "	}\n"
 "}\n"
 "}\n"
 "\n"
 "\n"

+ 10 - 6
src/help.c

@@ -622,8 +622,8 @@ struct help_type help_table[] =
 		"\n"
 		"\n"
 		"\\        An input line starting with a backslash is send verbatim if you are\n"
 		"\\        An input line starting with a backslash is send verbatim if you are\n"
 		"         connected to a server. This character can be configured with\n"
 		"         connected to a server. This character can be configured with\n"
-		"         #config, and is itself send verbatim when the verbatim config mode\n",
-		"         is enabled.\n"
+		"         #config, and is itself send verbatim when the verbatim config mode\n"
+		"         is enabled.\n",
 
 
 		"colors escape function mathematics pcre variable"
 		"colors escape function mathematics pcre variable"
 	},
 	},
@@ -1479,8 +1479,8 @@ struct help_type help_table[] =
 		"\n"
 		"\n"
 		"         <128>VARIABLE EVENTS<278>\n"
 		"         <128>VARIABLE EVENTS<278>\n"
 		"\n"
 		"\n"
-		"         VARIABLE UPDATE [VAR]  %0 name %1 new value\n"
-		"         VARIABLE UPDATED [VAR] %0 name %1 new value\n"
+		"         VARIABLE UPDATE <VAR>  %0 name %1 new value %2 path\n"
+		"         VARIABLE UPDATED <VAR> %0 name %1 new value %2 path\n"
 		"\n"
 		"\n"
 		"         <128>VT100 EVENTS<278>\n"
 		"         <128>VT100 EVENTS<278>\n"
 		"\n"
 		"\n"
@@ -2221,7 +2221,7 @@ struct help_type help_table[] =
 		"         #list {var} {delete} {index} {number}  Delete the item at {index},\n"
 		"         #list {var} {delete} {index} {number}  Delete the item at {index},\n"
 		"                                                the {number} is optional.\n"
 		"                                                the {number} is optional.\n"
 		"         #list {var} {explode}                  Turn list into a character list\n"
 		"         #list {var} {explode}                  Turn list into a character list\n"
-		"         #list {var} {index}                    Index a list table for sorting\n"
+		"         #list {var} {indexate}                 Index a list table for sorting\n"
 		"         #list {var} {insert} {index} {string}  Insert {string} at given index\n"
 		"         #list {var} {insert} {index} {string}  Insert {string} at given index\n"
 		"         #list {var} {find} {string} {variable} Return the found index\n"
 		"         #list {var} {find} {string} {variable} Return the found index\n"
 		"         #list {var} {get} {index} {variable}   Copy an item to {variable}\n"
 		"         #list {var} {get} {index} {variable}   Copy an item to {variable}\n"
@@ -2541,7 +2541,9 @@ struct help_type help_table[] =
 		"\n"
 		"\n"
 		"         Avoid setting the result variable as local in a function.\n"
 		"         Avoid setting the result variable as local in a function.\n"
 		"\n"
 		"\n"
-		"<178>Example<278>: #alias {swap} {#local x %0;#replace x {e} {u};#show $x}\n",
+		"<178>Example<278>: #alias {swap} {#local x %0;#replace x {e} {u};#show $x}\n"
+		"\n"
+		"<178>Comment<278>: You can remove a local variable with the #unlocal command.\n",
 
 
 		"format function math replace script variable"
 		"format function math replace script variable"
 	},
 	},
@@ -3909,6 +3911,7 @@ struct help_type help_table[] =
 		"\n"
 		"\n"
 		"         <178>#screen swap\n"
 		"         <178>#screen swap\n"
 		"         <278>  Swap the input and scroll region.\n",
 		"         <278>  Swap the input and scroll region.\n",
+
 		"bell"
 		"bell"
 	},
 	},
 
 
@@ -4449,6 +4452,7 @@ struct help_type help_table[] =
 		"",
 		"",
 		TOKEN_TYPE_COMMAND,
 		TOKEN_TYPE_COMMAND,
 		"",
 		"",
+
 		""
 		""
 	}
 	}
 };
 };

+ 13 - 1
src/input.c

@@ -223,6 +223,14 @@ void read_line(char *input, int len)
 		}
 		}
 	}
 	}
 
 
+	if (HAS_BIT(gtd->ses->charset, CHARSET_FLAG_EUC) && is_euc_head(gtd->ses, gtd->macro_buf))
+	{
+		if (gtd->macro_buf[1] == 0)
+		{
+			return;
+		}
+	}
+
 	if (HAS_BIT(gtd->ses->event_flags, EVENT_FLAG_INPUT))
 	if (HAS_BIT(gtd->ses->event_flags, EVENT_FLAG_INPUT))
 	{
 	{
 		check_all_events(gtd->ses, EVENT_FLAG_INPUT, 0, 2, "RECEIVED KEYPRESS", input, ntos(index));
 		check_all_events(gtd->ses, EVENT_FLAG_INPUT, 0, 2, "RECEIVED KEYPRESS", input, ntos(index));
@@ -272,10 +280,14 @@ void read_line(char *input, int len)
 				break;
 				break;
 
 
 			default:
 			default:
-				if (HAS_BIT(gtd->ses->charset, CHARSET_FLAG_UTF8) && gtd->macro_buf[0] & 128 && gtd->macro_buf[1])
+				if (HAS_BIT(gtd->ses->charset, CHARSET_FLAG_UTF8) && is_utf8_head(gtd->macro_buf) && gtd->macro_buf[1])
 				{
 				{
 					size = get_utf8_width(gtd->macro_buf, &width);
 					size = get_utf8_width(gtd->macro_buf, &width);
 				}
 				}
+				else if (HAS_BIT(gtd->ses->charset, CHARSET_FLAG_EUC) && is_euc_head(gtd->ses, gtd->macro_buf) && gtd->macro_buf[1])
+				{
+					size = get_euc_width(gtd->ses, gtd->macro_buf, &width);
+				}
 				else
 				else
 				{
 				{
 					size = get_ascii_width(gtd->macro_buf, &width);
 					size = get_ascii_width(gtd->macro_buf, &width);

+ 127 - 99
src/list.c

@@ -27,6 +27,62 @@
 
 
 #include "tintin.h"
 #include "tintin.h"
 
 
+#define DO_ARRAY(array) struct session *array (struct session *ses, struct listnode *list, char *arg, char *var, char *arg1, char *arg2)
+
+extern DO_ARRAY(array_add);
+extern DO_ARRAY(array_clear);
+extern DO_ARRAY(array_collapse);
+extern DO_ARRAY(array_create);
+extern DO_ARRAY(array_delete);
+extern DO_ARRAY(array_explode);
+extern DO_ARRAY(array_find);
+extern DO_ARRAY(array_get);
+extern DO_ARRAY(array_index);
+extern DO_ARRAY(array_insert);
+extern DO_ARRAY(array_order);
+extern DO_ARRAY(array_reverse);
+extern DO_ARRAY(array_set);
+extern DO_ARRAY(array_shuffle);
+extern DO_ARRAY(array_simplify);
+extern DO_ARRAY(array_size);
+extern DO_ARRAY(array_sort);
+extern DO_ARRAY(array_tokenize);
+
+typedef struct session *ARRAY(struct session *ses, struct listnode *list, char *arg, char *var, char *arg1, char *arg2);
+
+struct array_type
+{
+	char                  * name;
+	ARRAY                 * fun;
+	char                  * desc;
+};
+
+struct array_type array_table[] =
+{
+	{     "ADD",              array_add,         "Add an item to a list table"             },
+	{     "CLEAR",            array_clear,       "Clear a list"                            },
+	{     "CLR",              array_clear,       NULL                                      },
+	{     "COLLAPSE",         array_collapse,    "Collapse the list into a variable"       },
+	{     "CREATE",           array_create,      "Create a list table with given items"    },
+	{     "DELETE",           array_delete,      "Delete a list item with given index"     },
+	{     "EXPLODE",          array_explode,     "Explode the variable into a list"        },
+	{     "FIND",             array_find,        "Find a list item with given regex"       },
+	{     "FND",              array_find,        NULL                                      },
+	{     "GET",              array_get,         "Retrieve a list item with given index"   },
+	{     "INDEXATE",         array_index,       "Indexate a list table for sorting"       },
+	{     "INSERT",           array_insert,      "Insert a list item at given index"       },
+	{     "ORDER",            array_order,       "Sort a list table numerically"           },
+	{     "LENGTH",           array_size,        NULL                                      },
+	{     "REVERSE",          array_reverse,     "Sort a list table in reverse order"      },
+	{     "SET",              array_set,         "Change a list item at given index"       },
+	{     "SHUFFLE",          array_shuffle,     "Sort a list table in random order"       },
+	{     "SIMPLIFY",         array_simplify,    "Turn a list table into a simple list"    },
+	{     "SIZE",             array_size,        NULL                                      },
+	{     "SORT",             array_sort,        "Sort a list table alphabetically"        },
+	{     "SRT",              array_sort,        NULL                                      },
+	{     "TOKENIZE",         array_tokenize,    "Create a list with given characters"     },
+	{     "",                 NULL,              ""                                        }
+};
 
 
 DO_COMMAND(do_list)
 DO_COMMAND(do_list)
 {
 {
@@ -88,6 +144,32 @@ DO_COMMAND(do_list)
 	return ses;
 	return ses;
 }
 }
 
 
+int get_list_index(struct session *ses, struct listroot *root, char *arg)
+{
+	int toi;
+
+	toi = get_number(ses, arg);
+
+	if (toi > 0)
+	{
+		if (toi <= root->used)
+		{
+			return toi - 1;
+		}
+		return -1;
+	}
+
+	if (toi < 0)
+	{
+		if (root->used + toi >= 0)
+		{
+			return root->used + toi;
+		}
+		return -1;
+	}
+	return -1;
+}
+
 DO_ARRAY(array_add)
 DO_ARRAY(array_add)
 {
 {
 	char *str;
 	char *str;
@@ -212,24 +294,31 @@ DO_ARRAY(array_delete)
 		arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 		arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 		arg = get_arg_in_braces(ses, arg, arg2, GET_ALL);
 		arg = get_arg_in_braces(ses, arg, arg2, GET_ALL);
 
 
-		loop = *arg2 ? (int) get_number(ses, arg2) : 1;
+		index = get_list_index(ses, list->root, arg1);
 
 
-		while (loop--)
+		if (*arg2)
+		{
+			loop = URANGE(1, (int) get_number(ses, arg2), list->root->used - index);
+		}
+		else
 		{
 		{
-			index = search_nest_index(list->root, arg1);
+			loop = 1;
+		}
 
 
-			if (atoi(arg1) == 0 || index == -1)
-			{
-				show_error(ses, LIST_VARIABLE, "#LIST DEL: Invalid index: %s", arg1);
+		if (index == -1)
+		{
+			show_error(ses, LIST_VARIABLE, "#LIST {%s} DEL: Invalid index: %s", var, arg1);
 
 
-				return ses;
-			}
+			return ses;
+		}
 
 
-			for (cnt = index + 1 ; cnt < list->root->used ; cnt++)
-			{
-				str_cpy_printf(&list->root->list[cnt]->arg1, "%d", cnt);
-			}
+		for (cnt = index + loop ; cnt < list->root->used ; cnt++)
+		{
+			str_cpy_printf(&list->root->list[cnt]->arg1, "%d", cnt + 1 - loop);
+		}
 
 
+		while (loop--)
+		{
 			delete_index_list(list->root, index);
 			delete_index_list(list->root, index);
 		}
 		}
 	}
 	}
@@ -297,89 +386,31 @@ DO_ARRAY(array_explode)
 
 
 DO_ARRAY(array_find)
 DO_ARRAY(array_find)
 {
 {
-	char *arg3;
-	int cnt, index;
-
-	arg3 = str_alloc_stack(0);
+	int index;
 
 
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ONE, SUB_VAR|SUB_FUN);
-	arg = sub_arg_in_braces(ses, arg, arg3, GET_ALL, SUB_VAR|SUB_FUN);
 
 
 	if (*arg2 == 0)
 	if (*arg2 == 0)
 	{
 	{
-		show_error(ses, LIST_VARIABLE, "#SYNTAX: #LIST {variable} FIND [nest] {string} {variable}");
+		show_error(ses, LIST_VARIABLE, "#SYNTAX: #LIST {variable} FIND {string} {variable}");
 
 
 		return ses;
 		return ses;
 	}
 	}
 
 
 	if (list->root)
 	if (list->root)
 	{
 	{
-		if (*arg3 == 0)
+		for (index = 0 ; index < list->root->used ; index++)
 		{
 		{
-			for (index = 0 ; index < list->root->used ; index++)
-			{
-				if (match(ses, list->root->list[index]->arg2, arg1, SUB_NONE))
-				{
-					break;
-				}
-			}
-			if (index < list->root->used)
+			if (match(ses, list->root->list[index]->arg2, arg1, SUB_NONE))
 			{
 			{
 				set_nest_node_ses(ses, arg2, "%d", index + 1);
 				set_nest_node_ses(ses, arg2, "%d", index + 1);
-			}
-			else
-			{
-				set_nest_node_ses(ses, arg2, "0");
-			}
-			return ses;
-		}
-		else
-		{
-			if (list->root->list[0]->root == NULL)
-			{
-				show_error(ses, LIST_COMMAND, "#ERROR: #LIST {%s} FIND: NOT AN INDEXABLE LIST TABLE.");
-		
+
 				return ses;
 				return ses;
 			}
 			}
-		
-			if (list->root->used > 1)
-			{
-				int index = search_index_list(list->root->list[0]->root, arg1, "");
-		
-				if (index == -1)
-				{
-					show_error(ses, LIST_COMMAND, "#ERROR: #LIST {%s} FIND {%s}: FAILED TO FIND NEST.", var, arg1);
-		
-					return ses;
-				}
-		
-				for (cnt = 0 ; cnt < list->root->used ; cnt++)
-				{
-					if (list->root->list[cnt]->root && list->root->list[cnt]->root->used > index)
-					{
-						if (match(ses, list->root->list[cnt]->root->list[index]->arg2, arg2, SUB_NONE))
-						{
-							break;
-						}
-					}
-				}
-
-				if (cnt < list->root->used)
-				{
-					set_nest_node_ses(ses, arg3, "%d", cnt + 1);
-				}
-				else
-				{
-					set_nest_node_ses(ses, arg3, "%d", 0);
-				}
-			}
 		}
 		}
 	}
 	}
-	else
-	{
-		set_nest_node_ses(ses, arg2, "0");
-	}
+	set_nest_node_ses(ses, arg2, "0");
 
 
 	return ses;
 	return ses;
 }
 }
@@ -387,6 +418,8 @@ DO_ARRAY(array_find)
 
 
 DO_ARRAY(array_get)
 DO_ARRAY(array_get)
 {
 {
+	int index;
+
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
 
 
@@ -399,22 +432,16 @@ DO_ARRAY(array_get)
 
 
 	if (list->root)
 	if (list->root)
 	{
 	{
-		int index = search_nest_index(list->root, arg1);
+		index = get_list_index(ses, list->root, arg1);
 
 
-		if (atoi(arg1) == 0 || index == -1)
-		{
-			set_nest_node_ses(ses, arg2, "0");
-		}
-		else
+		if (index != -1)
 		{
 		{
 			set_nest_node_ses(ses, arg2, "%s", list->root->list[index]->arg2);
 			set_nest_node_ses(ses, arg2, "%s", list->root->list[index]->arg2);
+
+			return ses;
 		}
 		}
-		return ses;
-	}
-	else
-	{
-		set_nest_node_ses(ses, arg2, "0");
 	}
 	}
+	set_nest_node_ses(ses, arg2, "0");
 
 
 	return ses;
 	return ses;
 }
 }
@@ -461,7 +488,7 @@ DO_ARRAY(array_index)
 
 
 DO_ARRAY(array_insert)
 DO_ARRAY(array_insert)
 {
 {
-	int cnt, index;
+	int cnt, toi, index;
 
 
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
@@ -471,16 +498,18 @@ DO_ARRAY(array_insert)
 		list->root = init_list(ses, LIST_VARIABLE, LIST_SIZE);
 		list->root = init_list(ses, LIST_VARIABLE, LIST_SIZE);
 	}
 	}
 
 
-	index = search_nest_index(list->root, arg1);
+	toi = get_number(ses, arg1);
 
 
-	if (atoi(arg1) == 0)
+	if (toi == 0)
 	{
 	{
 		show_error(ses, LIST_VARIABLE, "#LIST INS: Invalid index: %s", arg1);
 		show_error(ses, LIST_VARIABLE, "#LIST INS: Invalid index: %s", arg1);
-		
+
 		return ses;
 		return ses;
 	}
 	}
 
 
-	if (index == -1 || atoi(arg1) < 0)
+	index = get_list_index(ses, list->root, arg1);
+
+	if (index == -1 || toi < 0)
 	{
 	{
 		index++;
 		index++;
 	}
 	}
@@ -645,22 +674,21 @@ DO_ARRAY(array_size)
 
 
 DO_ARRAY(array_set)
 DO_ARRAY(array_set)
 {
 {
+	int index;
+
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg2, GET_ALL, SUB_VAR|SUB_FUN);
 
 
 	if (list->root)
 	if (list->root)
 	{
 	{
-		int index = search_nest_index(list->root, arg1);
+		index = get_list_index(ses, list->root, arg1);
 
 
-		if (atoi(arg1) == 0 || index == -1)
+		if (index == -1)
 		{
 		{
-			show_error(ses, LIST_VARIABLE, "#LIST SET: Invalid index: %s", arg1);
-			
+			show_error(ses, LIST_VARIABLE, "#LIST {%s} SET: Invalid index: %s", var, arg1);
+
 			return ses;
 			return ses;
 		}
 		}
-
-//		set_nest_node(list->root, ntos(index + 1), "%s", arg2);
-
 		str_cpy(&list->root->list[index]->arg2, arg2);
 		str_cpy(&list->root->list[index]->arg2, arg2);
 
 
 		return ses;
 		return ses;

+ 11 - 7
src/main.c

@@ -150,7 +150,7 @@ void trap_handler(int signal)
 int main(int argc, char **argv)
 int main(int argc, char **argv)
 {
 {
 	int c, i = 0, greeting = 0;
 	int c, i = 0, greeting = 0;
-	char filename[PATH_SIZE];
+
 	char arg[BUFFER_SIZE];
 	char arg[BUFFER_SIZE];
 
 
 	#ifdef SOCKS
 	#ifdef SOCKS
@@ -286,12 +286,6 @@ int main(int argc, char **argv)
 
 
 	init_tintin(greeting);
 	init_tintin(greeting);
 
 
-	sprintf(filename, "%s/%s", gtd->system->tt_dir, HISTORY_FILE);
-
-	if (access(filename, F_OK ) != -1)
-	{
-		command(gts, do_history, "read %s", filename);
-	}
 
 
 	RESTRING(gtd->vars[1], argv[0]);
 	RESTRING(gtd->vars[1], argv[0]);
 
 
@@ -426,6 +420,7 @@ int main(int argc, char **argv)
 
 
 void init_tintin(int greeting)
 void init_tintin(int greeting)
 {
 {
+	char filename[PATH_SIZE];
 	int index;
 	int index;
 
 
 	gtd                 = (struct tintin_data *) calloc(1, sizeof(struct tintin_data));
 	gtd                 = (struct tintin_data *) calloc(1, sizeof(struct tintin_data));
@@ -526,6 +521,8 @@ void init_tintin(int greeting)
 	gts->lognext_name   = strdup("");
 	gts->lognext_name   = strdup("");
 	gts->logline_name   = strdup("");
 	gts->logline_name   = strdup("");
 
 
+	gts->more_output    = str_dup("");
+
 	gtd->ses = gts;
 	gtd->ses = gts;
 
 
 	for (index = 0 ; index < LIST_MAX ; index++)
 	for (index = 0 ; index < LIST_MAX ; index++)
@@ -591,6 +588,13 @@ void init_tintin(int greeting)
 	command(gts, do_pathdir, "se nw  6");
 	command(gts, do_pathdir, "se nw  6");
 	command(gts, do_pathdir, "sw ne 12");
 	command(gts, do_pathdir, "sw ne 12");
 
 
+	sprintf(filename, "%s/%s", gtd->system->tt_dir, HISTORY_FILE);
+
+	if (access(filename, F_OK ) != -1)
+	{
+		command(gts, do_history, "read %s", filename);
+	}
+
 	gtd->level->input--;
 	gtd->level->input--;
 
 
 	if (HAS_BIT(greeting,  STARTUP_FLAG_VERBOSE))
 	if (HAS_BIT(greeting,  STARTUP_FLAG_VERBOSE))

+ 3 - 3
src/mapper.c

@@ -2414,10 +2414,10 @@ char *draw_room(struct session *ses, struct room_data *room, int line, int x, in
 		if (HAS_BIT(room->flags, ROOM_FLAG_PATH) && room->search_stamp == ses->map->search->stamp)
 		if (HAS_BIT(room->flags, ROOM_FLAG_PATH) && room->search_stamp == ses->map->search->stamp)
 		{
 		{
 			room_color = ses->map->color[MAP_COLOR_PATH];
 			room_color = ses->map->color[MAP_COLOR_PATH];
-
 			if (symsize > 1)
 			if (symsize > 1)
 			{
 			{
-				symsize = 0;
+				strcpy(room_symbol, " ");
+				symsize = 1;
 			}
 			}
 		}
 		}
 		else if (*room->color)
 		else if (*room->color)
@@ -7190,7 +7190,7 @@ DO_MAP(map_map)
 			break;
 			break;
 
 
 		case 'D':
 		case 'D':
-			draw_arg(ses, 1, 2, 3, 4, 5, 6, 7, "", arg4, arg2, arg1, arg3);
+			command(ses, do_draw, "tile %s {%s}", arg4, arg1);
 			break;
 			break;
 
 
 		case 'S':
 		case 'S':

+ 13 - 1
src/misc.c

@@ -221,11 +221,22 @@ DO_COMMAND(do_send)
 }
 }
 
 
 
 
-
 DO_COMMAND(do_test)
 DO_COMMAND(do_test)
 {
 {
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ONE, SUB_VAR|SUB_FUN);
 
 
+/*	if (!strcmp(arg1, "bla"))
+	{
+		int size = sizeof(_gbk1_to_unicode_table) / sizeof(struct interval_type);
+
+		printf("size: %d\n", size);
+
+		for (int i = 0 ; i < size ; i++)
+		{
+			command(ses, do_line, "log tmp %d,", _gbk1_to_unicode_table[i].tail);
+		}
+	}
+*/
 	if (!strcmp(arg1, "rain"))
 	if (!strcmp(arg1, "rain"))
 	{
 	{
 		strcpy(arg2, "9");
 		strcpy(arg2, "9");
@@ -250,6 +261,7 @@ DO_COMMAND(do_test)
 
 
 		return ses;
 		return ses;
 	}
 	}
+
 	return ses;
 	return ses;
 }
 }
 
 

+ 44 - 15
src/nest.c

@@ -815,7 +815,7 @@ void show_nest_node(struct listnode *node, char **str_result, int initialize)
 	}
 	}
 }
 }
 
 
-void view_nest_node(struct listnode *node, char **str_result, int nest, int initialize)
+void view_nest_node(struct listnode *node, char **str_result, int nest, int initialize, int color)
 {
 {
 	if (initialize == TRUE)
 	if (initialize == TRUE)
 	{
 	{
@@ -830,7 +830,14 @@ void view_nest_node(struct listnode *node, char **str_result, int nest, int init
 		}
 		}
 		else
 		else
 		{
 		{
-			str_cat_printf(str_result, COLOR_BRACE "{" COLOR_STRING "%s" COLOR_BRACE "}\n", node->arg2);
+			if (color)
+			{
+				str_cat_printf(str_result, COLOR_BRACE "{" COLOR_STRING "%s" COLOR_BRACE "}\n", node->arg2);
+			}
+			else
+			{
+				str_cat_printf(str_result, "{%s}\n", node->arg2);
+			}
 		}
 		}
 	}
 	}
 	else
 	else
@@ -840,23 +847,44 @@ void view_nest_node(struct listnode *node, char **str_result, int nest, int init
 
 
 		if (initialize == FALSE)
 		if (initialize == FALSE)
 		{
 		{
-			str_cat_printf(str_result, "\n" COLOR_BRACE "%s{\n", indent(nest));
+			if (color)
+			{
+				str_cat_printf(str_result, "\n" COLOR_BRACE "%s{\n", indent(nest));
+			}
+			else
+			{
+				str_cat_printf(str_result, "\n%s{\n", indent(nest));
+			}
 		}
 		}
 
 
 		nest++;
 		nest++;
 
 
 		for (i = 0 ; i < root->used ; i++)
 		for (i = 0 ; i < root->used ; i++)
 		{
 		{
-			str_cat_printf(str_result, COLOR_BRACE "%s{" COLOR_STRING "%s" COLOR_BRACE "} ", indent(nest), root->list[i]->arg1);
+			if (color)
+			{
+				str_cat_printf(str_result, COLOR_BRACE "%s{" COLOR_STRING "%s" COLOR_BRACE "} ", indent(nest), root->list[i]->arg1);
+			}
+			else
+			{
+				str_cat_printf(str_result, "%s{%s} ", indent(nest), root->list[i]->arg1);
+			}
 
 
-			view_nest_node(root->list[i], str_result, nest, FALSE);
+			view_nest_node(root->list[i], str_result, nest, FALSE, color);
 		}
 		}
 
 
 		nest--;
 		nest--;
 
 
 		if (initialize == FALSE)
 		if (initialize == FALSE)
 		{
 		{
-			str_cat_printf(str_result, COLOR_BRACE "%s}\n", indent(nest), "");
+			if (color)
+			{
+				str_cat_printf(str_result, COLOR_BRACE "%s}\n", indent(nest), "");
+			}
+			else
+			{
+				str_cat_printf(str_result, "%s}\n", indent(nest), "");
+			}
 		}
 		}
 	}
 	}
 }
 }
@@ -883,7 +911,7 @@ struct listnode *set_nest_node_ses(struct session *ses, char *arg1, char *format
 
 
 	if (HAS_BIT(ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 2, "VARIABLE UPDATE %s", name, name, arg2);
+		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATE %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	root = search_nest_base_ses(ses, name);
 	root = search_nest_base_ses(ses, name);
@@ -896,7 +924,7 @@ struct listnode *set_nest_node_ses(struct session *ses, char *arg1, char *format
 		}
 		}
 		else
 		else
 		{
 		{
-			root = ses->list[LIST_VARIABLE];
+                      root = ses->list[LIST_VARIABLE];
 		}
 		}
 		node = NULL;
 		node = NULL;
 	}
 	}
@@ -946,7 +974,7 @@ struct listnode *set_nest_node_ses(struct session *ses, char *arg1, char *format
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 1, "VARIABLE UPDATED %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATED %s", name, name, arg2, arg1);
 	}
 	}
 	free(arg2);
 	free(arg2);
 
 
@@ -977,7 +1005,7 @@ struct listnode *add_nest_node_ses(struct session *ses, char *arg1, char *format
 
 
 	if (HAS_BIT(ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 2, "VARIABLE UPDATE %s", name, name, arg2);
+		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATE %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	root = search_nest_base_ses(ses, name);
 	root = search_nest_base_ses(ses, name);
@@ -1035,7 +1063,7 @@ struct listnode *add_nest_node_ses(struct session *ses, char *arg1, char *format
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 1, "VARIABLE UPDATED %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATED %s", name, name, arg2, arg1);
 	}
 	}
 	free(arg2);
 	free(arg2);
 
 
@@ -1065,7 +1093,7 @@ struct listnode *set_nest_node(struct listroot *root, char *arg1, char *format,
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 2, "VARIABLE UPDATE %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATE %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_LOCAL))
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_LOCAL))
@@ -1119,7 +1147,7 @@ struct listnode *set_nest_node(struct listroot *root, char *arg1, char *format,
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 1, "VARIABLE UPDATED %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATED %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	free(arg2);
 	free(arg2);
@@ -1140,6 +1168,7 @@ struct listnode *add_nest_node(struct listroot *root, char *arg1, char *format,
 	push_call("add_nest_node(%p,%s,%p,...)",root,arg1,format);
 	push_call("add_nest_node(%p,%s,%p,...)",root,arg1,format);
 
 
 	va_start(args, format);
 	va_start(args, format);
+
 	if (vasprintf(&arg2, format, args) == -1)
 	if (vasprintf(&arg2, format, args) == -1)
 	{
 	{
 		syserr_printf(root->ses, "add_nest_node: vasprintf");
 		syserr_printf(root->ses, "add_nest_node: vasprintf");
@@ -1151,7 +1180,7 @@ struct listnode *add_nest_node(struct listroot *root, char *arg1, char *format,
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 2, "VARIABLE UPDATE %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATE %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_LOCAL))
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_LOCAL))
@@ -1208,7 +1237,7 @@ struct listnode *add_nest_node(struct listroot *root, char *arg1, char *format,
 
 
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	if (HAS_BIT(root->ses->event_flags, EVENT_FLAG_VARIABLE))
 	{
 	{
-		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 1, "VARIABLE UPDATED %s", name, name, arg2);
+		check_all_events(root->ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATED %s", name, name, arg2, arg1);
 	}
 	}
 
 
 	free(arg2);
 	free(arg2);

+ 6 - 6
src/net.c

@@ -480,13 +480,13 @@ void readmud(struct session *ses)
 				*next_line++ = 0;
 				*next_line++ = 0;
 			}
 			}
 
 
-			if (strlen(ses->more_output) < BUFFER_SIZE / 3)
+			if (str_len(ses->more_output) < BUFFER_SIZE / 3)
 			{
 			{
 				if (!HAS_BIT(ses->telopts, TELOPT_FLAG_PROMPT))
 				if (!HAS_BIT(ses->telopts, TELOPT_FLAG_PROMPT))
 				{
 				{
 					if (ses->packet_patch)
 					if (ses->packet_patch)
 					{
 					{
-						strcat(ses->more_output, line);
+						str_cat(&ses->more_output, line);
 						ses->check_output = utime() + ses->packet_patch;
 						ses->check_output = utime() + ses->packet_patch;
 
 
 						break;
 						break;
@@ -497,14 +497,14 @@ void readmud(struct session *ses)
 						{
 						{
 							if (!detect_prompt(ses, line))
 							if (!detect_prompt(ses, line))
 							{
 							{
-								strcat(ses->more_output, line);
+								str_cat(&ses->more_output, line);
 								ses->check_output = utime() + 500000ULL;
 								ses->check_output = utime() + 500000ULL;
 								break;
 								break;
 							}
 							}
 						}
 						}
 						else if (HAS_BIT(ses->config_flags, CONFIG_FLAG_AUTOPROMPT))
 						else if (HAS_BIT(ses->config_flags, CONFIG_FLAG_AUTOPROMPT))
 						{
 						{
-							strcat(ses->more_output, line);
+							str_cat(&ses->more_output, line);
 							ses->check_output = utime() + 500000ULL;
 							ses->check_output = utime() + 500000ULL;
 							break;
 							break;
 						}
 						}
@@ -517,10 +517,10 @@ void readmud(struct session *ses)
 		{
 		{
 			if (ses->check_output)
 			if (ses->check_output)
 			{
 			{
-				strcat(ses->more_output, line);
+				str_cat(&ses->more_output, line);
 				strcpy(linebuf, ses->more_output);
 				strcpy(linebuf, ses->more_output);
 
 
-				ses->more_output[0] = 0;
+				str_cpy(&ses->more_output, "");
 			}
 			}
 			else
 			else
 			{
 			{

+ 36 - 0
src/scan.c

@@ -34,6 +34,42 @@
 #endif
 #endif
 #include <dirent.h>
 #include <dirent.h>
 
 
+#define DO_SCAN(scan) struct session *scan(struct session *ses, FILE *fp, char *arg, char *arg1, char *arg2)
+
+DO_SCAN(scan_abort);
+DO_SCAN(scan_csv);
+DO_SCAN(scan_dir);
+DO_SCAN(scan_file);
+DO_SCAN(scan_forward);
+DO_SCAN(scan_tsv);
+DO_SCAN(scan_txt);
+
+#define SCAN_FLAG_NONE                0
+#define SCAN_FLAG_FILE                BV01
+#define SCAN_FLAG_SCAN                BV02
+
+typedef struct session *SCAN(struct session *ses, FILE *fp, char *arg, char *arg1, char *arg2);
+
+struct scan_type
+{
+	char                  * name;
+	SCAN                  * fun;
+	int                     flags;
+	char                  * desc;
+};
+
+struct scan_type scan_table[] =
+{
+	{       "ABORT",            scan_abort,   SCAN_FLAG_NONE,                "Abort a scan currently in progress."},
+	{       "CSV",              scan_csv,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a comma separated value file." },
+	{       "DIR",              scan_dir,     SCAN_FLAG_FILE,                "Scan a directory to a variable."    },
+	{       "FILE",             scan_file,    SCAN_FLAG_FILE,                "Scan a file all at once."           },
+	{       "FORWARD",          scan_forward, SCAN_FLAG_FILE,                "Scan a file and send each line."    },
+	{       "TSV",              scan_tsv,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a tab separated value file."   },
+	{       "TXT",              scan_txt,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a text file line by line."     },
+	{       "",                 NULL,         0,                             ""                                   }
+};
+
 DO_COMMAND(do_scan)
 DO_COMMAND(do_scan)
 {
 {
 	char cmd[BUFFER_SIZE];
 	char cmd[BUFFER_SIZE];

+ 266 - 4
src/screen.c

@@ -26,6 +26,252 @@
 #include "tintin.h"
 #include "tintin.h"
 #include "telnet.h"
 #include "telnet.h"
 
 
+#define DO_SCREEN(screen)               void screen (struct session *ses, int ind, char *arg, char *arg1, char *arg2)
+
+extern DO_SCREEN(screen_blur);
+extern DO_SCREEN(screen_clear);
+extern DO_SCREEN(screen_cursor);
+extern DO_SCREEN(screen_dump);
+extern DO_SCREEN(screen_fill);
+extern DO_SCREEN(screen_focus);
+extern DO_SCREEN(screen_fullscreen);
+extern DO_SCREEN(screen_get);
+extern DO_SCREEN(screen_info);
+extern DO_SCREEN(screen_inputregion);
+extern DO_SCREEN(screen_load);
+extern DO_SCREEN(screen_maximize);
+extern DO_SCREEN(screen_minimize);
+extern DO_SCREEN(screen_move);
+extern DO_SCREEN(screen_print);
+extern DO_SCREEN(screen_raise);
+extern DO_SCREEN(screen_refresh);
+extern DO_SCREEN(screen_resize);
+extern DO_SCREEN(screen_rescale);
+extern DO_SCREEN(screen_save);
+extern DO_SCREEN(screen_scrollbar);
+extern DO_SCREEN(screen_scrollregion);
+extern DO_SCREEN(screen_set);
+extern DO_SCREEN(screen_swap);
+
+typedef void            SCREEN  (struct session *ses, int ind, char *arg, char *arg1, char *arg2);
+
+struct screen_type
+{
+	char                  * name;
+	char                  * desc;
+	int                     get1;
+	int                     get2;
+	int                     flags;
+	SCREEN                * fun;
+};
+
+struct screen_type screen_table[] =
+{
+	{
+		"BLUR",
+		"Shuffle the screen to the back of the desktop.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_blur
+	},
+	{
+		"CLEAR",
+		"Clear the screen.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_NONE,
+		SCREEN_FLAG_CSIP,
+		screen_clear
+	},
+	{
+		"CURSOR",
+		"Cursor settings.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_cursor
+	},
+
+	{
+		"DUMP",
+		"Dump the screen buffer.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_dump
+	},
+
+	{
+		"FILL",
+		"Fill given region with given character.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_fill
+	},
+	{
+		"FOCUS",
+		"Shuffle the screen to the front of the desktop.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_focus
+	},
+	{
+		"FULLSCREEN",
+		"Toggle fullscreen mode.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_fullscreen
+	},
+	{
+		"GET",
+		"Save screen information to given variable.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_get
+	},
+	{
+		"INFO",
+		"Show some debugging information.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_info
+	},
+	{
+		"INPUTREGION",
+		"Set the input region to {square}.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_inputregion
+	},
+
+	{
+		"LOAD",
+		"Load screen information from memory.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_OSCT,
+		screen_load
+	},
+	{
+		"MAXIMIZE",
+		"Maximize or restore the screen.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_maximize
+	},
+
+	{
+		"MINIMIZE",
+		"Minimize or restore the screen.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_minimize
+	},
+	{
+		"MOVE",
+		"Move the screen to the given position.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_move
+	},
+	{
+		"PRINT",
+		"Print the screen dump to the screen.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_print
+	},
+	{
+		"RAISE",
+		"Raise a screen event.",
+		SCREEN_FLAG_GET_ALL,
+		SCREEN_FLAG_GET_ALL,
+		SCREEN_FLAG_CSIP,
+		screen_raise
+	},
+	{
+		"REFRESH",
+		"Force a refresh of the screen.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_refresh
+	},
+	{
+		"RESCALE",
+		"Rescale the screen to {height} {width} pixels.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_rescale
+	},
+	{
+		"RESIZE",
+		"Resize the screen to {rows} {cols} characters.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_resize
+	},
+	{
+		"SAVE",
+		"Save screen information to memory.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_save
+	},
+
+	{
+		"SCROLLREGION",
+		"Set the scroll region to {square}.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_scrollregion
+	},
+
+	{
+		"SCROLLBAR",
+		"Scrollbar settings.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_scrollbar
+	},
+
+
+	{
+		"SET",
+		"Set screen information.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_OSCT,
+		screen_set
+	},
+	{
+		"SWAP",
+		"Swap the input and scroll region.",
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_GET_ONE,
+		SCREEN_FLAG_CSIP,
+		screen_swap
+	},
+	{
+		"", "", 0, 0, 0, NULL
+	}
+};
+
 void screen_osc(char *arg1, char *arg2);
 void screen_osc(char *arg1, char *arg2);
 void screen_csi(char *cmd, char *arg1, char *arg2, char *arg3, char *tc);
 void screen_csi(char *cmd, char *arg1, char *arg2, char *arg3, char *tc);
 void screen_csit(struct session *ses, char *arg1, char *arg2, char *tc);
 void screen_csit(struct session *ses, char *arg1, char *arg2, char *tc);
@@ -138,6 +384,11 @@ DO_SCREEN(screen_clear)
 {
 {
 	int top_row, top_col, bot_row, bot_col;
 	int top_row, top_col, bot_row, bot_col;
 
 
+	if (ses != gtd->ses)
+	{
+		return;
+	}
+
 	if (is_abbrev(arg1, "ALL"))
 	if (is_abbrev(arg1, "ALL"))
 	{
 	{
 		print_stdout(0, 0, "\e[2J");
 		print_stdout(0, 0, "\e[2J");
@@ -301,12 +552,12 @@ DO_SCREEN(screen_fill)
 		{
 		{
 			if (ses->split->sav_top_col)
 			if (ses->split->sav_top_col)
 			{
 			{
-				command(ses, do_draw, "%s VERTICAL LINE %d %d %d %d", arg2, ses->split->top_row, ses->split->top_col - 1, ses->split->bot_row, ses->split->top_col - 1);
+				command(ses, do_draw, "%s BOT TEED LINE %d %d %d %d", arg2, ses->split->top_row, ses->split->top_col - 1, ses->split->bot_row + 1, ses->split->top_col - 1);
 			}
 			}
 
 
 			if (ses->split->sav_bot_col)
 			if (ses->split->sav_bot_col)
 			{
 			{
-				command(ses, do_draw, "%s VERTICAL LINE %d %d %d %d", arg2, ses->split->top_row, ses->split->bot_col + 1, ses->split->bot_row, ses->split->bot_col + 1);
+				command(ses, do_draw, "%s BOT TEED LINE %d %d %d %d", arg2, ses->split->top_row, ses->split->bot_col + 1, ses->split->bot_row + 1, ses->split->bot_col + 1);
 			}
 			}
 		}
 		}
 	}
 	}
@@ -1883,7 +2134,12 @@ void destroy_screen()
 
 
 void print_scroll_region(struct session *ses)
 void print_scroll_region(struct session *ses)
 {
 {
-	int cnt;
+	char *wrap;
+	int cnt, height, width;
+
+	push_call("print_scroll_region(%p)",ses);
+
+	wrap = str_alloc_stack(0);
 
 
 	save_pos(ses);
 	save_pos(ses);
 
 
@@ -1891,9 +2147,15 @@ void print_scroll_region(struct session *ses)
 	{
 	{
 		print_stdout(0, 0, "\e[%d;%dH\e[%dX%s", cnt, ses->split->top_col, ses->wrap, gtd->screen->line[cnt - 1]->str);
 		print_stdout(0, 0, "\e[%d;%dH\e[%dX%s", cnt, ses->split->top_col, ses->wrap, gtd->screen->line[cnt - 1]->str);
 	}
 	}
-	print_stdout(0, 0, "\e[%d;%dH\e[%dX%s", cnt, ses->split->top_col, ses->wrap, ses->scroll->input);
+
+	word_wrap_split(ses, ses->scroll->input, wrap, ses->wrap, 0, 1, WRAP_FLAG_SPLIT, &height, &width);
+
+	print_stdout(0, 0, "\e[%d;%dH\e[%dX%s", cnt, ses->split->top_col, ses->wrap, wrap);
 
 
 	restore_pos(ses);
 	restore_pos(ses);
+
+	pop_call();
+	return;
 }
 }
 
 
 void print_screen()
 void print_screen()

+ 6 - 0
src/session.c

@@ -310,6 +310,8 @@ struct session *activate_session(struct session *ses)
 
 
 	if (!check_all_events(ses, EVENT_FLAG_GAG, 0, 1, "GAG SESSION ACTIVATED", ses->name))
 	if (!check_all_events(ses, EVENT_FLAG_GAG, 0, 1, "GAG SESSION ACTIVATED", ses->name))
 	{
 	{
+		buffer_refresh(ses, "", "", "");
+
 		show_message(ses, LIST_COMMAND, "#SESSION '%s' ACTIVATED.", ses->name);
 		show_message(ses, LIST_COMMAND, "#SESSION '%s' ACTIVATED.", ses->name);
 	}
 	}
 
 
@@ -393,6 +395,8 @@ struct session *new_session(struct session *ses, char *name, char *arg, int desc
 	newses->logline_name   = strdup("");
 	newses->logline_name   = strdup("");
 	newses->rand           = utime();
 	newses->rand           = utime();
 
 
+	newses->more_output    = str_dup("");
+
 	LINK(newses, gts->next, gts->prev);
 	LINK(newses, gts->next, gts->prev);
 
 
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_INHERITANCE))
 	if (HAS_BIT(gtd->flags, TINTIN_FLAG_INHERITANCE))
@@ -760,6 +764,8 @@ void dispose_session(struct session *ses)
 	free(ses->split);
 	free(ses->split);
 	free(ses->input);
 	free(ses->input);
 
 
+	str_free(ses->more_output);
+
 	free(ses);
 	free(ses);
 
 
 	pop_call();
 	pop_call();

+ 0 - 1
src/split.c

@@ -184,7 +184,6 @@ void init_split(struct session *ses, int top_row, int top_col, int bot_row, int
 		SET_BIT(ses->flags, SES_FLAG_UPDATEVTMAP);
 		SET_BIT(ses->flags, SES_FLAG_UPDATEVTMAP);
 	}
 	}
 
 
-
 	check_all_events(ses, EVENT_FLAG_SCREEN, 0, 4, "SCREEN SPLIT FILL", ntos(ses->split->top_row), ntos(ses->split->top_col), ntos(ses->split->bot_row), ntos(ses->split->bot_col), ntos(ses->split->sav_top_row), ntos(ses->split->sav_bot_row), ntos(ses->split->sav_top_col), ntos(ses->split->sav_bot_col));
 	check_all_events(ses, EVENT_FLAG_SCREEN, 0, 4, "SCREEN SPLIT FILL", ntos(ses->split->top_row), ntos(ses->split->top_col), ntos(ses->split->bot_row), ntos(ses->split->bot_col), ntos(ses->split->sav_top_row), ntos(ses->split->sav_bot_row), ntos(ses->split->sav_top_col), ntos(ses->split->sav_bot_col));
 
 
 	if (!check_all_events(ses, EVENT_FLAG_CATCH, 0, 8, "CATCH SCREEN SPLIT FILL", ntos(ses->split->top_row), ntos(ses->split->top_col), ntos(ses->split->bot_row), ntos(ses->split->bot_col), ntos(ses->split->sav_top_row), ntos(ses->split->sav_bot_row), ntos(ses->split->sav_top_col), ntos(ses->split->sav_bot_col)))
 	if (!check_all_events(ses, EVENT_FLAG_CATCH, 0, 8, "CATCH SCREEN SPLIT FILL", ntos(ses->split->top_row), ntos(ses->split->top_col), ntos(ses->split->bot_row), ntos(ses->split->bot_col), ntos(ses->split->sav_top_row), ntos(ses->split->sav_bot_row), ntos(ses->split->sav_top_col), ntos(ses->split->sav_bot_col)))

+ 23 - 23
src/substitute.c

@@ -1103,11 +1103,9 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					{
 					{
 						brace = TRUE;
 						brace = TRUE;
 
 
-						ptt = get_arg_in_braces(ses, &pti[i], buf, GET_ALL);
+						sub_arg_in_braces(ses, &pti[i], buf, GET_ONE, flags_neol);
 
 
-						i += strlen(buf) + 2;
-
-						substitute(ses, buf, temp, flags_neol);
+						get_arg_to_brackets(ses, buf, temp);
 					}
 					}
 					else
 					else
 					{
 					{
@@ -1124,14 +1122,17 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 
 
 					if (*temp)
 					if (*temp)
 					{
 					{
-						root = local_list(ses);
+						root = search_nest_base_ses(ses, temp);
 
 
-						if ((node = search_node_list(root, temp)) == NULL)
+						if (root)
 						{
 						{
-							root = ses->list[LIST_VARIABLE];
-
 							node = search_node_list(root, temp);
 							node = search_node_list(root, temp);
 						}
 						}
+						else
+						{
+							root = ses->list[LIST_VARIABLE];
+							node = NULL;
+						}
 					}
 					}
 					else
 					else
 					{
 					{
@@ -1165,7 +1166,7 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					}
 					}
 					else
 					else
 					{
 					{
-						pti = ptt;
+						pti = get_arg_in_braces(ses, &pti[i], temp, GET_ONE);
 					}
 					}
 
 
 					substitute(ses, temp, buf, flags_neol);
 					substitute(ses, temp, buf, flags_neol);
@@ -1208,11 +1209,9 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					{
 					{
 						brace = TRUE;
 						brace = TRUE;
 
 
-						ptt = get_arg_in_braces(ses, &pti[i], buf, GET_ALL);
+						sub_arg_in_braces(ses, &pti[i], buf, GET_ONE, flags_neol);
 
 
-						i += strlen(buf) + 2;
-
-						substitute(ses, buf, temp, flags_neol);
+						get_arg_to_brackets(ses, buf, temp);
 					}
 					}
 					else
 					else
 					{
 					{
@@ -1273,7 +1272,7 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					}
 					}
 					else
 					else
 					{
 					{
-						pti = ptt;
+						pti = get_arg_in_braces(ses, &pti[i], temp, GET_ONE);
 					}
 					}
 
 
 					substitute(ses, temp, buf, flags_neol);
 					substitute(ses, temp, buf, flags_neol);
@@ -1283,7 +1282,6 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					get_nest_node_val(root, buf, &str, brace);
 					get_nest_node_val(root, buf, &str, brace);
 
 
 					substitute(ses, str, pto, flags_neol - SUB_VAR);
 					substitute(ses, str, pto, flags_neol - SUB_VAR);
-//					substitute(ses, str, pto, flags_neol);
 
 
 					pto += strlen(pto);
 					pto += strlen(pto);
 
 
@@ -1345,11 +1343,9 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					{
 					{
 						brace = TRUE;
 						brace = TRUE;
 
 
-						ptt = get_arg_in_braces(ses, &pti[i], buf, GET_ALL);
-
-						i += strlen(buf) + 2;
+						sub_arg_in_braces(ses, &pti[i], buf, GET_ONE, flags_neol);
 
 
-						substitute(ses, buf, temp, flags_neol);
+						get_arg_to_brackets(ses, buf, temp);
 					}
 					}
 					else
 					else
 					{
 					{
@@ -1366,13 +1362,17 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 
 
 					if (*temp)
 					if (*temp)
 					{
 					{
-						root = local_list(ses);
+						root = search_nest_base_ses(ses, temp);
 
 
-						if ((node = search_node_list(root, temp)) == NULL)
+						if (root)
 						{
 						{
-							root = ses->list[LIST_VARIABLE];
 							node = search_node_list(root, temp);
 							node = search_node_list(root, temp);
 						}
 						}
+						else
+						{
+							root = ses->list[LIST_VARIABLE];
+							node = NULL;
+						}
 					}
 					}
 					else
 					else
 					{
 					{
@@ -1406,7 +1406,7 @@ int substitute(struct session *ses, char *string, char *result, int flags)
 					}
 					}
 					else
 					else
 					{
 					{
-						pti = ptt;
+						pti = get_arg_in_braces(ses, &pti[i], temp, GET_ONE);
 					}
 					}
 
 
 					substitute(ses, temp, buf, flags_neol);
 					substitute(ses, temp, buf, flags_neol);

+ 0 - 340
src/tables.c

@@ -728,23 +728,6 @@ struct color_type map_color_table[] =
 	{     NULL,               "<888>" }
 	{     NULL,               "<888>" }
 };
 };
 
 
-struct class_type class_table[] =
-{
-	{    "ASSIGN",            class_assign           },
-	{    "CLEAR",             class_clear            },
-	{    "CLOSE",             class_close            },
-	{    "KILL",              class_kill             },
-	{    "LIST",              class_list             },
-	{    "LOAD",              class_load             },
-	{    "OPEN",              class_open             },
-	{    "READ",              class_read             },
-	{    "SAVE",              class_save             },
-	{    "SIZE",              class_size             },
-	{    "WRITE",             class_write            },
-
-	{    "",                  NULL                   },
-};
-
 struct chat_type chat_table[] =
 struct chat_type chat_table[] =
 {
 {
 	{     "ACCEPT",           chat_accept,         0, 1, "Accept a file transfer"		              },
 	{     "ACCEPT",           chat_accept,         0, 1, "Accept a file transfer"		              },
@@ -818,33 +801,6 @@ struct rank_type rank_table[] =
 	{     "SCOUT",            RANK_FLAG_SCOUT     }
 	{     "SCOUT",            RANK_FLAG_SCOUT     }
 };
 };
 
 
-struct array_type array_table[] =
-{
-	{     "ADD",              array_add,         "Add an item to a list table"             },
-	{     "CLEAR",            array_clear,       "Clear a list"                            },
-	{     "CLR",              array_clear,       NULL                                      },
-	{     "COLLAPSE",         array_collapse,    "Collapse the list into a variable"       },
-	{     "CREATE",           array_create,      "Create a list table with given items"    },
-	{     "DELETE",           array_delete,      "Delete a list item with given index"     },
-	{     "EXPLODE",          array_explode,     "Explode the variable into a list"        },
-	{     "FIND",             array_find,        "Find a list item with given regex"       },
-	{     "FND",              array_find,        NULL                                      },
-	{     "GET",              array_get,         "Retrieve a list item with given index"   },
-	{     "INDEX",            array_index,       "Index a list table for sorting"          },
-	{     "INSERT",           array_insert,      "Insert a list item at given index"       },
-	{     "ORDER",            array_order,       "Sort a list table numerically"           },
-	{     "LENGTH",           array_size,        NULL                                      },
-	{     "REVERSE",          array_reverse,     "Sort a list table in reverse order"      },
-	{     "SET",              array_set,         "Change a list item at given index"       },
-	{     "SHUFFLE",          array_shuffle,     "Sort a list table in random order"       },
-	{     "SIMPLIFY",         array_simplify,    "Turn a list table into a simple list"    },
-	{     "SIZE",             array_size,        NULL                                      },
-	{     "SORT",             array_sort,        "Sort a list table alphabetically"        },
-	{     "SRT",              array_sort,        NULL                                      },
-	{     "TOKENIZE",         array_tokenize,    "Create a list with given characters"     },
-	{     "",                 NULL,                                                        }
-};
-
 // 0 no map, 1 has map, 2 is inside map
 // 0 no map, 1 has map, 2 is inside map
 
 
 struct map_type map_table[] =
 struct map_type map_table[] =
@@ -979,80 +935,6 @@ struct cursor_type cursor_table[] =
 	{     "",                   "",                                               "",                               0,    NULL,                         ""          }
 	{     "",                   "",                                               "",                               0,    NULL,                         ""          }
 };
 };
 
 
-struct draw_type draw_table[] =
-{
-	{
-		"BOX",
-		"Draw four sides of a box.",
-		DRAW_FLAG_BOXED|DRAW_FLAG_LEFT|DRAW_FLAG_RIGHT|DRAW_FLAG_TOP|DRAW_FLAG_BOT,
-		draw_box
-	},
-
-	{
-		"BUFFER",
-		"Draw the scrollback buffer.",
-		0,
-		draw_buffer
-	},
-
-	{
-		"CORNER",
-		"Draw a corner",
-		DRAW_FLAG_CORNERED,
-		draw_corner
-	},
-
-	{
-		"LINE",
-		"Draw a line.",
-		DRAW_FLAG_NONE,
-		draw_line
-	},
-
-	{
-		"MAP",
-		"Draw the map.",
-		0,
-		draw_map
-	},
-
-	{
-		"RAIN",
-		"Draw digital rain.",
-		0,
-		draw_rain
-	},
-
-	{
-		"SIDE",
-		"Draw a line with corners.",
-		DRAW_FLAG_BOXED,
-		draw_side
-	},
-
-	{
-		"TABLE",
-		"Draw a table.",
-		DRAW_FLAG_BOXED|DRAW_FLAG_LEFT|DRAW_FLAG_RIGHT|DRAW_FLAG_TOP|DRAW_FLAG_BOT,
-		draw_table_grid
-	},
-
-	{
-		"TILE",
-		"Draw a tile.",
-		0,
-		draw_square
-	},
-
-	{
-		"",
-		"",
-		0,
-		NULL
-	}
-};
-
-
 struct edit_type edit_table[] =
 struct edit_type edit_table[] =
 {
 {
 	{      "CREATE",            edit_create,         "Create an editor"                  },
 	{      "CREATE",            edit_create,         "Create an editor"                  },
@@ -1065,227 +947,6 @@ struct edit_type edit_table[] =
 	{      "",                  NULL,                ""                                  },
 	{      "",                  NULL,                ""                                  },
 };
 };
 
 
-
-struct scan_type scan_table[] =
-{
-	{       "ABORT",            scan_abort,   SCAN_FLAG_NONE,                "Abort a scan currently in progress."},
-	{       "CSV",              scan_csv,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a comma separated value file." },
-	{       "DIR",              scan_dir,     SCAN_FLAG_FILE,                "Scan a directory to a variable."    },
-	{       "FILE",             scan_file,    SCAN_FLAG_FILE,                "Scan a file all at once."           },
-	{       "FORWARD",          scan_forward, SCAN_FLAG_FILE,                "Scan a file and send each line."    },
-	{       "TSV",              scan_tsv,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a tab separated value file."   },
-	{       "TXT",              scan_txt,     SCAN_FLAG_FILE|SCAN_FLAG_SCAN, "Scan a text file line by line."     },
-	{       "",                 NULL,         0,                             ""                                   }
-};
-
-struct screen_type screen_table[] =
-{
-	{
-		"BLUR",
-		"Shuffle the screen to the back of the desktop.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_blur
-	},
-	{
-		"CLEAR",
-		"Clear the screen.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_NONE,
-		SCREEN_FLAG_CSIP,
-		screen_clear
-	},
-	{
-		"CURSOR",
-		"Cursor settings.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_cursor
-	},
-
-	{
-		"DUMP",
-		"Dump the screen buffer.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_dump
-	},
-
-	{
-		"FILL",
-		"Fill given region with given character.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_fill
-	},
-	{
-		"FOCUS",
-		"Shuffle the screen to the front of the desktop.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_focus
-	},
-	{
-		"FULLSCREEN",
-		"Toggle fullscreen mode.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_fullscreen
-	},
-	{
-		"GET",
-		"Save screen information to given variable.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_get
-	},
-	{
-		"INFO",
-		"Show some debugging information.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_info
-	},
-	{
-		"INPUTREGION",
-		"Set the input region to {square}.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_inputregion
-	},
-
-	{
-		"LOAD",
-		"Load screen information from memory.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_OSCT,
-		screen_load
-	},
-	{
-		"MAXIMIZE",
-		"Maximize or restore the screen.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_maximize
-	},
-
-	{
-		"MINIMIZE",
-		"Minimize or restore the screen.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_minimize
-	},
-	{
-		"MOVE",
-		"Move the screen to the given position.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_move
-	},
-	{
-		"PRINT",
-		"Print the screen dump to the screen.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_print
-	},
-	{
-		"RAISE",
-		"Raise a screen event.",
-		SCREEN_FLAG_GET_ALL,
-		SCREEN_FLAG_GET_ALL,
-		SCREEN_FLAG_CSIP,
-		screen_raise
-	},
-	{
-		"REFRESH",
-		"Force a refresh of the screen.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_refresh
-	},
-	{
-		"RESCALE",
-		"Rescale the screen to {height} {width} pixels.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_rescale
-	},
-	{
-		"RESIZE",
-		"Resize the screen to {rows} {cols} characters.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_resize
-	},
-	{
-		"SAVE",
-		"Save screen information to memory.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_save
-	},
-
-	{
-		"SCROLLREGION",
-		"Set the scroll region to {square}.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_scrollregion
-	},
-
-	{
-		"SCROLLBAR",
-		"Scrollbar settings.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_scrollbar
-	},
-
-
-	{
-		"SET",
-		"Set screen information.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_OSCT,
-		screen_set
-	},
-	{
-		"SWAP",
-		"Swap the input and scroll region.",
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_GET_ONE,
-		SCREEN_FLAG_CSIP,
-		screen_swap
-	},
-	{
-		"", "", 0, 0, 0, NULL
-	}
-};
-
-
 struct timer_type timer_table[] =
 struct timer_type timer_table[] =
 {
 {
 	{    "Update Input"                },
 	{    "Update Input"                },
@@ -1359,7 +1020,6 @@ struct event_type event_table[] =
 	{    "PRESSED ",                               0, EVENT_FLAG_MOUSE,    "MOUSE",     "mouse button is pressed"    },
 	{    "PRESSED ",                               0, EVENT_FLAG_MOUSE,    "MOUSE",     "mouse button is pressed"    },
 	{    "PROCESSED KEYPRESS",                     0, EVENT_FLAG_INPUT,    "INPUT",     "after a regular keypress"   },
 	{    "PROCESSED KEYPRESS",                     0, EVENT_FLAG_INPUT,    "INPUT",     "after a regular keypress"   },
 	{    "PROGRAM START",                          0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "main session starts"        },
 	{    "PROGRAM START",                          0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "main session starts"        },
-
 	{    "PROGRAM TERMINATION",                    0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "main session exists"        },
 	{    "PROGRAM TERMINATION",                    0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "main session exists"        },
 	{    "READ ERROR",                             0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "the read command fails"     },
 	{    "READ ERROR",                             0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "the read command fails"     },
 	{    "RECEIVED ERROR",                         0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "an error is received"       },
 	{    "RECEIVED ERROR",                         0, EVENT_FLAG_SYSTEM,   "SYSTEM",    "an error is received"       },

+ 29 - 91
src/text.c

@@ -214,7 +214,9 @@ int word_wrap(struct session *ses, char *textin, char *textout, int flags, int *
 			lis = pti;
 			lis = pti;
 		}
 		}
 
 
-		if (ses->cur_col > wrap)
+		size = get_vt102_width(ses, pti, &tab);
+
+		if (ses->cur_col > 1 && ses->cur_col + tab > wrap + 1)
 		{
 		{
 			cur_height++;
 			cur_height++;
 
 
@@ -253,29 +255,7 @@ int word_wrap(struct session *ses, char *textin, char *textout, int flags, int *
 		}
 		}
 		else
 		else
 		{
 		{
-			if (HAS_BIT(ses->charset, CHARSET_FLAG_EUC) && is_euc_head(ses, pti))
-			{
-				size = get_euc_width(ses, pti, &tab);
-
-				while (size--)
-				{
-					*pto++ = *pti++;
-				}
-				cur_width += tab;
-				ses->cur_col += tab;
-			}
-			else if (HAS_BIT(ses->charset, CHARSET_FLAG_UTF8) && is_utf8_head(pti))
-			{
-				size = get_utf8_width(pti, &tab);
-
-				while (size--)
-				{
-					*pto++ = *pti++;
-				}
-				cur_width += tab;
-				ses->cur_col += tab;
-			}
-			else if (*pti == '\t')
+			if (*pti == '\t')
 			{
 			{
 				tab = ses->tab_width - (ses->cur_col - 1) % ses->tab_width;
 				tab = ses->tab_width - (ses->cur_col - 1) % ses->tab_width;
 
 
@@ -292,10 +272,12 @@ int word_wrap(struct session *ses, char *textin, char *textout, int flags, int *
 			}
 			}
 			else
 			else
 			{
 			{
-				*pto++ = *pti++;
-
-				cur_width++;
-				ses->cur_col++;
+				while (size--)
+				{
+					*pto++ = *pti++;
+				}
+				cur_width += tab;
+				ses->cur_col += tab;
 			}
 			}
 		}
 		}
 	}
 	}
@@ -427,7 +409,9 @@ int word_wrap_split(struct session *ses, char *textin, char *textout, int wrap,
 			los = pto;
 			los = pto;
 		}
 		}
 
 
-		if (cur_col > wrap)
+		size = get_vt102_width(ses, pti, &tab);
+
+		if (cur_col > 1 && cur_col + tab > wrap + 1)
 		{
 		{
 			if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
 			if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
 			{
 			{
@@ -494,86 +478,40 @@ int word_wrap_split(struct session *ses, char *textin, char *textout, int wrap,
 			continue;
 			continue;
 		}
 		}
 
 
-		if (HAS_BIT(ses->charset, CHARSET_FLAG_EUC) && is_euc_head(ses, pti))
+		if (*pti == '\t')
 		{
 		{
-			size = get_euc_width(ses, pti, &tab);
+			tab = ses->tab_width - (cur_col - 1) % ses->tab_width;
 
 
-			if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
+			if (cur_col + tab >= wrap)
 			{
 			{
-				while (size--)
-				{
-					*pto++ = *pti++;
-				}
+				tab = (wrap - cur_col);
 			}
 			}
-			else
+
+			if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
 			{
 			{
-				pti += size;
+				pto += sprintf(pto, "%.*s", tab, "                ");
 			}
 			}
+			pti++;
+
 			cur_width += tab;
 			cur_width += tab;
 			cur_col += tab;
 			cur_col += tab;
-		}
-		else if (HAS_BIT(ses->charset, CHARSET_FLAG_UTF8) && is_utf8_head(pti))
-		{
-			size = get_utf8_width(pti, &tab);
-
-			if (size)
-			{
-				if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
-				{
-					while (size--)
-					{
-						*pto++ = *pti++;
-					}
-				}
-				else
-				{
-					pti += size;
-				}
-				cur_width += tab;
-				cur_col += tab;
-			}
-			else
-			{
-				print_stdout(0, 0, "debug: word_wrap_split: utf8 error\n");
-				*pto++ = *pti++;
-				cur_width++;
-				cur_col++;
-			}
+			cur_space = cur_col;
 		}
 		}
 		else
 		else
 		{
 		{
-			if (*pti == '\t')
+			if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
 			{
 			{
-				tab = ses->tab_width - (cur_col - 1) % ses->tab_width;
-
-				if (cur_col + tab >= wrap)
-				{
-					tab = (wrap - cur_col);
-				}
-
-				if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
+				while (size--)
 				{
 				{
-					pto += sprintf(pto, "%.*s", tab, "                ");
+					*pto++ = *pti++;
 				}
 				}
-				pti++;
-
-				cur_width += tab;
-				cur_col += tab;
-				cur_space = cur_col;
 			}
 			}
 			else
 			else
 			{
 			{
-				if (!HAS_BIT(flags, WRAP_FLAG_SPLIT) || (cur_height >= start && cur_height < end))
-				{
-					*pto++ = *pti++;
-				}
-				else
-				{
-					pti++;
-				}
-				cur_width++;
-				cur_col++;
+				pti += size;
 			}
 			}
+			cur_width += tab;
+			cur_col += tab;
 		}
 		}
 	}
 	}
 	*pto = 0;
 	*pto = 0;

+ 27 - 322
src/tintin.h

@@ -203,7 +203,7 @@
 #define STRING_SIZE        2 * BUFFER_SIZE
 #define STRING_SIZE        2 * BUFFER_SIZE
 
 
 #define CLIENT_NAME              "TinTin++"
 #define CLIENT_NAME              "TinTin++"
-#define CLIENT_VERSION           "2.02.04 "
+#define CLIENT_VERSION           "2.02.05 "
 
 
 
 
 #define XT_E                            0x27
 #define XT_E                            0x27
@@ -471,51 +471,6 @@ enum operators
 #define CHAT_FLAG_DND                 BV08
 #define CHAT_FLAG_DND                 BV08
 #define CHAT_FLAG_LINKLOST            BV09
 #define CHAT_FLAG_LINKLOST            BV09
 
 
-#define DRAW_FLAG_NONE                   0
-#define DRAW_FLAG_ASCII               BV01
-#define DRAW_FLAG_BLANKED             BV02
-#define DRAW_FLAG_BOT                 BV03
-#define DRAW_FLAG_BOXED               BV04
-#define DRAW_FLAG_BUMP                BV05
-#define DRAW_FLAG_CIRCLED             BV06
-#define DRAW_FLAG_COLOR1              BV07
-#define DRAW_FLAG_COLOR2              BV08
-#define DRAW_FLAG_CONVERT             BV09
-#define DRAW_FLAG_CORNERED            BV10
-#define DRAW_FLAG_CROSSED             BV11
-#define DRAW_FLAG_FILLED              BV12
-#define DRAW_FLAG_FOREGROUND          BV13
-#define DRAW_FLAG_GRID                BV14
-#define DRAW_FLAG_HOR                 BV15
-#define DRAW_FLAG_HUGE                BV16
-#define DRAW_FLAG_JEWELED             BV17
-#define DRAW_FLAG_LEFT                BV18
-//#define DRAW_FLAG_LINED               BV19 unused / obsolete
-#define DRAW_FLAG_NUMBERED            BV20
-#define DRAW_FLAG_PRUNED              BV21
-#define DRAW_FLAG_RIGHT               BV22
-#define DRAW_FLAG_ROUNDED             BV23
-#define DRAW_FLAG_SCALED              BV24
-#define DRAW_FLAG_SCROLL              BV25
-#define DRAW_FLAG_SHADOWED            BV26
-#define DRAW_FLAG_TEED                BV27
-#define DRAW_FLAG_TOP                 BV28
-#define DRAW_FLAG_TRACED              BV29
-#define DRAW_FLAG_TUBED               BV30
-#define DRAW_FLAG_UTF8                BV31
-#define DRAW_FLAG_VER                 BV32
-
-#define DRAW_FLAG_CURSIVE             BV33
-#define DRAW_FLAG_FAT                 BV34
-#define DRAW_FLAG_SANSSERIF           BV35
-#define DRAW_FLAG_CALIGN              BV36
-#define DRAW_FLAG_LALIGN              BV37
-#define DRAW_FLAG_RALIGN              BV38
-#define DRAW_FLAG_TALIGN              BV39
-#define DRAW_FLAG_UALIGN              BV40
-
-#define DRAW_FLAG_APPENDIX            DRAW_FLAG_CIRCLED|DRAW_FLAG_CORNERED|DRAW_FLAG_CROSSED|DRAW_FLAG_JEWELED|DRAW_FLAG_PRUNED|DRAW_FLAG_ROUNDED|DRAW_FLAG_TEED
-
 #define INPUT_FLAG_EDIT               BV01
 #define INPUT_FLAG_EDIT               BV01
 #define INPUT_FLAG_HISTORYBROWSE      BV02
 #define INPUT_FLAG_HISTORYBROWSE      BV02
 #define INPUT_FLAG_HISTORYSEARCH      BV03
 #define INPUT_FLAG_HISTORYSEARCH      BV03
@@ -564,10 +519,6 @@ enum operators
 #define MTTS_FLAG_PROXY               BV08
 #define MTTS_FLAG_PROXY               BV08
 #define MTTS_FLAG_TRUECOLOR           BV09
 #define MTTS_FLAG_TRUECOLOR           BV09
 
 
-#define SCAN_FLAG_NONE                0
-#define SCAN_FLAG_FILE                BV01
-#define SCAN_FLAG_SCAN                BV02
-
 #define SCREEN_FLAG_CSIP              BV01
 #define SCREEN_FLAG_CSIP              BV01
 #define SCREEN_FLAG_OSCT              BV02
 #define SCREEN_FLAG_OSCT              BV02
 #define SCREEN_FLAG_OMIT              BV03
 #define SCREEN_FLAG_OMIT              BV03
@@ -644,13 +595,13 @@ enum operators
 #define TINTIN_FLAG_INHERITANCE       BV04
 #define TINTIN_FLAG_INHERITANCE       BV04
 #define TINTIN_FLAG_INSERTINPUT       BV05
 #define TINTIN_FLAG_INSERTINPUT       BV05
 #define TINTIN_FLAG_CHILDLOCK         BV06
 #define TINTIN_FLAG_CHILDLOCK         BV06
-#define TINTIN_FLAG_TERMINATE         BV06
-#define TINTIN_FLAG_MOUSETRACKING     BV07
-#define TINTIN_FLAG_DISPLAYUPDATE     BV08
-#define TINTIN_FLAG_DAEMONIZE         BV09
-#define TINTIN_FLAG_HIDDENCURSOR      BV10
-#define TINTIN_FLAG_LOCAL             BV11
-#define TINTIN_FLAG_PRESERVEMACRO     BV12
+#define TINTIN_FLAG_TERMINATE         BV07
+#define TINTIN_FLAG_MOUSETRACKING     BV08
+#define TINTIN_FLAG_DISPLAYUPDATE     BV09
+#define TINTIN_FLAG_DAEMONIZE         BV10
+#define TINTIN_FLAG_HIDDENCURSOR      BV11
+#define TINTIN_FLAG_LOCAL             BV12
+#define TINTIN_FLAG_PRESERVEMACRO     BV13
 
 
 
 
 #define CONFIG_FLAG_AUTOPATCH         BV01
 #define CONFIG_FLAG_AUTOPATCH         BV01
@@ -1045,7 +996,7 @@ enum operators
 
 
 #define SCROLL(ses)               ((ses)->cur_row == 0 || ((ses)->cur_row >= (ses)->split->top_row && (ses)->cur_row <= (ses)->split->bot_row) || ((ses)->cur_row >= ses->input->top_row && (ses)->cur_row <= ses->input->bot_row))
 #define SCROLL(ses)               ((ses)->cur_row == 0 || ((ses)->cur_row >= (ses)->split->top_row && (ses)->cur_row <= (ses)->split->bot_row) || ((ses)->cur_row >= ses->input->top_row && (ses)->cur_row <= ses->input->bot_row))
 
 
-#define VERBATIM(ses)             (gtd->level->verbatim || (gtd->level->input == 0 && HAS_BIT((ses)->config_flags, CONFIG_FLAG_VERBATIM)) || HAS_BIT(gtd->flags, TINTIN_FLAG_CHILDLOCK))
+#define VERBATIM(ses)             (gtd->level->verbatim || (gtd->level->input == 0 && (HAS_BIT((ses)->config_flags, CONFIG_FLAG_VERBATIM) || HAS_BIT(gtd->flags, TINTIN_FLAG_CHILDLOCK))))
 
 
 
 
 
 
@@ -1232,7 +1183,8 @@ struct session
 	int                     read_max;
 	int                     read_max;
 	unsigned long long      connect_retry;
 	unsigned long long      connect_retry;
 	int                     connect_error;
 	int                     connect_error;
-	char                    more_output[BUFFER_SIZE];
+//	char                    more_output[BUFFER_SIZE];
+	char                  * more_output;
 	int                     color;
 	int                     color;
 	char                    color_patch[100];
 	char                    color_patch[100];
 	unsigned long long      packet_patch;
 	unsigned long long      packet_patch;
@@ -1631,10 +1583,8 @@ struct window_data
 	struct input_data      **buffer;
 	struct input_data      **buffer;
 };
 };
 
 
-#define DO_ARRAY(array)       struct session *array (struct session *ses, struct listnode *list, char *arg, char *var, char *arg1, char *arg2)
 #define DO_BUFFER(buffer)               void buffer (struct session *ses, char *arg, char *arg1, char *arg2)
 #define DO_BUFFER(buffer)               void buffer (struct session *ses, char *arg, char *arg1, char *arg2)
 #define DO_CHAT(chat)                     void chat (char *arg1, char *arg2)
 #define DO_CHAT(chat)                     void chat (char *arg1, char *arg2)
-#define DO_CLASS(class)       struct session *class (struct session *ses, struct listnode *node, char *arg1, char *arg2)
 #define DO_COMMAND(command) struct session *command (struct session *ses, char *arg, char *arg1, char *arg2, char *arg3, char *arg4)
 #define DO_COMMAND(command) struct session *command (struct session *ses, char *arg, char *arg1, char *arg2, char *arg3, char *arg4)
 #define DO_CONFIG(config)    struct session *config (struct session *ses, char *arg1, char *arg2, int index)
 #define DO_CONFIG(config)    struct session *config (struct session *ses, char *arg1, char *arg2, int index)
 #define DO_CURSOR(cursor)               void cursor (struct session *ses, char *arg)
 #define DO_CURSOR(cursor)               void cursor (struct session *ses, char *arg)
@@ -1646,9 +1596,7 @@ struct window_data
 #define DO_MAP(map)                        void map (struct session *ses, char *arg, char *arg1, char *arg2)
 #define DO_MAP(map)                        void map (struct session *ses, char *arg, char *arg1, char *arg2)
 #define DO_PATH(path)                     void path (struct session *ses, char *arg)
 #define DO_PATH(path)                     void path (struct session *ses, char *arg)
 #define DO_PORT(port)          struct session *port (struct session *ses, char *arg1, char *arg2, char *arg)
 #define DO_PORT(port)          struct session *port (struct session *ses, char *arg1, char *arg2, char *arg)
-#define DO_SCAN(scan)          struct session *scan (struct session *ses, FILE *fp, char *arg, char *arg1, char *arg2)
-#define DO_SCREEN(screen)               void screen (struct session *ses, int ind, char *arg, char *arg1, char *arg2)
-#define DO_DRAW(draw)                     void draw (struct session *ses, int top_row, int top_col, int bot_row, int bot_col, int rows, int cols, long long flags, char *color, char *arg, char *arg1, char *arg2, char *arg3)
+
 
 
 /*
 /*
 	Typedefs
 	Typedefs
@@ -1656,15 +1604,12 @@ struct window_data
 
 
 typedef int             CMPFUNC (const void *a, const void *b);
 typedef int             CMPFUNC (const void *a, const void *b);
 
 
-typedef struct session *ARRAY   (struct session *ses, struct listnode *list, char *arg, char *var, char *arg1, char *arg2);
 typedef void            BUFFER  (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            BUFFER  (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            CHAT    (char *arg1, char *arg2);
 typedef void            CHAT    (char *arg1, char *arg2);
-typedef struct session *CLASS   (struct session *ses, struct listnode *node, char *left, char *right);
 typedef struct session *CONFIG  (struct session *ses, char *arg1, char *arg2, int index);
 typedef struct session *CONFIG  (struct session *ses, char *arg1, char *arg2, int index);
 typedef struct session *COMMAND (struct session *ses, char *arg, char *arg1, char *arg2, char *arg3, char *arg4);
 typedef struct session *COMMAND (struct session *ses, char *arg, char *arg1, char *arg2, char *arg3, char *arg4);
 typedef void            CURSOR  (struct session *ses, char *arg);
 typedef void            CURSOR  (struct session *ses, char *arg);
 typedef void            DAEMON  (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            DAEMON  (struct session *ses, char *arg, char *arg1, char *arg2);
-typedef void            DRAW    (struct session *ses, int top_row, int top_col, int bot_row, int bot_col, int rows, int cols, long long flags, char *color, char *arg, char *arg1, char *arg2, char *arg3);
 typedef struct session *EDIT    (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef struct session *EDIT    (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            HISTORY (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            HISTORY (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            LOG     (struct session *ses, char *arg, char *arg1, char *arg2);
 typedef void            LOG     (struct session *ses, char *arg, char *arg1, char *arg2);
@@ -1673,23 +1618,12 @@ typedef void            MAP     (struct session *ses, char *arg, char *arg1, cha
 typedef void            MSDP    (struct session *ses, struct port_data *buddy, int index);
 typedef void            MSDP    (struct session *ses, struct port_data *buddy, int index);
 typedef void            PATH    (struct session *ses, char *arg);
 typedef void            PATH    (struct session *ses, char *arg);
 typedef struct session *PORT    (struct session *ses, char *arg1, char *arg2, char *arg);
 typedef struct session *PORT    (struct session *ses, char *arg1, char *arg2, char *arg);
-typedef struct session *SCAN    (struct session *ses, FILE *fp, char *arg, char *arg1, char *arg2);
-typedef void            SCREEN  (struct session *ses, int ind, char *arg, char *arg1, char *arg2);
-
-
 
 
 
 
 /*
 /*
 	Structures for tables.c
 	Structures for tables.c
 */
 */
 
 
-struct array_type
-{
-	char                  * name;
-	ARRAY                 * fun;
-	char                  * desc;
-};
-
 struct buffer_type
 struct buffer_type
 {
 {
 	char                  * name;
 	char                  * name;
@@ -1706,12 +1640,6 @@ struct chat_type
 	char                  * desc;
 	char                  * desc;
 };
 };
 
 
-struct class_type
-{
-	char                  * name;
-	CLASS                 * fun;
-};
-
 struct color_type
 struct color_type
 {
 {
 	char                  * name;
 	char                  * name;
@@ -1752,14 +1680,6 @@ struct daemon_type
 	char                  * desc;
 	char                  * desc;
 };
 };
 
 
-struct draw_type
-{
-	char                  * name;
-	char                  * desc;
-	int                     flags;
-	DRAW                  * fun;
-};
-
 struct edit_type
 struct edit_type
 {
 {
 	char                  * name;
 	char                  * name;
@@ -1886,25 +1806,6 @@ struct rank_type
 	int                     flags;
 	int                     flags;
 };
 };
 
 
-struct scan_type
-{
-	char                  * name;
-	SCAN                  * fun;
-	int                   flags;
-	char                  * desc;
-};
-
-struct screen_type
-{
-	char                  * name;
-	char                  * desc;
-	int                     get1;
-	int                     get2;
-	int                     flags;
-	SCREEN                * fun;
-};
-
-
 struct stamp_type
 struct stamp_type
 {
 {
 	char                  * name;
 	char                  * name;
@@ -1930,14 +1831,6 @@ struct telopt_type
 	int                     flags;
 	int                     flags;
 };
 };
 
 
-
-
-
-/*
-	Various structures
-*/
-
-
 #endif
 #endif
 
 
 
 
@@ -1946,34 +1839,6 @@ struct telopt_type
 */
 */
 
 
 
 
-
-#ifndef __ARRAY_H__
-#define __ARRAY_H__
-
-extern DO_COMMAND(do_list);
-
-extern DO_ARRAY(array_add);
-extern DO_ARRAY(array_clear);
-extern DO_ARRAY(array_collapse);
-extern DO_ARRAY(array_create);
-extern DO_ARRAY(array_delete);
-extern DO_ARRAY(array_explode);
-extern DO_ARRAY(array_find);
-extern DO_ARRAY(array_get);
-extern DO_ARRAY(array_index);
-extern DO_ARRAY(array_insert);
-extern DO_ARRAY(array_order);
-extern DO_ARRAY(array_reverse);
-extern DO_ARRAY(array_set);
-extern DO_ARRAY(array_shuffle);
-extern DO_ARRAY(array_simplify);
-extern DO_ARRAY(array_size);
-extern DO_ARRAY(array_sort);
-extern DO_ARRAY(array_tokenize);
-
-#endif
-
-
 #ifndef __BANNER_H__
 #ifndef __BANNER_H__
 #define __BANNER_H__
 #define __BANNER_H__
 
 
@@ -2071,34 +1936,9 @@ extern DO_CHAT(chat_zap);
 
 
 #endif
 #endif
 
 
-
-#ifndef __CLASS_H__
-#define __CLASS_H__
-
-extern DO_COMMAND(do_class);
-
-extern  int count_class(struct session *ses, struct listnode *group);
-extern void parse_class(struct session *ses, char *input, struct listnode *group);
-
-extern DO_CLASS(class_assign);
-extern DO_CLASS(class_clear);
-extern DO_CLASS(class_close);
-extern DO_CLASS(class_kill);
-extern DO_CLASS(class_list);
-extern DO_CLASS(class_load);
-extern DO_CLASS(class_open);
-extern DO_CLASS(class_read);
-extern DO_CLASS(class_save);
-extern DO_CLASS(class_size);
-extern DO_CLASS(class_write);
-
-#endif
-
 #ifndef __COMMAND_H__
 #ifndef __COMMAND_H__
 #define __COMMAND_H__
 #define __COMMAND_H__
 
 
-extern DO_COMMAND(do_commands);
-
 extern void init_commands(void);
 extern void init_commands(void);
 
 
 #endif
 #endif
@@ -2256,8 +2096,6 @@ extern DO_MAP(map_write);
 #ifndef __TT_MATH_H__
 #ifndef __TT_MATH_H__
 #define __TT_MATH_H__
 #define __TT_MATH_H__
 
 
-extern DO_COMMAND(do_math);
-
 extern int is_math(struct session *ses, char *str);
 extern int is_math(struct session *ses, char *str);
 extern int get_ellipsis(struct listroot *root, char *name, int *min, int *max);
 extern int get_ellipsis(struct listroot *root, char *name, int *min, int *max);
 extern long double get_number(struct session *ses, char *str);
 extern long double get_number(struct session *ses, char *str);
@@ -2341,11 +2179,6 @@ extern void winch_daemon(void);
 #define __DATA_H__
 #define __DATA_H__
 
 
 extern DO_COMMAND(do_kill);
 extern DO_COMMAND(do_kill);
-extern DO_COMMAND(do_killall);
-extern DO_COMMAND(do_message);
-extern DO_COMMAND(do_ignore);
-extern DO_COMMAND(do_debug);
-
 
 
 extern void kill_list(struct listroot *root);
 extern void kill_list(struct listroot *root);
 extern void free_list(struct listroot *root);
 extern void free_list(struct listroot *root);
@@ -2428,36 +2261,14 @@ extern void remove_line(struct edit_data *edit, int index);
 
 
 extern DO_COMMAND(do_draw);
 extern DO_COMMAND(do_draw);
 
 
-extern void scale_drawing(struct session *ses, int *top_row, int *top_col, int *bot_row, int *bot_col, int *rows, int *cols, int index, long long flags, char *arg);
-
-extern DO_DRAW(draw_blank);
-extern DO_DRAW(draw_bot_side);
-extern DO_DRAW(draw_arg);
-extern DO_DRAW(draw_box);
-extern DO_DRAW(draw_buffer);
-extern DO_DRAW(draw_corner);
-extern DO_DRAW(draw_horizontal_line);
-extern DO_DRAW(draw_left_side);
-extern DO_DRAW(draw_line);
-extern DO_DRAW(draw_map);
-extern DO_DRAW(draw_right_side);
-extern DO_DRAW(draw_side);
-extern DO_DRAW(draw_square);
-extern DO_DRAW(draw_rain);
-extern DO_DRAW(draw_table_grid);
-extern DO_DRAW(draw_text);
-extern DO_DRAW(draw_top_side);
-//extern DO_DRAW(draw_vertical_line);
-extern DO_DRAW(draw_vertical_lines);
-
 #endif
 #endif
 
 
 
 
 #ifndef __EVENT_H__
 #ifndef __EVENT_H__
 #define __EVENT_H__
 #define __EVENT_H__
 
 
-extern DO_COMMAND(do_event);
-extern DO_COMMAND(do_unevent);
+//extern DO_COMMAND(do_event);
+//extern DO_COMMAND(do_unevent);
 
 
 extern  int check_all_events(struct session *ses, int flags, int args, int vars, char *fmt, ...);
 extern  int check_all_events(struct session *ses, int flags, int args, int vars, char *fmt, ...);
 extern void mouse_handler(struct session *ses, int val1, int val2, int val3);
 extern void mouse_handler(struct session *ses, int val1, int val2, int val3);
@@ -2490,6 +2301,7 @@ extern DO_COMMAND(do_help);
 #define __HISTORY_H__
 #define __HISTORY_H__
 
 
 extern DO_COMMAND(do_history);
 extern DO_COMMAND(do_history);
+
 extern void add_line_history(struct session *ses, char *line);
 extern void add_line_history(struct session *ses, char *line);
 extern void insert_line_history(struct session *ses, char *line);
 extern void insert_line_history(struct session *ses, char *line);
 extern struct session *repeat_history(struct session *ses, char *line);
 extern struct session *repeat_history(struct session *ses, char *line);
@@ -2512,6 +2324,7 @@ DO_HISTORY(history_write);
 #define __LINE_H__
 #define __LINE_H__
 
 
 extern DO_COMMAND(do_line);
 extern DO_COMMAND(do_line);
+
 extern DO_LINE(line_background);
 extern DO_LINE(line_background);
 extern DO_LINE(line_benchmark);
 extern DO_LINE(line_benchmark);
 extern DO_LINE(line_capture);
 extern DO_LINE(line_capture);
@@ -2538,8 +2351,6 @@ extern DO_LINE(line_verbose);
 #ifndef __LOG_H__
 #ifndef __LOG_H__
 #define __LOG_H__
 #define __LOG_H__
 
 
-extern DO_COMMAND(do_log);
-
 DO_LOG(log_append);
 DO_LOG(log_append);
 DO_LOG(log_info);
 DO_LOG(log_info);
 DO_LOG(log_overwrite);
 DO_LOG(log_overwrite);
@@ -2626,20 +2437,9 @@ extern char *str_alloc_stack(int size);
 #ifndef __MISC_H__
 #ifndef __MISC_H__
 #define __MISC_H__
 #define __MISC_H__
 
 
-extern DO_COMMAND(do_all);
-extern DO_COMMAND(do_bell);
-
-extern DO_COMMAND(do_cr);
-extern DO_COMMAND(do_echo);
 extern DO_COMMAND(do_end);
 extern DO_COMMAND(do_end);
-extern DO_COMMAND(do_forall);
-extern DO_COMMAND(do_info);
 extern DO_COMMAND(do_nop);
 extern DO_COMMAND(do_nop);
-extern DO_COMMAND(do_send);
-extern DO_COMMAND(do_snoop);
-extern DO_COMMAND(do_suspend);
 extern DO_COMMAND(do_test);
 extern DO_COMMAND(do_test);
-extern DO_COMMAND(do_zap);
 
 
 #endif
 #endif
 
 
@@ -2691,7 +2491,7 @@ extern struct listnode *get_nest_node_key(struct listroot *root, char *variable,
 extern struct listnode *get_nest_node_val(struct listroot *root, char *variable, char **result, int def);
 extern struct listnode *get_nest_node_val(struct listroot *root, char *variable, char **result, int def);
 extern int get_nest_index(struct listroot *root, char *variable, char **result, int def);
 extern int get_nest_index(struct listroot *root, char *variable, char **result, int def);
 extern void show_nest_node(struct listnode *node, char **result, int initialize);
 extern void show_nest_node(struct listnode *node, char **result, int initialize);
-extern void view_nest_node(struct listnode *node, char **str_result, int nest, int initialize);
+extern void view_nest_node(struct listnode *node, char **str_result, int nest, int initialize, int color);
 extern struct listnode *set_nest_node_ses(struct session *ses, char *arg1, char *format, ...);
 extern struct listnode *set_nest_node_ses(struct session *ses, char *arg1, char *format, ...);
 extern struct listnode *add_nest_node_ses(struct session *ses, char *arg1, char *format, ...);
 extern struct listnode *add_nest_node_ses(struct session *ses, char *arg1, char *format, ...);
 extern struct listnode *set_nest_node(struct listroot *root, char *arg1, char *format, ...);
 extern struct listnode *set_nest_node(struct listroot *root, char *arg1, char *format, ...);
@@ -2751,9 +2551,7 @@ extern void do_one_line(char *line, struct session *ses);
 #ifndef __PATH_H__
 #ifndef __PATH_H__
 #define __PATH_H__
 #define __PATH_H__
 
 
-extern DO_COMMAND(do_path);
 extern DO_COMMAND(do_pathdir);
 extern DO_COMMAND(do_pathdir);
-extern DO_COMMAND(do_unpathdir);
 
 
 int is_pathdir(struct session *ses, char *dir);
 int is_pathdir(struct session *ses, char *dir);
 int exit_to_dir(struct session *ses, char *name);
 int exit_to_dir(struct session *ses, char *name);
@@ -2793,8 +2591,6 @@ extern DO_PATH(path_end);
 #ifndef __PORT_H__
 #ifndef __PORT_H__
 #define __PORT_H__
 #define __PORT_H__
 
 
-
-extern DO_COMMAND(do_port);
 extern DO_PORT(port_call);
 extern DO_PORT(port_call);
 extern DO_PORT(port_color);
 extern DO_PORT(port_color);
 extern DO_PORT(port_flag);
 extern DO_PORT(port_flag);
@@ -2831,51 +2627,11 @@ extern struct port_data *find_port_group(struct session *ses, char *arg);
 
 
 #endif
 #endif
 
 
-#ifndef __SCAN_H__
-#define __SCAN_H__
-
-extern DO_COMMAND(do_scan);
-
-DO_SCAN(scan_abort);
-DO_SCAN(scan_csv);
-DO_SCAN(scan_dir);
-DO_SCAN(scan_file);
-DO_SCAN(scan_forward);
-DO_SCAN(scan_tsv);
-DO_SCAN(scan_txt);
-
-#endif
-
 #ifndef __SCREEN_H__
 #ifndef __SCREEN_H__
 #define __SCREEN_H__
 #define __SCREEN_H__
 
 
 extern DO_COMMAND(do_screen);
 extern DO_COMMAND(do_screen);
 
 
-extern DO_SCREEN(screen_blur);
-extern DO_SCREEN(screen_clear);
-extern DO_SCREEN(screen_cursor);
-extern DO_SCREEN(screen_dump);
-extern DO_SCREEN(screen_fill);
-extern DO_SCREEN(screen_focus);
-extern DO_SCREEN(screen_fullscreen);
-extern DO_SCREEN(screen_get);
-extern DO_SCREEN(screen_info);
-extern DO_SCREEN(screen_inputregion);
-extern DO_SCREEN(screen_load);
-extern DO_SCREEN(screen_maximize);
-extern DO_SCREEN(screen_minimize);
-extern DO_SCREEN(screen_move);
-extern DO_SCREEN(screen_print);
-extern DO_SCREEN(screen_raise);
-extern DO_SCREEN(screen_refresh);
-extern DO_SCREEN(screen_resize);
-extern DO_SCREEN(screen_rescale);
-extern DO_SCREEN(screen_save);
-extern DO_SCREEN(screen_scrollbar);
-extern DO_SCREEN(screen_scrollregion);
-extern DO_SCREEN(screen_set);
-extern DO_SCREEN(screen_swap);
-
 extern void init_inputregion(struct session *ses, int top_row, int top_col, int bot_row, int bot_col);
 extern void init_inputregion(struct session *ses, int top_row, int top_col, int bot_row, int bot_col);
 extern  int get_row_index(struct session *ses, int val);
 extern  int get_row_index(struct session *ses, int val);
 extern  int get_col_index(struct session *ses, int val);
 extern  int get_col_index(struct session *ses, int val);
@@ -2923,6 +2679,9 @@ extern void get_word_screen(char *str, int row, int col);
 #define __SESSION_H__
 #define __SESSION_H__
 
 
 extern DO_COMMAND(do_session);
 extern DO_COMMAND(do_session);
+extern DO_COMMAND(do_snoop);
+extern DO_COMMAND(do_zap);
+
 extern struct session *session_command(char *arg, struct session *ses);
 extern struct session *session_command(char *arg, struct session *ses);
 extern void show_session(struct session *ses, struct session *ptr);
 extern void show_session(struct session *ses, struct session *ptr);
 extern struct session *find_session(char *name);
 extern struct session *find_session(char *name);
@@ -2939,8 +2698,6 @@ extern void dispose_session(struct session *ses);
 #ifndef __SHOW_H__
 #ifndef __SHOW_H__
 #define __SHOW_H__
 #define __SHOW_H__
 
 
-extern DO_COMMAND(do_showme);
-
 extern void show_message(struct session *ses, int index, char *format, ...);
 extern void show_message(struct session *ses, int index, char *format, ...);
 extern void show_error(struct session *ses, int index, char *format, ...);
 extern void show_error(struct session *ses, int index, char *format, ...);
 extern void show_debug(struct session *ses, int index, char *format, ...);
 extern void show_debug(struct session *ses, int index, char *format, ...);
@@ -2988,8 +2745,6 @@ extern void split_show(struct session *ses, char *prompt, char *row, char *col);
 #ifndef __SSL_H__
 #ifndef __SSL_H__
 #define __SSL_H__
 #define __SSL_H__
 
 
-extern DO_COMMAND(do_ssl);
-
 extern gnutls_session_t ssl_negotiate(struct session *ses);
 extern gnutls_session_t ssl_negotiate(struct session *ses);
 
 
 #endif
 #endif
@@ -3036,12 +2791,7 @@ extern int substitute_color(char *input, char *output, int colors);
 #ifndef __SYSTEM_H__
 #ifndef __SYSTEM_H__
 #define __SYSTEM_H__
 #define __SYSTEM_H__
 
 
-
-extern DO_COMMAND(do_run);
-
-extern DO_COMMAND(do_script);
-extern DO_COMMAND(do_system);
-extern DO_COMMAND(do_textin);
+extern DO_COMMAND(do_suspend);
 
 
 #endif
 #endif
 
 
@@ -3049,18 +2799,15 @@ extern DO_COMMAND(do_textin);
 #ifndef __TABLES_H__
 #ifndef __TABLES_H__
 #define __TABLES_H__
 #define __TABLES_H__
 
 
-extern struct array_type array_table[];
 extern struct buffer_type buffer_table[];
 extern struct buffer_type buffer_table[];
 extern struct chat_type chat_table[];
 extern struct chat_type chat_table[];
 extern   char character_table[];
 extern   char character_table[];
-extern struct class_type class_table[];
 extern struct color_type color_table[];
 extern struct color_type color_table[];
 extern struct color_type map_color_table[];
 extern struct color_type map_color_table[];
-//extern struct command_type command_table[];
 extern struct config_type config_table[];
 extern struct config_type config_table[];
 extern struct cursor_type cursor_table[];
 extern struct cursor_type cursor_table[];
 extern struct daemon_type daemon_table[];
 extern struct daemon_type daemon_table[];
-extern struct draw_type draw_table[];
+//extern struct draw_type draw_table[];
 extern struct edit_type edit_table[];
 extern struct edit_type edit_table[];
 extern struct event_type event_table[];
 extern struct event_type event_table[];
 extern struct history_type history_table[];
 extern struct history_type history_table[];
@@ -3071,13 +2818,13 @@ extern struct map_type map_table[];
 extern struct path_type path_table[];
 extern struct path_type path_table[];
 extern struct port_type port_table[];
 extern struct port_type port_table[];
 extern struct rank_type rank_table[];
 extern struct rank_type rank_table[];
-extern struct scan_type scan_table[];
+//extern struct scan_type scan_table[];
 extern struct stamp_type huge_stamp_table[];
 extern struct stamp_type huge_stamp_table[];
 extern struct substitution_type substitution_table[];
 extern struct substitution_type substitution_table[];
 extern struct telopt_type telopt_table[];
 extern struct telopt_type telopt_table[];
 extern   char *telcmds[];
 extern   char *telcmds[];
 extern struct timer_type timer_table[];
 extern struct timer_type timer_table[];
-extern struct screen_type screen_table[];
+//extern struct screen_type screen_table[];
 extern struct map_legend_type map_legend_table[];
 extern struct map_legend_type map_legend_table[];
 extern struct map_legend_group_type map_legend_group_table[];
 extern struct map_legend_group_type map_legend_group_table[];
 
 
@@ -3167,50 +2914,16 @@ extern char *script_viewer(struct session *ses, char *str);
 #ifndef __TRIGGER_H__
 #ifndef __TRIGGER_H__
 #define __TRIGGER_H__
 #define __TRIGGER_H__
 
 
+extern DO_COMMAND(do_delay);
 
 
-DO_COMMAND(do_action);
-DO_COMMAND(do_unaction);
 extern void check_all_actions(struct session *ses, char *original, char *line, char *buf);
 extern void check_all_actions(struct session *ses, char *original, char *line, char *buf);
-
-DO_COMMAND(do_alias);
-DO_COMMAND(do_unalias);
-extern int check_all_aliases(struct session *ses, char *input);
-
-DO_COMMAND(do_button);
-DO_COMMAND(do_unbutton);
+extern  int check_all_aliases(struct session *ses, char *input);
 extern void check_all_buttons(struct session *ses, short row, short col, char *arg1, char *arg2, char *word, char *line);
 extern void check_all_buttons(struct session *ses, short row, short col, char *arg1, char *arg2, char *word, char *line);
-
-extern DO_COMMAND(do_delay);
-extern DO_COMMAND(do_undelay);
-
-extern DO_COMMAND(do_function);
-extern DO_COMMAND(do_unfunction);
-
-extern DO_COMMAND(do_gag);
-extern DO_COMMAND(do_ungag);
 extern void check_all_gags(struct session *ses, char *original, char *line);
 extern void check_all_gags(struct session *ses, char *original, char *line);
-
-extern DO_COMMAND(do_highlight);
-extern DO_COMMAND(do_unhighlight);
 extern void check_all_highlights(struct session *ses, char *original, char *line);
 extern void check_all_highlights(struct session *ses, char *original, char *line);
-
-extern DO_COMMAND(do_macro);
-extern DO_COMMAND(do_unmacro);
-
-extern DO_COMMAND(do_prompt);
-extern DO_COMMAND(do_unprompt);
-extern int check_all_prompts(struct session *ses, char *original, char *line);
-
-extern DO_COMMAND(do_substitute);
-extern DO_COMMAND(do_unsubstitute);
+extern  int check_all_prompts(struct session *ses, char *original, char *line);
 extern void check_all_substitutions(struct session *ses, char *original, char *line);
 extern void check_all_substitutions(struct session *ses, char *original, char *line);
 
 
-extern DO_COMMAND(do_tab);
-extern DO_COMMAND(do_untab);
-
-extern DO_COMMAND(do_tick);
-extern DO_COMMAND(do_untick);
-
 #endif
 #endif
 
 
 // update.c
 // update.c
@@ -3291,14 +3004,6 @@ extern int utf8_to_cp1251(char *input, char *output);
 #ifndef __VARIABLE_H__
 #ifndef __VARIABLE_H__
 #define __VARIABLE_H__
 #define __VARIABLE_H__
 
 
-extern DO_COMMAND(do_variable);
-extern DO_COMMAND(do_unvariable);
-extern DO_COMMAND(do_local);
-extern DO_COMMAND(do_cat);
-extern DO_COMMAND(do_format);
-extern DO_COMMAND(do_replace);
-
-
 extern  int valid_variable(struct session *ses, char *arg);
 extern  int valid_variable(struct session *ses, char *arg);
 extern  int string_raw_str_len(struct session *ses, char *str, int start, int end);
 extern  int string_raw_str_len(struct session *ses, char *str, int start, int end);
 extern  int string_str_raw_len(struct session *ses, char *str, int start, int end);
 extern  int string_str_raw_len(struct session *ses, char *str, int start, int end);

+ 2 - 2
src/tokenize.c

@@ -893,7 +893,7 @@ struct scriptnode *parse_script(struct scriptroot *root, int lvl, struct scriptn
 
 
 				if (*token->data->arg == 0)
 				if (*token->data->arg == 0)
 				{
 				{
-					token->type++;
+//					token->type++;
 
 
 					do
 					do
 					{
 					{
@@ -958,7 +958,7 @@ struct scriptnode *parse_script(struct scriptroot *root, int lvl, struct scriptn
 
 
 					if (*token->data->arg == 0)
 					if (*token->data->arg == 0)
 					{
 					{
-						token->type++;
+//						token->type++;
 
 
 						do
 						do
 						{
 						{

+ 1 - 1
src/update.c

@@ -1016,7 +1016,7 @@ void packet_update(void)
 			{
 			{
 				strcpy(result, ses->more_output);
 				strcpy(result, ses->more_output);
 			}
 			}
-			ses->more_output[0] = 0;
+			str_cpy(&ses->more_output, "");
 
 
 			process_mud_output(ses, result, TRUE);
 			process_mud_output(ses, result, TRUE);
 
 

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 41 - 13
src/utf8.c


+ 1 - 1
src/utils.c

@@ -505,7 +505,7 @@ char *indent(int len)
 
 
 	if (outbuf[len][0] == 0)
 	if (outbuf[len][0] == 0)
 	{
 	{
-		sprintf(outbuf[len], "%*s", len * 5, "");
+		sprintf(outbuf[len], "%*s", len * 4, "");
 	}
 	}
 
 
 	return outbuf[len];
 	return outbuf[len];

+ 55 - 10
src/variable.c

@@ -51,7 +51,7 @@ DO_COMMAND(do_variable)
 
 
 				str_result = str_alloc_stack(0);
 				str_result = str_alloc_stack(0);
 
 
-				view_nest_node(node, &str_result, 0, 1);
+				view_nest_node(node, &str_result, 0, TRUE, TRUE);
 
 
 				print_lines(ses, SUB_NONE, COLOR_TINTIN "%c" COLOR_COMMAND "%s " COLOR_BRACE "{" COLOR_STRING "%s" COLOR_BRACE "}\n{\n" COLOR_STRING "%s" COLOR_BRACE "}" COLOR_RESET "\n", gtd->tintin_char, list_table[LIST_VARIABLE].name, node->arg1, str_result);
 				print_lines(ses, SUB_NONE, COLOR_TINTIN "%c" COLOR_COMMAND "%s " COLOR_BRACE "{" COLOR_STRING "%s" COLOR_BRACE "}\n{\n" COLOR_STRING "%s" COLOR_BRACE "}" COLOR_RESET "\n", gtd->tintin_char, list_table[LIST_VARIABLE].name, node->arg1, str_result);
 			}
 			}
@@ -96,6 +96,27 @@ DO_COMMAND(do_variable)
 	return ses;
 	return ses;
 }
 }
 
 
+DO_COMMAND(do_unvariable)
+{
+	arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
+
+	do
+	{
+		if (delete_nest_node(ses->list[LIST_VARIABLE], arg1))
+		{
+			show_message(ses, LIST_VARIABLE, "#OK. {%s} IS NO LONGER A VARIABLE.", arg1);
+		}
+		else
+		{
+			delete_node_with_wild(ses, LIST_VARIABLE, arg1);
+		}
+		arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
+	}
+	while (*arg1);
+
+	return ses;
+}
+
 DO_COMMAND(do_local)
 DO_COMMAND(do_local)
 {
 {
 	char *str;
 	char *str;
@@ -162,19 +183,41 @@ DO_COMMAND(do_local)
 	return ses;
 	return ses;
 }
 }
 
 
-DO_COMMAND(do_unvariable)
+DO_COMMAND(do_unlocal)
 {
 {
+	struct listroot *root;
+	int index, found;
+
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
 	arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
 
 
+	root = local_list(ses);
+
 	do
 	do
 	{
 	{
-		if (delete_nest_node(ses->list[LIST_VARIABLE], arg1))
+		if (delete_nest_node(root, arg1))
 		{
 		{
-			show_message(ses, LIST_VARIABLE, "#OK. {%s} IS NO LONGER A VARIABLE.", arg1);
+			show_message(ses, LIST_VARIABLE, "#OK. {%s} IS NO LONGER A LOCAL VARIABLE.", arg1);
 		}
 		}
 		else
 		else
 		{
 		{
-			delete_node_with_wild(ses, LIST_VARIABLE, arg1);
+			found = FALSE;
+
+			for (index = root->used - 1 ; index >= 0 ; index--)
+			{
+				if (match(ses, root->list[index]->arg1, arg1, SUB_VAR|SUB_FUN))
+				{
+					show_message(ses, LIST_VARIABLE, "#OK. {%s} IS NO LONGER A LOCAL VARIABLE.", root->list[index]->arg1);
+
+					delete_index_list(root, index);
+
+					found = TRUE;
+				}
+			}
+
+			if (found == 0)
+			{
+				show_message(ses, LIST_VARIABLE, "#UNLOCAL: NO MATCHES FOUND FOR {%s}.", arg1);
+			}
 		}
 		}
 		arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
 		arg = sub_arg_in_braces(ses, arg, arg1, GET_ALL, SUB_VAR|SUB_FUN);
 	}
 	}
@@ -185,7 +228,7 @@ DO_COMMAND(do_unvariable)
 
 
 DO_COMMAND(do_cat)
 DO_COMMAND(do_cat)
 {
 {
-	char *str;
+	char *str, name[BUFFER_SIZE];
 	struct listroot *root;
 	struct listroot *root;
 	struct listnode *node;
 	struct listnode *node;
 
 
@@ -203,17 +246,19 @@ DO_COMMAND(do_cat)
 		{
 		{
 			arg = sub_arg_in_braces(ses, arg, str, GET_ALL, SUB_VAR|SUB_FUN);
 			arg = sub_arg_in_braces(ses, arg, str, GET_ALL, SUB_VAR|SUB_FUN);
 
 
-			node = set_nest_node(ses->list[LIST_VARIABLE], arg1, "%s", str);
+			node = set_nest_node(ses->list[LIST_VARIABLE], arg1, "");
 		}
 		}
 
 
 		root = search_nest_base_ses(ses, arg1);
 		root = search_nest_base_ses(ses, arg1);
 
 
+		get_arg_to_brackets(ses, arg1, name);
+
+		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATE %s", name, name, node->arg2, arg1);
+
 		while (*arg)
 		while (*arg)
 		{
 		{
 			arg = sub_arg_in_braces(ses, arg, str, GET_ALL, SUB_VAR|SUB_FUN);
 			arg = sub_arg_in_braces(ses, arg, str, GET_ALL, SUB_VAR|SUB_FUN);
 
 
-			check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 2, "VARIABLE UPDATE %s", arg1, arg1, str);
-
 			if (*str)
 			if (*str)
 			{
 			{
 				if (node->root)
 				if (node->root)
@@ -227,7 +272,7 @@ DO_COMMAND(do_cat)
 			}
 			}
 		}
 		}
 
 
-		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 1, "VARIABLE UPDATED %s", arg1, arg1, str);
+		check_all_events(ses, EVENT_FLAG_VARIABLE, 1, 3, "VARIABLE UPDATED %s", name, name, node->arg2, arg1);
 
 
 		show_nest_node(node, &str, 1);
 		show_nest_node(node, &str, 1);
 
 

+ 10 - 16
src/vt102.c

@@ -136,16 +136,17 @@ void scroll_region(struct session *ses, int top, int bot)
 {
 {
 	push_call("scroll_region(%p,%d,%d)",ses,top,bot);
 	push_call("scroll_region(%p,%d,%d)",ses,top,bot);
 
 
-	if (top != 1)
-	{
-//		print_stdout(0, 0, "\e[?1047h\e[?1007h\e[?7786h\e[?7787h\e[%d;%dr", top, bot);
-		print_stdout(0, 0, "\e[?1047h\e[?7787h\e[%d;%dr", top, bot);
-	}
-	else
+	if (ses == gtd->ses)
 	{
 	{
-		print_stdout(0, 0, "\e[?1047l\e[?7787l\e[%d;%dr", top, bot);
+		if (top != 1)
+		{
+			print_stdout(0, 0, "\e[?1047h\e[?7787h\e[%d;%dr", top, bot);
+		}
+		else
+		{
+			print_stdout(0, 0, "\e[?1047l\e[?7787l\e[%d;%dr", top, bot);
+		}
 	}
 	}
-
 	ses->split->top_row = top;
 	ses->split->top_row = top;
 	ses->split->bot_row = bot;
 	ses->split->bot_row = bot;
 
 
@@ -159,14 +160,7 @@ void reset_scroll_region(struct session *ses)
 {
 {
 	if (ses == gtd->ses)
 	if (ses == gtd->ses)
 	{
 	{
-		if (ses->split->top_row != 1)
-		{
-			print_stdout(0, 0, "\e[?1047l\e[?7787l\e[r");
-		}
-		else
-		{
-			print_stdout(0, 0, "\e[r");
-		}
+		print_stdout(0, 0, "\e[?1047l\e[?7787l\e[r");
 	}
 	}
 	ses->split->top_row = 1;
 	ses->split->top_row = 1;
 	ses->split->top_col = 1;
 	ses->split->top_col = 1;

برخی فایل ها در این مقایسه diff نمایش داده نمی شوند زیرا تعداد فایل ها بسیار زیاد است