bug-bash
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH] bash-4.2-release-with-unlimited-history-by-crq.diff


From: cheng renquan
Subject: [PATCH] bash-4.2-release-with-unlimited-history-by-crq.diff
Date: Wed, 31 Oct 2012 12:43:50 -0700

just found a patch done by me some months ago, I have been using bash-4.2
with this patch for half a year, should be quite stable; it's mainly to
implement unlimited .bash_history;

1) HISTFILESIZE has a bug that current bash manual saying if HISTFILESIZE
is unset, then HISTFILE will be unlimited, but it seems there is no way to
unset it in bash_profile or any rc file?

2) remove duplicates in HISTFILE also, not just in current history in
memory, we can say this a deep dedup? it only run deep dedup when
HC_ERASEDUPS set,

Not sure if this can be applied to latest trunk code, but I can revamp it
to latest tree if there are interests;

Thanks,


--- bash-4.2.orig/bashhist.c 2010-08-13 18:09:08.000000000 -0700
+++ bash-4.2/bashhist.c 2011-11-02 11:34:36.350166000 -0700
@@ -29,6 +29,8 @@
 #  include <unistd.h>
 #endif

+#include <sys/mman.h>
+
 #include "bashtypes.h"
 #include <stdio.h>
 #include <errno.h>
@@ -281,9 +283,6 @@ load_history ()
   set_if_not ("HISTSIZE", "500");
   sv_histsize ("HISTSIZE");

-  set_if_not ("HISTFILESIZE", get_string_value ("HISTSIZE"));
-  sv_histsize ("HISTFILESIZE");
-
   /* Read the history in HISTFILE into the history list. */
   hf = get_string_value ("HISTFILE");

@@ -345,6 +344,69 @@ bash_delete_last_history ()
   return r;
 }

+int
+erasedups_history (nelements, filename)
+     int nelements;
+     const char *filename;
+{
+  HIST_ENTRY *temp;
+  int r, fd, rv = 0;
+  size_t cursize, mmap_size;
+  char *buffer, *line, *lineend;
+
+  fd = open (filename, O_RDWR);
+
+  if (fd < 0)
+    return errno;
+
+  cursize = lseek (fd, 0, SEEK_END);
+
+  using_history ();
+
+  mmap_size = cursize +1; /* for possibly not newline ending */
+  buffer = mmap (0, mmap_size, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
+  if ((void *)buffer == MAP_FAILED)
+    {
+      rv = errno;
+      close (fd);
+      return rv;
+    }
+
+  line = buffer;
+  while (line < buffer+cursize) {
+    lineend = strchr (line, '\n');
+
+    if (!lineend) { /* last line not newline ending? */
+      lineend = line + strlen(line);
+      *lineend = '\n';
+      buffer[++cursize] = '\0';
+    }
+
+    for (r = 0; (temp = previous_history ()) && r < nelements; r++)
+      if (STREQN (line, temp->line, strlen (temp->line))) {
+ memmove (line, lineend+1, (buffer+cursize) - (lineend+1));
+ cursize -= (lineend+1 - line);
+ buffer[cursize] = '\0';
+ lineend = NULL;
+ break;
+      }
+    using_history ();
+
+    if (lineend)
+      line = lineend+1;
+  }
+
+  if (ftruncate (fd, cursize) == -1)
+    rv = errno;
+  if (!rv && msync (buffer, cursize, 0) == -1)
+    rv = errno;
+  if (!rv && munmap (buffer, mmap_size) == -1)
+    rv = errno;
+  close (fd);
+
+  return rv;
+}
+
 #ifdef INCLUDE_UNUSED
 /* Write the existing history out to the history file. */
 void
@@ -389,9 +451,16 @@ maybe_append_history (filename)
     }
   close (fd);
  }
+      if (history_control & HC_ERASEDUPS)
+ erasedups_history (history_lines_this_session, filename);
       result = append_history (history_lines_this_session, filename);
       history_lines_in_file += history_lines_this_session;
-      history_lines_this_session = 0;
+
+      {
+ char *hf = get_string_value ("HISTFILE");
+ if (hf && *hf && !strcmp(hf, filename))
+  history_lines_this_session = 0;
+      }
     }
   return (result);
 }
@@ -426,6 +495,8 @@ maybe_save_shell_history ()
   using_history ();
   if (history_lines_this_session <= where_history () ||
force_append_history)
     {
+      if (history_control & HC_ERASEDUPS)
+ erasedups_history (history_lines_this_session, hf);
       result = append_history (history_lines_this_session, hf);
       history_lines_in_file += history_lines_this_session;
     }


-- 
Cheng Renquan (程任全)


reply via email to

[Prev in Thread] Current Thread [Next in Thread]