miscellaneous bug fixes, part 2

git-svn-id: svn://svn.savannah.gnu.org/nano/trunk/nano@1331 35c25a1d-7b9e-4130-9fde-d3aeb78583b8
master
David Lawrence Ramsey 2002-12-22 16:30:00 +00:00
parent 334a94049f
commit 9b13ff31bb
14 changed files with 505 additions and 423 deletions

View File

@ -9,9 +9,72 @@ CVS code -
- Minor cosmetic tweaks to the ngettext() macro, and fix to - Minor cosmetic tweaks to the ngettext() macro, and fix to
properly detect systems lacking ngettext() and correctly properly detect systems lacking ngettext() and correctly
compile on them; the previous fix didn't work. (DLR) compile on them; the previous fix didn't work. (DLR)
- Fix problems with some code sections' not being #ifdef'ed out
when they should be, or being #ifdef'ed out improperly. (David
Benbennick and DLR)
- Change FOLLOW_SYMLINKS to NOFOLLOW_SYMLINKS, and rework the
associated logic accordingly, throughout the code. (David
Benbennick)
- Rework #ifdefs to not include mouse_init() at all if
DISABLE_MOUSE is defined or NCURSES_MOUSE_VERSION isn't. (DLR)
- For consistency, change many references of (!x) to (x == NULL)
and (x) to (x != NULL). (DLR)
- Define KEY_IC properly (and KEY_DC more portably) when slang
support is enabled, and remove the hack to work around the
former's not being defined. (David Benbennick and DLR)
- configure.ac: - configure.ac:
- Added tr to ALL_LINGUAS (Jordi). - Added tr to ALL_LINGUAS (Jordi).
- Fix now inaccurate description of --enable-tiny's effects; it
no longer disables NLS support. (DLR)
- Fix typo. (David Benbennick)
- Check for strcasecmp() and strncasecmp(), since they are
apparently only standard under BSD. (DLR)
- cut.c:
do_cut_text()
- Fix a memory corruption problem caused by accessing edittop
after it was freed but before it was reset to a sane value
from current. (David Benbennick)
do_uncut_text()
- If uncutting more than one line of unmarked text at editbot,
don't center the screen, since Pico doesn't. (DLR)
- files.c:
read_line()
- Miscellaneous cleanups. (David Benbennick)
read_file()
- Miscellaneous cleanups. (David Benbennick)
- Fix len's being off by one when reading in Mac-format files,
exposed by one of David Benbennick's cleanups. (DLR)
- If NO_CONVERT isn't set when we first enter, and it gets set
while reading in the file, unset it again afterwards. (DLR)
add_open_file()
- Fix minor logic error when determining when to resave fileage
and filebot. (DLR)
write_file()
- Change lineswritten from a long to an int, to match
filestruct->lineno. (DLR; mismatch found by David Benbennick)
input_tab()
- Variable name change: matchBuf -> matchbuf. (DLR)
diralphasort()
- Remove the HAVE_STRCASECMP #ifdef block; see the changes to
configure.ac and nano.h for why. (DLR)
- move.c:
do_page_down()
- If there's a page or less of text, do an edit_update() if the
mark is on; otherwise, the highlight won't be displayed. (DLR)
- nano.c: - nano.c:
do_prev_word()
- Make the assert match that in do_next_word(). (DLR)
do_enter()
- If smooth scrolling is on, and Enter is pressed on the
magicline, don't center the screen. (DLR)
do_justify()
- Fix memory corruption problem triggered when edittop and
current->next pointed to the same value and current->next was
destroyed during justification. (DLR)
- Center the screen when justification moves the cursor entirely
off the bottom of the screen, instead of when it moves the
cursor near the bottom of the screen, to more closely match
Pico's behavior. (DLR)
version() version()
- Remove obsolete reference to --enable-undo. (David Benbennick) - Remove obsolete reference to --enable-undo. (David Benbennick)
do_int_speller() do_int_speller()
@ -23,7 +86,22 @@ CVS code -
- Programs now return char *, NULL for successful completion, - Programs now return char *, NULL for successful completion,
otherwise the error string to display. This allows us to give otherwise the error string to display. This allows us to give
more useful feedback to the user when spell checking fails. more useful feedback to the user when spell checking fails.
ABCD()
- Renamed abcd(). (DLR)
- nano.h:
- Make sure NO_RCFILE and COLOR_SYNTAX aren't set to the same
value. (DLR; discovered by Ken Tyler)
- If strcasecmp() and/or strncasecmp() aren't available, use
strcmp() and/or strncmp instead. (DLR)
- utils.c:
is_cntrl_char()
- Rework to fix a problem with displaying certain high-bit
characters. (David Benbennick; reported by Andrzej Marecki)
- winio.c: - winio.c:
edit_refresh()
- Miscellaneous cleanups that fix a bug where the screen
isn't updated after uncutting chunks of upwardly marked cut
text that are over a page in length. (David Benbennick)
do_credits() do_credits()
- Add David Benbennick to credits. (DLR) - Add David Benbennick to credits. (DLR)
- nanorc.sample: - nanorc.sample:

View File

@ -84,7 +84,7 @@ void do_colorinit(void)
if (background == -1) if (background == -1)
#ifdef HAVE_USE_DEFAULT_COLORS #ifdef HAVE_USE_DEFAULT_COLORS
if (!defok) if (defok == 0)
#endif #endif
background = COLOR_BLACK; background = COLOR_BLACK;

View File

@ -37,8 +37,7 @@ AC_ARG_ENABLE(extra,
fi]) fi])
AC_ARG_ENABLE(tiny, AC_ARG_ENABLE(tiny,
[ --enable-tiny Disable features for the sake of size [ --enable-tiny Disable features for the sake of size],
(currently disables detailed help and i18n)],
[if test x$enableval = xyes; then [if test x$enableval = xyes; then
AC_DEFINE(NANO_SMALL, 1, [Define this to make the nano executable as small as possible.]) tiny_support=yes AC_DEFINE(NANO_SMALL, 1, [Define this to make the nano executable as small as possible.]) tiny_support=yes
AC_DEFINE(DISABLE_BROWSER, 1, [Define this to disable the built-in (crappy) file browser.]) AC_DEFINE(DISABLE_BROWSER, 1, [Define this to disable the built-in (crappy) file browser.])
@ -223,7 +222,7 @@ AC_MSG_WARN([*** Can not use slang when cross-compiling])),
esac], [AC_MSG_RESULT(no)]) esac], [AC_MSG_RESULT(no)])
dnl Checks for functions dnl Checks for functions
AC_CHECK_FUNCS(snprintf vsnprintf) AC_CHECK_FUNCS(snprintf vsnprintf strcasecmp strncasecmp)
if test "x$ac_cv_func_snprintf" = "xno" -o "xac_cv_func_vsnprintf" = "xno" if test "x$ac_cv_func_snprintf" = "xno" -o "xac_cv_func_vsnprintf" = "xno"
then then
AM_PATH_GLIB(1.2.4,, AM_PATH_GLIB(1.2.4,,
@ -284,7 +283,7 @@ if test x$slang_support != xyes; then
AC_CHECK_LIB([$CURSES_LIB_NAME], wresize, AC_DEFINE(HAVE_WRESIZE, 1, [Define this if you have the wresize function in your ncurses-type library.])) AC_CHECK_LIB([$CURSES_LIB_NAME], wresize, AC_DEFINE(HAVE_WRESIZE, 1, [Define this if you have the wresize function in your ncurses-type library.]))
AC_CHECK_LIB([$CURSES_LIB_NAME], resizeterm, AC_DEFINE(HAVE_RESIZETERM, 1, [Define this if you have the resizeterm function in your ncurses-type library.])) AC_CHECK_LIB([$CURSES_LIB_NAME], resizeterm, AC_DEFINE(HAVE_RESIZETERM, 1, [Define this if you have the resizeterm function in your ncurses-type library.]))
# Taken from aumix (can't tell form the variable name?) # Taken from aumix (can't tell from the variable name?)
AC_CACHE_CHECK([for private member _use_keypad in WINDOW], AC_CACHE_CHECK([for private member _use_keypad in WINDOW],
aumix_cv_struct_window_usekeypad, aumix_cv_struct_window_usekeypad,
[AC_TRY_COMPILE([#ifdef HAVE_NCURSES_H [AC_TRY_COMPILE([#ifdef HAVE_NCURSES_H

33
cut.c
View File

@ -29,7 +29,8 @@
#include "nano.h" #include "nano.h"
static int marked_cut; /* Is the cutbuffer from a mark? */ static int marked_cut; /* Is the cutbuffer from a mark? */
static filestruct *cutbottom = NULL; /* Pointer to end of cutbuffer */ static filestruct *cutbottom = NULL;
/* Pointer to end of cutbuffer */
filestruct *get_cutbottom(void) filestruct *get_cutbottom(void)
{ {
@ -39,7 +40,7 @@ filestruct *get_cutbottom(void)
void add_to_cutbuffer(filestruct *inptr) void add_to_cutbuffer(filestruct *inptr)
{ {
#ifdef DEBUG #ifdef DEBUG
fprintf(stderr, _("add_to_cutbuffer called with inptr->data = %s\n"), fprintf(stderr, _("add_to_cutbuffer() called with inptr->data = %s\n"),
inptr->data); inptr->data);
#endif #endif
@ -57,6 +58,7 @@ void add_to_cutbuffer(filestruct *inptr)
#ifndef NANO_SMALL #ifndef NANO_SMALL
/* Cut a marked segment instead of a whole line. /* Cut a marked segment instead of a whole line.
*
* The first cut character is top->data[top_x]. Unless top == bot, the * The first cut character is top->data[top_x]. Unless top == bot, the
* last cut line has length bot_x. That is, if bot_x > 0 then we cut to * last cut line has length bot_x. That is, if bot_x > 0 then we cut to
* bot->data[bot_x - 1]. * bot->data[bot_x - 1].
@ -121,8 +123,8 @@ void cut_marked_segment(filestruct *top, size_t top_x, filestruct *bot,
} else { } else {
totsize -= bot_x + 1; totsize -= bot_x + 1;
/* Here, the remainder line might get longer, so we realloc /* Here, the remainder line might get longer, so we
it first. */ realloc() it first. */
top->data = (char *)nrealloc(top->data, top->data = (char *)nrealloc(top->data,
sizeof(char) * newsize); sizeof(char) * newsize);
memmove(top->data + top_x, bot->data + bot_x, memmove(top->data + top_x, bot->data + bot_x,
@ -248,12 +250,11 @@ int do_cut_text(void)
UNSET(MARK_ISSET); UNSET(MARK_ISSET);
marked_cut = 1; marked_cut = 1;
set_modified(); if (dontupdate)
if (dontupdate) {
fix_editbot();
edit_refresh(); edit_refresh();
} else else
edit_update(current, CENTER); edit_update(current, CENTER);
set_modified();
return 1; return 1;
} }
@ -291,8 +292,7 @@ int do_cut_text(void)
int do_uncut_text(void) int do_uncut_text(void)
{ {
filestruct *tmp = current, *fileptr = current; filestruct *tmp = current, *fileptr = current;
filestruct *newbuf = NULL; filestruct *newbuf = NULL, *newend = NULL;
filestruct *newend = NULL;
#ifndef NANO_SMALL #ifndef NANO_SMALL
char *tmpstr, *tmpstr2; char *tmpstr, *tmpstr2;
filestruct *hold = current; filestruct *hold = current;
@ -305,7 +305,7 @@ int do_uncut_text(void)
return 0; /* AIEEEEEEEEEEEE */ return 0; /* AIEEEEEEEEEEEE */
#ifndef NANO_SMALL #ifndef NANO_SMALL
if (!marked_cut || cutbuffer->next != NULL) if (marked_cut == 0 || cutbuffer->next != NULL)
#endif #endif
{ {
newbuf = copy_filestruct(cutbuffer); newbuf = copy_filestruct(cutbuffer);
@ -316,7 +316,7 @@ int do_uncut_text(void)
/* Hook newbuf into fileptr */ /* Hook newbuf into fileptr */
#ifndef NANO_SMALL #ifndef NANO_SMALL
if (marked_cut) { if (marked_cut != 0) {
int recenter_me = 0; int recenter_me = 0;
/* Should we eventually use edit_update(CENTER)? */ /* Should we eventually use edit_update(CENTER)? */
@ -329,7 +329,7 @@ int do_uncut_text(void)
memmove(current->data + current_x + buf_len, memmove(current->data + current_x + buf_len,
current->data + current_x, cur_len - current_x + 1); current->data + current_x, cur_len - current_x + 1);
strncpy(current->data + current_x, cutbuffer->data, buf_len); strncpy(current->data + current_x, cutbuffer->data, buf_len);
/* Use strncpy to not copy the terminal '\0'. */ /* Use strncpy() to not copy the terminal '\0'. */
current_x += buf_len; current_x += buf_len;
totsize += buf_len; totsize += buf_len;
@ -398,8 +398,7 @@ int do_uncut_text(void)
if (marked_cut == 2) { if (marked_cut == 2) {
tmp = make_new_node(current); tmp = make_new_node(current);
tmp->data = charalloc(strlen(&current->data[current_x]) + 1); tmp->data = mallocstrcpy(NULL, current->data + current_x);
strcpy(tmp->data, &current->data[current_x]);
splice_node(current, tmp, current->next); splice_node(current, tmp, current->next);
null_at(&current->data, current_x); null_at(&current->data, current_x);
current = current->next; current = current->next;
@ -449,7 +448,9 @@ int do_uncut_text(void)
i = editbot->lineno; i = editbot->lineno;
renumber(newbuf); renumber(newbuf);
if (i < newend->lineno) /* Center the screen if we've moved beyond the line numbers of both
the old and new editbots */
if (i < newend->lineno && editbot->lineno < newend->lineno)
edit_update(fileptr, CENTER); edit_update(fileptr, CENTER);
else else
edit_refresh(); edit_refresh();

305
files.c
View File

@ -80,7 +80,7 @@ void new_file(void)
this new file; without this, if nano is started without a filename this new file; without this, if nano is started without a filename
on the command line, a new file will be created, but it will be on the command line, a new file will be created, but it will be
given no open_files entry */ given no open_files entry */
if (!open_files) { if (open_files == NULL) {
add_open_file(0); add_open_file(0);
/* turn off view mode in this case; this is for consistency /* turn off view mode in this case; this is for consistency
whether multibuffers are compiled in or not */ whether multibuffers are compiled in or not */
@ -100,51 +100,47 @@ void new_file(void)
filestruct *read_line(char *buf, filestruct *prev, int *line1ins, int len) filestruct *read_line(char *buf, filestruct *prev, int *line1ins, int len)
{ {
filestruct *fileptr; filestruct *fileptr = (filestruct *)nmalloc(sizeof(filestruct));
fileptr = nmalloc(sizeof(filestruct));
/* nulls to newlines; len is the string's real length here */ /* nulls to newlines; len is the string's real length here */
unsunder(buf, len); unsunder(buf, len);
fileptr->data = charalloc(strlen(buf) + 2); assert(strlen(buf) == len);
strcpy(fileptr->data, buf);
fileptr->data = mallocstrcpy(NULL, buf);
#ifndef NANO_SMALL #ifndef NANO_SMALL
/* If it's a DOS file (CRLF), and file conversion isn't disabled, /* If it's a DOS file (CRLF), and file conversion isn't disabled,
strip out the CR part */ strip out the CR part */
if (!ISSET(NO_CONVERT) && buf[strlen(buf) - 1] == '\r') { if (!ISSET(NO_CONVERT) && len > 0 && buf[len - 1] == '\r') {
fileptr->data[strlen(buf) - 1] = '\0'; fileptr->data[len - 1] = '\0';
totsize--; totsize--;
if (!fileformat) if (fileformat == 0)
fileformat = 1; fileformat = 1;
} }
#endif #endif
if (*line1ins) { if (*line1ins != 0 || fileage == NULL) {
/* Special case, insert with cursor on 1st line. */ /* Special case, insert with cursor on 1st line. */
fileptr->prev = NULL; fileptr->prev = NULL;
fileptr->next = fileage; fileptr->next = fileage;
fileptr->lineno = 1; fileptr->lineno = 1;
if (*line1ins != 0) {
*line1ins = 0; *line1ins = 0;
/* If we're inserting into the first line of the file, then /* If we're inserting into the first line of the file, then
we want to make sure that our edit buffer stays on the we want to make sure that our edit buffer stays on the
first line (and that fileage stays up to date!) */ first line (and that fileage stays up to date!) */
fileage = fileptr;
edittop = fileptr; edittop = fileptr;
} else if (fileage == NULL) { } else
filebot = fileptr;
fileage = fileptr; fileage = fileptr;
fileage->lineno = 1; } else {
fileage->next = fileage->prev = NULL; assert(prev != NULL);
fileptr = filebot = fileage;
} else if (prev) {
fileptr->prev = prev; fileptr->prev = prev;
fileptr->next = NULL; fileptr->next = NULL;
fileptr->lineno = prev->lineno + 1; fileptr->lineno = prev->lineno + 1;
prev->next = fileptr; prev->next = fileptr;
} else {
die(_("read_line: not on first line and prev is NULL"));
} }
return fileptr; return fileptr;
@ -153,45 +149,44 @@ filestruct *read_line(char *buf, filestruct *prev, int *line1ins, int len)
int read_file(FILE *f, const char *filename, int quiet) int read_file(FILE *f, const char *filename, int quiet)
{ {
int num_lines = 0, len = 0; int num_lines = 0, len = 0;
char input = 0; /* current input character */ char input = '\0'; /* current input character */
char *buf; char *buf;
long i = 0, bufx = 128; long i = 0, bufx = 128;
filestruct *fileptr = current, *tmp = NULL; filestruct *fileptr = current, *tmp = NULL;
#ifndef NANO_SMALL
int old_no_convert = ISSET(NO_CONVERT);
#endif
int line1ins = 0; int line1ins = 0;
int input_int; int input_int;
buf = charalloc(bufx); buf = charalloc(bufx);
buf[0] = '\0'; buf[0] = '\0';
if (fileptr != NULL && fileptr->prev != NULL) { if (current != NULL) {
fileptr = fileptr->prev; if (current == fileage)
tmp = fileptr;
} else if (fileptr != NULL && fileptr->prev == NULL) {
tmp = fileage;
current = fileage;
line1ins = 1; line1ins = 1;
else
fileptr = current->prev;
tmp = fileptr;
} }
/* For the assertion in read_line(), it must be true that if current is
NULL then so is fileage. */
assert(current != NULL || fileage == NULL);
/* Read the entire file into file struct */ /* Read the entire file into file struct */
while ((input_int = getc(f)) != EOF) { while ((input_int = getc(f)) != EOF) {
input = (char)input_int; input = (char)input_int;
#ifndef NANO_SMALL #ifndef NANO_SMALL
if (!ISSET(NO_CONVERT) && is_cntrl_char((int)input)
&& input != '\t' && input != '\r' && input != '\n') {
/* If the file has binary chars in it, don't stupidly /* If the file has binary chars in it, don't stupidly
assume it's a DOS or Mac formatted file! */ assume it's a DOS or Mac formatted file! */
if (!ISSET(NO_CONVERT) && is_cntrl_char((int)input) != 0
&& input != '\t' && input != '\r' && input != '\n')
SET(NO_CONVERT); SET(NO_CONVERT);
}
#endif #endif
/* calculate the total length of the line; it might have nulls in
it, so we can't just use strlen() */
len++;
if (input == '\n') { if (input == '\n') {
/* don't count the newline in the line length */
len--;
/* read in the line properly */ /* read in the line properly */
fileptr = read_line(buf, fileptr, &line1ins, len); fileptr = read_line(buf, fileptr, &line1ins, len);
@ -207,14 +202,13 @@ int read_file(FILE *f, const char *filename, int quiet)
} else if (!ISSET(NO_CONVERT) && i > 0 && buf[i - 1] == '\r') { } else if (!ISSET(NO_CONVERT) && i > 0 && buf[i - 1] == '\r') {
fileformat = 2; fileformat = 2;
/* don't count the newline in the line length */
len--;
/* read in the line properly */ /* read in the line properly */
fileptr = read_line(buf, fileptr, &line1ins, len); fileptr = read_line(buf, fileptr, &line1ins, len);
/* reset the line length, in preparation for the next line */ /* reset the line length, in preparation for the next line;
len = 0; since we've already read in the next character, reset it
to 1 instead of 0 */
len = 1;
num_lines++; num_lines++;
totsize++; totsize++;
@ -223,14 +217,18 @@ int read_file(FILE *f, const char *filename, int quiet)
i = 1; i = 1;
#endif #endif
} else { } else {
/* Calculate the total length of the line; it might have
nulls in it, so we can't just use strlen(). */
len++;
/* Now we allocate a bigger buffer 128 characters at a time. /* Now we allocate a bigger buffer 128 characters at a time.
If we allocate a lot of space for one line, we may indeed If we allocate a lot of space for one line, we may indeed
have to use a buffer this big later on, so we don't have to use a buffer this big later on, so we don't
decrease it at all. We do free it at the end, though. */ decrease it at all. We do free it at the end, though. */
if (i >= bufx - 1) { if (i >= bufx - 1) {
buf = nrealloc(buf, bufx + 128);
bufx += 128; bufx += 128;
buf = nrealloc(buf, bufx);
} }
buf[i] = input; buf[i] = input;
buf[i + 1] = '\0'; buf[i + 1] = '\0';
@ -239,11 +237,11 @@ int read_file(FILE *f, const char *filename, int quiet)
totsize++; totsize++;
} }
if (ferror(f)) { /* This conditional duplicates previous read_byte() behavior;
/* This conditional duplicates previous read_byte(); behavior;
perhaps this could use some better handling. */ perhaps this could use some better handling. */
if (ferror(f))
nperror(filename); nperror(filename);
} fclose(f);
/* Did we not get a newline but still have stuff to do? */ /* Did we not get a newline but still have stuff to do? */
if (len > 0) { if (len > 0) {
@ -251,7 +249,7 @@ int read_file(FILE *f, const char *filename, int quiet)
/* If file conversion isn't disabled, the last character in /* If file conversion isn't disabled, the last character in
this file is a CR and fileformat isn't set yet, make sure this file is a CR and fileformat isn't set yet, make sure
it's set to Mac format */ it's set to Mac format */
if (!ISSET(NO_CONVERT) && buf[len - 1] == '\r' && !fileformat) if (!ISSET(NO_CONVERT) && buf[len - 1] == '\r' && fileformat == 0)
fileformat = 2; fileformat = 2;
#endif #endif
@ -263,11 +261,10 @@ int read_file(FILE *f, const char *filename, int quiet)
buf[0] = '\0'; buf[0] = '\0';
} }
#ifndef NANO_SMALL #ifndef NANO_SMALL
else { else if (!ISSET(NO_CONVERT) && input == '\r') {
/* If file conversion isn't disabled and the last character in /* If file conversion isn't disabled and the last character in
this file is a CR, read it in properly as a (Mac format) this file is a CR, read it in properly as a (Mac format)
line */ line */
if (!ISSET(NO_CONVERT) && input == '\r') {
buf[0] = input; buf[0] = input;
buf[1] = '\0'; buf[1] = '\0';
len = 1; len = 1;
@ -276,7 +273,15 @@ int read_file(FILE *f, const char *filename, int quiet)
totsize++; totsize++;
buf[0] = '\0'; buf[0] = '\0';
} }
} #endif
free(buf);
#ifndef NANO_SMALL
/* If NO_CONVERT wasn't set before we read the file, but it is now,
unset it again. */
if (!old_no_convert && ISSET(NO_CONVERT))
UNSET(NO_CONVERT);
#endif #endif
/* Did we even GET a file if we don't already have one? */ /* Did we even GET a file if we don't already have one? */
@ -315,9 +320,6 @@ int read_file(FILE *f, const char *filename, int quiet)
totlines += num_lines; totlines += num_lines;
free(buf);
fclose(f);
return 1; return 1;
} }
@ -359,7 +361,7 @@ int open_file(const char *filename, int insert, int quiet)
if (!quiet) if (!quiet)
statusbar(_("Reading File")); statusbar(_("Reading File"));
f = fdopen(fd, "rb"); /* Binary for our own line-end munging */ f = fdopen(fd, "rb"); /* Binary for our own line-end munging */
if (!f) { if (f == NULL) {
nperror("fdopen"); nperror("fdopen");
return -1; return -1;
} }
@ -409,17 +411,19 @@ int do_insertfile(int loading_file)
char *realname = NULL; char *realname = NULL;
static char *inspath = NULL; static char *inspath = NULL;
if (inspath == NULL) if (inspath == NULL) {
inspath = mallocstrcpy(inspath, ""); inspath = charalloc(1);
inspath[0] = '\0';
}
wrap_reset(); wrap_reset();
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) #if !defined(DISABLE_BROWSER) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = insertfile_list; currshortcut = insertfile_list;
#endif #endif
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
if (operating_dir && strcmp(operating_dir, ".")) if (operating_dir != NULL && strcmp(operating_dir, ".") != 0)
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
if (ISSET(MULTIBUFFER)) if (ISSET(MULTIBUFFER))
i = statusq(1, insertfile_list, inspath, _("File to insert into new buffer [from %s] "), i = statusq(1, insertfile_list, inspath, _("File to insert into new buffer [from %s] "),
@ -454,7 +458,7 @@ int do_insertfile(int loading_file)
if (i == NANO_TOFILES_KEY) { if (i == NANO_TOFILES_KEY) {
char *tmp = do_browse_from(realname); char *tmp = do_browse_from(realname);
#if !defined(DISABLE_HELP) || !defined(DISABLE_MOUSE) #if !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = insertfile_list; currshortcut = insertfile_list;
#endif #endif
#ifdef DISABLE_TABCOMP #ifdef DISABLE_TABCOMP
@ -469,7 +473,7 @@ int do_insertfile(int loading_file)
#endif #endif
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
if (operating_dir && check_operating_dir(realname, 0)) { if (operating_dir != NULL && check_operating_dir(realname, 0)) {
statusbar(_("Can't insert file from outside of %s"), statusbar(_("Can't insert file from outside of %s"),
operating_dir); operating_dir);
return 0; return 0;
@ -682,11 +686,11 @@ int add_open_file(int update)
{ {
openfilestruct *tmp; openfilestruct *tmp;
if (!fileage || !current || !filename) if (fileage == NULL || current == NULL || filename == NULL)
return 1; return 1;
/* if no entries, make the first one */ /* if no entries, make the first one */
if (!open_files) if (open_files == NULL)
open_files = make_new_opennode(NULL); open_files = make_new_opennode(NULL);
else if (!update) { else if (!update) {
@ -746,7 +750,7 @@ int add_open_file(int update)
/* if we're in view mode and updating, the file contents won't /* if we're in view mode and updating, the file contents won't
have changed, so we won't bother resaving the filestruct have changed, so we won't bother resaving the filestruct
then; otherwise, we will */ then; otherwise, we will */
if (!(ISSET(VIEW_MODE) && !update)) { if (!(ISSET(VIEW_MODE) || !update)) {
/* save current file buffer */ /* save current file buffer */
open_files->fileage = fileage; open_files->fileage = fileage;
open_files->filebot = filebot; open_files->filebot = filebot;
@ -766,7 +770,7 @@ int add_open_file(int update)
*/ */
int load_open_file(void) int load_open_file(void)
{ {
if (!open_files) if (open_files == NULL)
return 1; return 1;
/* set up the filename, the file buffer, the total number of lines in /* set up the filename, the file buffer, the total number of lines in
@ -827,7 +831,7 @@ int load_open_file(void)
*/ */
int open_prevfile(int closing_file) int open_prevfile(int closing_file)
{ {
if (!open_files) if (open_files == NULL)
return 1; return 1;
/* if we're not about to close the current entry, update it before /* if we're not about to close the current entry, update it before
@ -835,7 +839,7 @@ int open_prevfile(int closing_file)
if (!closing_file) if (!closing_file)
add_open_file(1); add_open_file(1);
if (!open_files->prev && !open_files->next) { if (open_files->prev == NULL && open_files->next == NULL) {
/* only one file open */ /* only one file open */
if (!closing_file) if (!closing_file)
@ -843,7 +847,7 @@ int open_prevfile(int closing_file)
return 1; return 1;
} }
if (open_files->prev) { if (open_files->prev != NULL) {
open_files = open_files->prev; open_files = open_files->prev;
#ifdef DEBUG #ifdef DEBUG
@ -852,10 +856,10 @@ int open_prevfile(int closing_file)
} }
else if (open_files->next) { else if (open_files->next != NULL) {
/* if we're at the beginning, wrap around to the end */ /* if we're at the beginning, wrap around to the end */
while (open_files->next) while (open_files->next != NULL)
open_files = open_files->next; open_files = open_files->next;
#ifdef DEBUG #ifdef DEBUG
@ -890,7 +894,7 @@ int open_prevfile_void(void)
*/ */
int open_nextfile(int closing_file) int open_nextfile(int closing_file)
{ {
if (!open_files) if (open_files == NULL)
return 1; return 1;
/* if we're not about to close the current entry, update it before /* if we're not about to close the current entry, update it before
@ -898,7 +902,7 @@ int open_nextfile(int closing_file)
if (!closing_file) if (!closing_file)
add_open_file(1); add_open_file(1);
if (!open_files->prev && !open_files->next) { if (open_files->prev == NULL && open_files->next == NULL) {
/* only one file open */ /* only one file open */
if (!closing_file) if (!closing_file)
@ -906,7 +910,7 @@ int open_nextfile(int closing_file)
return 1; return 1;
} }
if (open_files->next) { if (open_files->next != NULL) {
open_files = open_files->next; open_files = open_files->next;
#ifdef DEBUG #ifdef DEBUG
@ -914,10 +918,10 @@ int open_nextfile(int closing_file)
#endif #endif
} }
else if (open_files->prev) { else if (open_files->prev != NULL) {
/* if we're at the end, wrap around to the beginning */ /* if we're at the end, wrap around to the beginning */
while (open_files->prev) { while (open_files->prev != NULL) {
open_files = open_files->prev; open_files = open_files->prev;
#ifdef DEBUG #ifdef DEBUG
@ -954,7 +958,7 @@ int close_open_file(void)
{ {
openfilestruct *tmp; openfilestruct *tmp;
if (!open_files) if (open_files == NULL)
return 1; return 1;
/* make sure open_files->fileage and fileage, and open_files->filebot /* make sure open_files->fileage and fileage, and open_files->filebot
@ -1003,7 +1007,7 @@ char *get_full_path(const char *origpath)
d_here = getcwd(NULL, 0); d_here = getcwd(NULL, 0);
#endif #endif
if (d_here) { if (d_here != NULL) {
align(&d_here); align(&d_here);
if (strcmp(d_here, "/")) { if (strcmp(d_here, "/")) {
@ -1041,7 +1045,7 @@ char *get_full_path(const char *origpath)
/* if we didn't find one, copy d_here into d_there; all data is /* if we didn't find one, copy d_here into d_there; all data is
then set up */ then set up */
if (!last_slash) if (last_slash == NULL)
d_there = mallocstrcpy(d_there, d_here); d_there = mallocstrcpy(d_there, d_here);
else { else {
/* otherwise, remove all non-path elements from d_there /* otherwise, remove all non-path elements from d_there
@ -1074,7 +1078,7 @@ char *get_full_path(const char *origpath)
#endif #endif
align(&d_there); align(&d_there);
if (d_there) { if (d_there != NULL) {
/* add a slash to d_there, unless it's "/", in which /* add a slash to d_there, unless it's "/", in which
case we don't need it */ case we don't need it */
@ -1130,7 +1134,7 @@ char *check_writable_directory(const char *path)
struct stat fileinfo; struct stat fileinfo;
/* if get_full_path() failed, return NULL */ /* if get_full_path() failed, return NULL */
if (!full_path) if (full_path == NULL)
return NULL; return NULL;
/* otherwise, stat() the full path to see if it's writable by the /* otherwise, stat() the full path to see if it's writable by the
@ -1170,24 +1174,24 @@ char *safe_tempnam(const char *dirname, const char *filename_prefix)
/* if $TMPDIR is set and non-empty, set tempdir to it, run it through /* if $TMPDIR is set and non-empty, set tempdir to it, run it through
get_full_path(), and save the result in full_tempdir; otherwise, get_full_path(), and save the result in full_tempdir; otherwise,
leave full_tempdir set to to NULL */ leave full_tempdir set to NULL */
TMPDIR_env = getenv("TMPDIR"); TMPDIR_env = getenv("TMPDIR");
if (TMPDIR_env && TMPDIR_env[0] != '\0') if (TMPDIR_env != NULL && TMPDIR_env[0] != '\0')
full_tempdir = check_writable_directory(TMPDIR_env); full_tempdir = check_writable_directory(TMPDIR_env);
/* if $TMPDIR is blank or isn't set, or isn't a writable /* if $TMPDIR is blank or isn't set, or isn't a writable
directory, and dirname isn't NULL, try it; otherwise, leave directory, and dirname isn't NULL, try it; otherwise, leave
full_tempdir set to NULL */ full_tempdir set to NULL */
if (!full_tempdir && dirname) if (full_tempdir == NULL && dirname != NULL)
full_tempdir = check_writable_directory(dirname); full_tempdir = check_writable_directory(dirname);
/* if $TMPDIR is blank or isn't set, or if it isn't a writable /* if $TMPDIR is blank or isn't set, or if it isn't a writable
directory, and dirname is NULL, try P_tmpdir instead */ directory, and dirname is NULL, try P_tmpdir instead */
if (!full_tempdir) if (full_tempdir == NULL)
full_tempdir = check_writable_directory(P_tmpdir); full_tempdir = check_writable_directory(P_tmpdir);
/* if P_tmpdir didn't work, use /tmp instead */ /* if P_tmpdir didn't work, use /tmp instead */
if (!full_tempdir) { if (full_tempdir == NULL) {
full_tempdir = charalloc(6); full_tempdir = charalloc(6);
strcpy(full_tempdir, "/tmp/"); strcpy(full_tempdir, "/tmp/");
} }
@ -1219,13 +1223,13 @@ void init_operating_dir(void)
{ {
assert(full_operating_dir == NULL); assert(full_operating_dir == NULL);
if (!operating_dir) if (operating_dir == NULL)
return; return;
full_operating_dir = get_full_path(operating_dir); full_operating_dir = get_full_path(operating_dir);
/* If get_full_path() failed or the operating directory is /* If get_full_path() failed or the operating directory is
inaccessible, unset operating_dir. */ inaccessible, unset operating_dir. */
if (!full_operating_dir || chdir(full_operating_dir) == -1) { if (full_operating_dir == NULL || chdir(full_operating_dir) == -1) {
free(full_operating_dir); free(full_operating_dir);
full_operating_dir = NULL; full_operating_dir = NULL;
free(operating_dir); free(operating_dir);
@ -1251,11 +1255,11 @@ int check_operating_dir(const char *currpath, int allow_tabcomp)
const char *whereami1, *whereami2 = NULL; const char *whereami1, *whereami2 = NULL;
/* if no operating directory is set, don't bother doing anything */ /* if no operating directory is set, don't bother doing anything */
if (!operating_dir) if (operating_dir == NULL)
return 0; return 0;
fullpath = get_full_path(currpath); fullpath = get_full_path(currpath);
if (!fullpath) if (fullpath == NULL)
return 1; return 1;
whereami1 = strstr(fullpath, full_operating_dir); whereami1 = strstr(fullpath, full_operating_dir);
@ -1288,14 +1292,15 @@ int check_operating_dir(const char *currpath, int allow_tabcomp)
* append == 2 means we are prepending instead of overwriting. * append == 2 means we are prepending instead of overwriting.
* *
* nonamechange means don't change the current filename, it is ignored * nonamechange means don't change the current filename, it is ignored
* if tmp == 1 or if we're appending/prepending. * if tmp is nonzero or if we're appending/prepending.
*/ */
int write_file(const char *name, int tmp, int append, int nonamechange) int write_file(const char *name, int tmp, int append, int nonamechange)
{ {
int retval = -1; int retval = -1;
/* Instead of returning in this function, you should always /* Instead of returning in this function, you should always
* merely set retval then goto cleanup_and_exit. */ * merely set retval then goto cleanup_and_exit. */
long size, lineswritten = 0; long size;
int lineswritten = 0;
char *buf = NULL; char *buf = NULL;
const filestruct *fileptr; const filestruct *fileptr;
FILE *f; FILE *f;
@ -1320,7 +1325,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
/* If we're writing a temporary file, we're probably going outside /* If we're writing a temporary file, we're probably going outside
the operating directory, so skip the operating directory test. */ the operating directory, so skip the operating directory test. */
if (!tmp && operating_dir && check_operating_dir(realname, 0)) { if (!tmp && operating_dir != NULL && check_operating_dir(realname, 0)) {
statusbar(_("Can't write outside of %s"), operating_dir); statusbar(_("Can't write outside of %s"), operating_dir);
goto cleanup_and_exit; goto cleanup_and_exit;
} }
@ -1337,7 +1342,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
the file has not been modified by someone else since nano opened the file has not been modified by someone else since nano opened
it. */ it. */
if (ISSET(BACKUP_FILE) && !tmp && realexists == 0 && if (ISSET(BACKUP_FILE) && !tmp && realexists == 0 &&
(append || ISSET(MARK_ISSET) || (append != 0 || ISSET(MARK_ISSET) ||
originalfilestat.st_mtime == st.st_mtime)) { originalfilestat.st_mtime == st.st_mtime)) {
FILE *backup_file; FILE *backup_file;
char *backupname = NULL; char *backupname = NULL;
@ -1351,7 +1356,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
/* open the original file to copy to the backup */ /* open the original file to copy to the backup */
f = fopen(realname, "rb"); f = fopen(realname, "rb");
if (!f) { if (f == NULL) {
statusbar(_("Could not read %s for backup: %s"), realname, statusbar(_("Could not read %s for backup: %s"), realname,
strerror(errno)); strerror(errno));
return -1; return -1;
@ -1362,7 +1367,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
/* get a file descriptor for the destination backup file */ /* get a file descriptor for the destination backup file */
backup_file = fopen(backupname, "wb"); backup_file = fopen(backupname, "wb");
if (!backup_file) { if (backup_file == NULL) {
statusbar(_("Couldn't write backup: %s"), strerror(errno)); statusbar(_("Couldn't write backup: %s"), strerror(errno));
free(backupname); free(backupname);
return -1; return -1;
@ -1407,14 +1412,14 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
goto cleanup_and_exit; goto cleanup_and_exit;
/* NOTE: If you change this statement, you MUST CHANGE the if /* NOTE: If you change this statement, you MUST CHANGE the if
statement below (that says: statement below (that says:
if (realexists == -1 || tmp || (!ISSET(FOLLOW_SYMLINKS) && if (realexists == -1 || tmp || (ISSET(NOFOLLOW_SYMLINKS) &&
S_ISLNK(lst.st_mode))) { S_ISLNK(lst.st_mode))) {
to reflect whether or not to link/unlink/rename the file */ to reflect whether or not to link/unlink/rename the file */
else if (append != 2 && (ISSET(FOLLOW_SYMLINKS) || !S_ISLNK(lst.st_mode) else if (append != 2 && (!ISSET(NOFOLLOW_SYMLINKS) || !S_ISLNK(lst.st_mode)
|| tmp)) { || tmp)) {
/* Use O_EXCL if tmp == 1. This is now copied from joe, because /* Use O_EXCL if tmp is nonzero. This is now copied from joe,
wiggy says so *shrug*. */ because wiggy says so *shrug*. */
if (append) if (append != 0)
fd = open(realname, O_WRONLY | O_CREAT | O_APPEND, (S_IRUSR|S_IWUSR)); fd = open(realname, O_WRONLY | O_CREAT | O_APPEND, (S_IRUSR|S_IWUSR));
else if (tmp) else if (tmp)
fd = open(realname, O_WRONLY | O_CREAT | O_EXCL, (S_IRUSR|S_IWUSR)); fd = open(realname, O_WRONLY | O_CREAT | O_EXCL, (S_IRUSR|S_IWUSR));
@ -1454,7 +1459,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
#endif #endif
f = fdopen(fd, append == 1 ? "ab" : "wb"); f = fdopen(fd, append == 1 ? "ab" : "wb");
if (!f) { if (f == NULL) {
statusbar(_("Could not open file for writing: %s"), strerror(errno)); statusbar(_("Could not open file for writing: %s"), strerror(errno));
goto cleanup_and_exit; goto cleanup_and_exit;
} }
@ -1539,7 +1544,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
} }
} }
if (fclose(f)) { if (fclose(f) != 0) {
statusbar(_("Could not close %s: %s"), realname, strerror(errno)); statusbar(_("Could not close %s: %s"), realname, strerror(errno));
unlink(buf); unlink(buf);
goto cleanup_and_exit; goto cleanup_and_exit;
@ -1556,7 +1561,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
goto cleanup_and_exit; goto cleanup_and_exit;
} }
f_dest = fdopen(fd_dest, "wb"); f_dest = fdopen(fd_dest, "wb");
if (!f_dest) { if (f_dest == NULL) {
statusbar(_("Could not reopen %s: %s"), buf, strerror(errno)); statusbar(_("Could not reopen %s: %s"), buf, strerror(errno));
close(fd_dest); close(fd_dest);
goto cleanup_and_exit; goto cleanup_and_exit;
@ -1567,7 +1572,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
goto cleanup_and_exit; goto cleanup_and_exit;
} }
f_source = fdopen(fd_source, "rb"); f_source = fdopen(fd_source, "rb");
if (!f_source) { if (f_source == NULL) {
statusbar(_("Could not open %s for prepend: %s"), realname, strerror(errno)); statusbar(_("Could not open %s for prepend: %s"), realname, strerror(errno));
fclose(f_dest); fclose(f_dest);
close(fd_source); close(fd_source);
@ -1596,7 +1601,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
} }
if (realexists == -1 || tmp || if (realexists == -1 || tmp ||
(!ISSET(FOLLOW_SYMLINKS) && S_ISLNK(lst.st_mode))) { (ISSET(NOFOLLOW_SYMLINKS) && S_ISLNK(lst.st_mode))) {
/* Use default umask as file permissions if file is a new file. */ /* Use default umask as file permissions if file is a new file. */
mask = umask(0); mask = umask(0);
@ -1611,7 +1616,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
mask = st.st_mode; mask = st.st_mode;
if (append == 2 || if (append == 2 ||
(!tmp && (!ISSET(FOLLOW_SYMLINKS) && S_ISLNK(lst.st_mode)))) { (!tmp && (ISSET(NOFOLLOW_SYMLINKS) && S_ISLNK(lst.st_mode)))) {
if (unlink(realname) == -1) { if (unlink(realname) == -1) {
if (errno != ENOENT) { if (errno != ENOENT) {
statusbar(_("Could not open %s for writing: %s"), statusbar(_("Could not open %s for writing: %s"),
@ -1638,7 +1643,7 @@ int write_file(const char *name, int tmp, int append, int nonamechange)
statusbar(_("Could not set permissions %o on %s: %s"), statusbar(_("Could not set permissions %o on %s: %s"),
mask, realname, strerror(errno)); mask, realname, strerror(errno));
if (!tmp && !append) { if (!tmp && append == 0) {
if (!nonamechange) if (!nonamechange)
filename = mallocstrcpy(filename, realname); filename = mallocstrcpy(filename, realname);
@ -1667,14 +1672,14 @@ int do_writeout(const char *path, int exiting, int append)
static int did_cred = 0; static int did_cred = 0;
#endif #endif
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) #if !defined(DISABLE_BROWSER) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = writefile_list; currshortcut = writefile_list;
#endif #endif
answer = mallocstrcpy(answer, path); answer = mallocstrcpy(answer, path);
if (exiting && ISSET(TEMP_OPT)) { if (exiting && ISSET(TEMP_OPT)) {
if (filename[0]) { if (filename[0] != '\0') {
i = write_file(answer, 0, 0, 0); i = write_file(answer, 0, 0, 0);
display_main_list(); display_main_list();
return i; return i;
@ -1708,7 +1713,7 @@ int do_writeout(const char *path, int exiting, int append)
if (append == 2) if (append == 2)
i = statusq(1, writefile_list, "", i = statusq(1, writefile_list, "",
"%s%s%s", _("Prepend Selection to File"), formatstr, backupstr); "%s%s%s", _("Prepend Selection to File"), formatstr, backupstr);
else if (append) else if (append == 1)
i = statusq(1, writefile_list, "", i = statusq(1, writefile_list, "",
"%s%s%s", _("Append Selection to File"), formatstr, backupstr); "%s%s%s", _("Append Selection to File"), formatstr, backupstr);
else else
@ -1718,7 +1723,7 @@ int do_writeout(const char *path, int exiting, int append)
if (append == 2) if (append == 2)
i = statusq(1, writefile_list, answer, i = statusq(1, writefile_list, answer,
"%s%s%s", _("File Name to Prepend to"), formatstr, backupstr); "%s%s%s", _("File Name to Prepend to"), formatstr, backupstr);
else if (append) else if (append == 1)
i = statusq(1, writefile_list, answer, i = statusq(1, writefile_list, answer,
"%s%s%s", _("File Name to Append to"), formatstr, backupstr); "%s%s%s", _("File Name to Append to"), formatstr, backupstr);
else else
@ -1729,7 +1734,7 @@ int do_writeout(const char *path, int exiting, int append)
if (append == 2) if (append == 2)
i = statusq(1, writefile_list, answer, i = statusq(1, writefile_list, answer,
"%s", _("File Name to Prepend to")); "%s", _("File Name to Prepend to"));
else if (append) else if (append == 1)
i = statusq(1, writefile_list, answer, i = statusq(1, writefile_list, answer,
"%s", _("File Name to Append to")); "%s", _("File Name to Append to"));
else else
@ -1788,7 +1793,7 @@ int do_writeout(const char *path, int exiting, int append)
return -1; return -1;
} }
#endif #endif
if (!append && strcmp(answer, filename)) { if (append == 0 && strcmp(answer, filename) != 0) {
struct stat st; struct stat st;
if (!stat(answer, &st)) { if (!stat(answer, &st)) {
@ -1916,8 +1921,8 @@ int append_slash_if_dir(char *buf, int *lastwastab, int *place)
/* /*
* These functions (username_tab_completion, cwd_tab_completion, and * These functions (username_tab_completion, cwd_tab_completion, and
* input_tab were taken from busybox 0.46 (cmdedit.c). Here is the notice * input_tab) were taken from busybox 0.46 (cmdedit.c). Here is the
* from that file: * notice from that file:
* *
* Termios command line History and Editting, originally * Termios command line History and Editting, originally
* intended for NetBSD sh (ash) * intended for NetBSD sh (ash)
@ -1956,8 +1961,8 @@ char **username_tab_completion(char *buf, int *num_matches)
/* ...unless the match exists outside the operating /* ...unless the match exists outside the operating
directory, in which case just go to the next match */ directory, in which case just go to the next match */
if (operating_dir) { if (operating_dir != NULL) {
if (check_operating_dir(userdata->pw_dir, 1)) if (check_operating_dir(userdata->pw_dir, 1) != 0)
continue; continue;
} }
#endif #endif
@ -1974,7 +1979,7 @@ char **username_tab_completion(char *buf, int *num_matches)
} }
endpwent(); endpwent();
return (matches); return matches;
} }
/* This was originally called exe_n_cwd_tab_completion, but we're not /* This was originally called exe_n_cwd_tab_completion, but we're not
@ -1993,7 +1998,7 @@ char **cwd_tab_completion(char *buf, int *num_matches)
strcat(buf, "*"); strcat(buf, "*");
/* Okie, if there's a / in the buffer, strip out the directory part */ /* Okie, if there's a / in the buffer, strip out the directory part */
if (buf[0] != '\0' && strstr(buf, "/")) { if (buf[0] != '\0' && strstr(buf, "/") != NULL) {
dirname = charalloc(strlen(buf) + 1); dirname = charalloc(strlen(buf) + 1);
tmp = buf + strlen(buf); tmp = buf + strlen(buf);
while (*tmp != '/' && tmp != buf) while (*tmp != '/' && tmp != buf)
@ -2035,11 +2040,11 @@ char **cwd_tab_completion(char *buf, int *num_matches)
dir = opendir(dirname); dir = opendir(dirname);
if (!dir) { if (dir == NULL) {
/* Don't print an error, just shut up and return */ /* Don't print an error, just shut up and return */
*num_matches = 0; *num_matches = 0;
beep(); beep();
return (matches); return matches;
} }
while ((next = readdir(dir)) != NULL) { while ((next = readdir(dir)) != NULL) {
@ -2060,7 +2065,7 @@ char **cwd_tab_completion(char *buf, int *num_matches)
directory name to the beginning of the proposed match directory name to the beginning of the proposed match
before we check it */ before we check it */
if (operating_dir) { if (operating_dir != NULL) {
tmp2 = charalloc(strlen(dirname) + strlen(next->d_name) + 2); tmp2 = charalloc(strlen(dirname) + strlen(next->d_name) + 2);
strcpy(tmp2, dirname); strcpy(tmp2, dirname);
strcat(tmp2, "/"); strcat(tmp2, "/");
@ -2085,7 +2090,7 @@ char **cwd_tab_completion(char *buf, int *num_matches)
} }
} }
return (matches); return matches;
} }
/* This function now has an arg which refers to how much the /* This function now has an arg which refers to how much the
@ -2103,17 +2108,17 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
*list = 0; *list = 0;
if (*lastwastab == FALSE) { if (*lastwastab == FALSE) {
char *tmp, *copyto, *matchBuf; char *tmp, *copyto, *matchbuf;
*lastwastab = 1; *lastwastab = 1;
/* Make a local copy of the string -- up to the position of the /* Make a local copy of the string -- up to the position of the
cursor */ cursor */
matchBuf = (char *) nmalloc((strlen(buf) + 2) * sizeof(char)); matchbuf = (char *)nmalloc((strlen(buf) + 2) * sizeof(char));
memset(matchBuf, '\0', (strlen(buf) + 2)); memset(matchbuf, '\0', (strlen(buf) + 2));
strncpy(matchBuf, buf, place); strncpy(matchbuf, buf, place);
tmp = matchBuf; tmp = matchbuf;
/* skip any leading white space */ /* skip any leading white space */
while (*tmp && isspace((int)*tmp)) while (*tmp && isspace((int)*tmp))
@ -2136,7 +2141,7 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
the part we're tab-completing into buf, so tab completion the part we're tab-completing into buf, so tab completion
will result in buf's containing only the tab-completed will result in buf's containing only the tab-completed
username. */ username. */
if (buf[0] == '~' && !strchr(tmp, '/')) { if (buf[0] == '~' && strchr(tmp, '/') == NULL) {
buf = mallocstrcpy(buf, tmp); buf = mallocstrcpy(buf, tmp);
matches = username_tab_completion(tmp, &num_matches); matches = username_tab_completion(tmp, &num_matches);
} }
@ -2149,11 +2154,11 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
/* Try to match everything in the current working directory that /* Try to match everything in the current working directory that
* matches. */ * matches. */
if (!matches) if (matches == NULL)
matches = cwd_tab_completion(tmp, &num_matches); matches = cwd_tab_completion(tmp, &num_matches);
/* Don't leak memory */ /* Don't leak memory */
free(matchBuf); free(matchbuf);
#ifdef DEBUG #ifdef DEBUG
fprintf(stderr, "%d matches found...\n", num_matches); fprintf(stderr, "%d matches found...\n", num_matches);
@ -2168,7 +2173,7 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
buf = nrealloc(buf, strlen(buf) + strlen(matches[0]) + 1); buf = nrealloc(buf, strlen(buf) + strlen(matches[0]) + 1);
if (buf[0] != '\0' && strstr(buf, "/")) { if (buf[0] != '\0' && strstr(buf, "/") != NULL) {
for (tmp = buf + strlen(buf); *tmp != '/' && tmp != buf; for (tmp = buf + strlen(buf); *tmp != '/' && tmp != buf;
tmp--); tmp--);
tmp++; tmp++;
@ -2178,7 +2183,7 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
if (!strcmp(tmp, matches[0])) if (!strcmp(tmp, matches[0]))
is_dir = append_slash_if_dir(buf, lastwastab, newplace); is_dir = append_slash_if_dir(buf, lastwastab, newplace);
if (is_dir) if (is_dir != 0)
break; break;
copyto = tmp; copyto = tmp;
@ -2205,14 +2210,14 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
/* Check to see if all matches share a beginning, and, if so, /* Check to see if all matches share a beginning, and, if so,
tack it onto buf and then beep */ tack it onto buf and then beep */
if (buf[0] != '\0' && strstr(buf, "/")) { if (buf[0] != '\0' && strstr(buf, "/") != NULL) {
for (tmp = buf + strlen(buf); *tmp != '/' && tmp != buf; for (tmp = buf + strlen(buf); *tmp != '/' && tmp != buf;
tmp--); tmp--);
tmp++; tmp++;
} else } else
tmp = buf; tmp = buf;
for (pos = 0; *tmp == matches[0][pos] && *tmp != 0 && for (pos = 0; *tmp == matches[0][pos] && *tmp != '\0' &&
pos <= strlen(matches[0]); pos++) pos <= strlen(matches[0]); pos++)
tmp++; tmp++;
@ -2244,7 +2249,7 @@ char *input_tab(char *buf, int place, int *lastwastab, int *newplace, int *list)
/* Ok -- the last char was a TAB. Since they /* Ok -- the last char was a TAB. Since they
* just hit TAB again, print a list of all the * just hit TAB again, print a list of all the
* available choices... */ * available choices... */
if (matches && num_matches > 1) { if (matches != NULL && num_matches > 1) {
/* Blank the edit window, and print the matches out there */ /* Blank the edit window, and print the matches out there */
blank_edit(); blank_edit();
@ -2327,16 +2332,12 @@ int diralphasort(const void *va, const void *vb)
int aisdir = stat(a, &fileinfo) != -1 && S_ISDIR(fileinfo.st_mode); int aisdir = stat(a, &fileinfo) != -1 && S_ISDIR(fileinfo.st_mode);
int bisdir = stat(b, &fileinfo) != -1 && S_ISDIR(fileinfo.st_mode); int bisdir = stat(b, &fileinfo) != -1 && S_ISDIR(fileinfo.st_mode);
if (aisdir && !bisdir) if (aisdir != 0 && bisdir == 0)
return -1; return -1;
if (!aisdir && bisdir) if (aisdir == 0 && bisdir != 0)
return 1; return 1;
#ifdef HAVE_STRCASECMP
return strcasecmp(a, b); return strcasecmp(a, b);
#else
return strcmp(a, b);
#endif
} }
/* Free our malloc()ed memory */ /* Free our malloc()ed memory */
@ -2397,7 +2398,7 @@ char **browser_init(const char *path, int *longest, int *numents)
size_t path_len; size_t path_len;
dir = opendir(path); dir = opendir(path);
if (!dir) if (dir == NULL)
return NULL; return NULL;
*numents = 0; *numents = 0;
@ -2442,10 +2443,8 @@ char *do_browser(const char *inpath)
int col = 0, selected = 0, editline = 0, width = 0, filecols = 0; int col = 0, selected = 0, editline = 0, width = 0, filecols = 0;
int lineno = 0, kb; int lineno = 0, kb;
char **filelist = (char **)NULL; char **filelist = (char **)NULL;
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
MEVENT mevent; MEVENT mevent;
#endif
#endif #endif
assert(inpath != NULL); assert(inpath != NULL);
@ -2483,7 +2482,7 @@ char *do_browser(const char *inpath)
blank_statusbar_refresh(); blank_statusbar_refresh();
#if !defined(DISABLE_HELP) || !defined(DISABLE_MOUSE) #if !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = browser_list; currshortcut = browser_list;
#endif #endif
@ -2497,8 +2496,7 @@ char *do_browser(const char *inpath)
switch (kbinput) { switch (kbinput) {
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
case KEY_MOUSE: case KEY_MOUSE:
if (getmouse(&mevent) == ERR) if (getmouse(&mevent) == ERR)
return retval; return retval;
@ -2530,7 +2528,6 @@ char *do_browser(const char *inpath)
do_mouse(); do_mouse();
break; break;
#endif
#endif #endif
case NANO_UP_KEY: case NANO_UP_KEY:
case KEY_UP: case KEY_UP:
@ -2595,7 +2592,7 @@ char *do_browser(const char *inpath)
/* Note: The case of the user's being completely outside the /* Note: The case of the user's being completely outside the
operating directory is handled elsewhere, before this operating directory is handled elsewhere, before this
point */ point */
if (operating_dir) { if (operating_dir != NULL) {
if (check_operating_dir(path, 0)) { if (check_operating_dir(path, 0)) {
statusbar(_("Can't visit parent in restricted mode")); statusbar(_("Can't visit parent in restricted mode"));
beep(); beep();
@ -2658,7 +2655,7 @@ char *do_browser(const char *inpath)
curs_set(0); curs_set(0);
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
if (operating_dir) { if (operating_dir != NULL) {
if (check_operating_dir(answer, 0)) { if (check_operating_dir(answer, 0)) {
statusbar(_("Can't go outside of %s in restricted mode"), operating_dir); statusbar(_("Can't go outside of %s in restricted mode"), operating_dir);
break; break;
@ -2705,7 +2702,7 @@ char *do_browser(const char *inpath)
blank_edit(); blank_edit();
if (width) if (width != 0)
i = width * editwinrows * ((selected / width) / editwinrows); i = width * editwinrows * ((selected / width) / editwinrows);
else else
i = 0; i = 0;
@ -2744,7 +2741,7 @@ char *do_browser(const char *inpath)
else if (st.st_size >= (1 << 20)) /* at least 1 meg */ else if (st.st_size >= (1 << 20)) /* at least 1 meg */
sprintf(foo + longest - 7, "%4d MB", sprintf(foo + longest - 7, "%4d MB",
(int) st.st_size >> 20); (int) st.st_size >> 20);
else /* Its more than 1 k and less than a meg */ else /* It's more than 1 k and less than a meg */
sprintf(foo + longest - 7, "%4d KB", sprintf(foo + longest - 7, "%4d KB",
(int) st.st_size >> 10); (int) st.st_size >> 10);
} }
@ -2800,12 +2797,12 @@ char *do_browse_from(const char *inpath)
char *from = getcwd(NULL, 0); char *from = getcwd(NULL, 0);
#endif #endif
bob = do_browser(from ? from : "./"); bob = do_browser(from != NULL ? from : "./");
free(from); free(from);
return bob; return bob;
} }
/* If the string is a directory, pass do_browser that */ /* If the string is a directory, pass do_browser() that */
st = filestat(inpath); st = filestat(inpath);
if (S_ISDIR(st.st_mode)) if (S_ISDIR(st.st_mode))
return do_browser(inpath); return do_browser(inpath);

View File

@ -111,9 +111,11 @@ shortcut *writefile_list = NULL;
shortcut *insertfile_list = NULL; shortcut *insertfile_list = NULL;
shortcut *help_list = NULL; shortcut *help_list = NULL;
shortcut *spell_list = NULL; shortcut *spell_list = NULL;
#ifndef NANO_SMALL #ifndef NANO_SMALL
shortcut *extcmd_list = NULL; shortcut *extcmd_list = NULL;
#endif #endif
#ifndef DISABLE_BROWSER #ifndef DISABLE_BROWSER
shortcut *browser_list = NULL; shortcut *browser_list = NULL;
#endif #endif
@ -124,7 +126,7 @@ shortcut *browser_list = NULL;
char *syntaxstr = NULL; char *syntaxstr = NULL;
#endif #endif
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) || !defined(DISABLE_HELP) #if !defined(DISABLE_BROWSER) || !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
const shortcut *currshortcut; /* Current shortcut list we're using */ const shortcut *currshortcut; /* Current shortcut list we're using */
#endif #endif
@ -207,9 +209,12 @@ void toggle_init_one(int val, const char *desc, int flag)
void toggle_init(void) void toggle_init(void)
{ {
char *toggle_const_msg, *toggle_autoindent_msg, *toggle_suspend_msg, char *toggle_const_msg, *toggle_autoindent_msg, *toggle_suspend_msg,
*toggle_nohelp_msg, *toggle_picomode_msg, *toggle_mouse_msg, *toggle_nohelp_msg, *toggle_picomode_msg, *toggle_cuttoend_msg,
*toggle_cuttoend_msg, *toggle_noconvert_msg, *toggle_dos_msg, *toggle_noconvert_msg, *toggle_dos_msg, *toggle_mac_msg,
*toggle_mac_msg, *toggle_backup_msg, *toggle_smooth_msg; *toggle_backup_msg, *toggle_smooth_msg;
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
char *toggle_mouse_msg;
#endif
#ifndef DISABLE_WRAPPING #ifndef DISABLE_WRAPPING
char *toggle_wrap_msg; char *toggle_wrap_msg;
#endif #endif
@ -232,7 +237,9 @@ void toggle_init(void)
toggle_suspend_msg = _("Suspend"); toggle_suspend_msg = _("Suspend");
toggle_nohelp_msg = _("Help mode"); toggle_nohelp_msg = _("Help mode");
toggle_picomode_msg = _("Pico mode"); toggle_picomode_msg = _("Pico mode");
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
toggle_mouse_msg = _("Mouse support"); toggle_mouse_msg = _("Mouse support");
#endif
toggle_cuttoend_msg = _("Cut to end"); toggle_cuttoend_msg = _("Cut to end");
toggle_noconvert_msg = _("No conversion from DOS/Mac format"); toggle_noconvert_msg = _("No conversion from DOS/Mac format");
toggle_dos_msg = _("Writing file in DOS format"); toggle_dos_msg = _("Writing file in DOS format");
@ -257,7 +264,9 @@ void toggle_init(void)
#ifndef DISABLE_WRAPPING #ifndef DISABLE_WRAPPING
toggle_init_one(TOGGLE_WRAP_KEY, toggle_wrap_msg, NO_WRAP); toggle_init_one(TOGGLE_WRAP_KEY, toggle_wrap_msg, NO_WRAP);
#endif #endif
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
toggle_init_one(TOGGLE_MOUSE_KEY, toggle_mouse_msg, USE_MOUSE); toggle_init_one(TOGGLE_MOUSE_KEY, toggle_mouse_msg, USE_MOUSE);
#endif
toggle_init_one(TOGGLE_CUTTOEND_KEY, toggle_cuttoend_msg, CUT_TO_END); toggle_init_one(TOGGLE_CUTTOEND_KEY, toggle_cuttoend_msg, CUT_TO_END);
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
toggle_init_one(TOGGLE_LOAD_KEY, toggle_load_msg, MULTIBUFFER); toggle_init_one(TOGGLE_LOAD_KEY, toggle_load_msg, MULTIBUFFER);
@ -401,7 +410,7 @@ void shortcut_init(int unjustify)
do_help); do_help);
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
if (open_files != NULL && (open_files->prev || open_files->next)) if (open_files != NULL && (open_files->prev != NULL || open_files->next != NULL))
sc_init_one(&main_list, NANO_EXIT_KEY, _("Close"), sc_init_one(&main_list, NANO_EXIT_KEY, _("Close"),
IFHELP(nano_exit_msg, 0), NANO_EXIT_FKEY, 0, VIEW, IFHELP(nano_exit_msg, 0), NANO_EXIT_FKEY, 0, VIEW,
do_exit); do_exit);
@ -775,7 +784,7 @@ void shortcut_init(int unjustify)
IFHELP(nano_cancel_msg, 0), 0, 0, VIEW, 0); IFHELP(nano_cancel_msg, 0), 0, 0, VIEW, 0);
#endif #endif
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) || !defined (DISABLE_HELP) #if !defined(DISABLE_BROWSER) || !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = main_list; currshortcut = main_list;
#endif #endif
#ifndef NANO_SMALL #ifndef NANO_SMALL

13
move.c
View File

@ -104,10 +104,16 @@ int do_page_down(void)
return 0; return 0;
/* AHEM, if we only have a screen or less of text, DON'T do an /* AHEM, if we only have a screen or less of text, DON'T do an
edit_update, just move the cursor to editbot! */ edit_update(), just move the cursor to editbot! */
if (edittop == fileage && editbot == filebot && totlines < editwinrows) { if (edittop == fileage && editbot == filebot && totlines < editwinrows) {
current = editbot; current = editbot;
reset_cursor(); reset_cursor();
#ifndef NANO_SMALL
/* ...unless marking is on, in which case we need it to update
the highlight. */
if (ISSET(MARK_ISSET))
edit_update(current, NONE);
#endif
} else if (editbot != filebot || edittop == fileage) { } else if (editbot != filebot || edittop == fileage) {
current_y = 0; current_y = 0;
current = editbot; current = editbot;
@ -153,7 +159,8 @@ int do_up(void)
/* Return value 1 means we moved down, 0 means we were already at the /* Return value 1 means we moved down, 0 means we were already at the
* bottom. */ * bottom. */
int do_down(void) { int do_down(void)
{
wrap_reset(); wrap_reset();
UNSET(KEEP_CUTBUFFER); UNSET(KEEP_CUTBUFFER);
check_statblank(); check_statblank();
@ -211,7 +218,7 @@ int do_right(void)
if (current->data[current_x] != '\0') if (current->data[current_x] != '\0')
current_x++; current_x++;
else if (current->next) { else if (current->next != NULL) {
do_down(); do_down();
current_x = 0; current_x = 0;
} }

157
nano.c
View File

@ -111,15 +111,15 @@ void die(const char *msg, ...)
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
/* then save all of the other modified loaded files, if any */ /* then save all of the other modified loaded files, if any */
if (open_files) { if (open_files != NULL) {
openfilestruct *tmp; openfilestruct *tmp;
tmp = open_files; tmp = open_files;
while (open_files->prev) while (open_files->prev != NULL)
open_files = open_files->prev; open_files = open_files->prev;
while (open_files->next) { while (open_files->next != NULL) {
/* if we already saved the file above (i. e. if it was the /* if we already saved the file above (i. e. if it was the
currently loaded file), don't save it again */ currently loaded file), don't save it again */
@ -228,17 +228,16 @@ void window_init(void)
bottomwin = newwin(3 - no_help(), COLS, LINES - 3 + no_help(), 0); bottomwin = newwin(3 - no_help(), COLS, LINES - 3 + no_help(), 0);
#ifdef PDCURSES #ifdef PDCURSES
/* Oops, I guess we need this again. /* Oops, I guess we need this again. Moved here so the keypad still
Moved here so the keypad still works after a Meta-X, for example */ works after a Meta-X, for example */
keypad(edit, TRUE); keypad(edit, TRUE);
keypad(bottomwin, TRUE); keypad(bottomwin, TRUE);
#endif #endif
} }
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
void mouse_init(void) void mouse_init(void)
{ {
#ifndef DISABLE_MOUSE
#ifdef NCURSES_MOUSE_VERSION
if (ISSET(USE_MOUSE)) { if (ISSET(USE_MOUSE)) {
keypad_on(edit, 1); keypad_on(edit, 1);
keypad_on(bottomwin, 1); keypad_on(bottomwin, 1);
@ -247,9 +246,8 @@ void mouse_init(void)
mouseinterval(50); mouseinterval(50);
} else } else
mousemask(0, NULL); mousemask(0, NULL);
#endif
#endif
} }
#endif
#ifndef DISABLE_HELP #ifndef DISABLE_HELP
/* This function allocates help_text, and stores the help string in it. /* This function allocates help_text, and stores the help string in it.
@ -651,11 +649,9 @@ void usage(void)
print1opt("-k", "--cut", _("Let ^K cut from cursor to end of line")); print1opt("-k", "--cut", _("Let ^K cut from cursor to end of line"));
#endif #endif
print1opt("-l", "--nofollow", _("Don't follow symbolic links, overwrite")); print1opt("-l", "--nofollow", _("Don't follow symbolic links, overwrite"));
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
print1opt("-m", "--mouse", _("Enable mouse")); print1opt("-m", "--mouse", _("Enable mouse"));
#endif #endif
#endif
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
print1opt(_("-o [dir]"), _("--operatingdir=[dir]"), _("Set operating directory")); print1opt(_("-o [dir]"), _("--operatingdir=[dir]"), _("Set operating directory"));
#endif #endif
@ -706,7 +702,7 @@ void version(void)
#ifdef DISABLE_JUSTIFY #ifdef DISABLE_JUSTIFY
printf(" --disable-justify"); printf(" --disable-justify");
#endif #endif
#ifdef DISABLE_MOUSE #if defined(DISABLE_MOUSE) || !defined(NCURSES_MOUSE_VERSION)
printf(" --disable-mouse"); printf(" --disable-mouse");
#endif #endif
#ifndef ENABLE_NLS #ifndef ENABLE_NLS
@ -769,7 +765,8 @@ static int pid; /* This is the PID of the newly forked process
RETSIGTYPE cancel_fork(int signal) RETSIGTYPE cancel_fork(int signal)
{ {
if (kill(pid, SIGKILL)==-1) nperror("kill"); if (kill(pid, SIGKILL) == -1)
nperror("kill");
} }
int open_pipe(const char *command) int open_pipe(const char *command)
@ -836,11 +833,11 @@ int open_pipe(const char *command)
/* See if the platform supports disabling individual control /* See if the platform supports disabling individual control
* characters. */ * characters. */
#ifdef _POSIX_VDISABLE #ifdef _POSIX_VDISABLE
if (!cancel_sigs && tcgetattr(0, &term) == -1) { if (cancel_sigs == 0 && tcgetattr(0, &term) == -1) {
cancel_sigs = 2; cancel_sigs = 2;
nperror("tcgetattr"); nperror("tcgetattr");
} }
if (!cancel_sigs) { if (cancel_sigs == 0) {
newterm = term; newterm = term;
/* Grab oldterm's VINTR key :-) */ /* Grab oldterm's VINTR key :-) */
newterm.c_cc[VINTR] = oldterm.c_cc[VINTR]; newterm.c_cc[VINTR] = oldterm.c_cc[VINTR];
@ -852,7 +849,7 @@ int open_pipe(const char *command)
#endif /* _POSIX_VDISABLE */ #endif /* _POSIX_VDISABLE */
f = fdopen(fd[0], "rb"); f = fdopen(fd[0], "rb");
if (!f) if (f == NULL)
nperror("fdopen"); nperror("fdopen");
read_file(f, "stdin", 0); read_file(f, "stdin", 0);
@ -865,7 +862,7 @@ int open_pipe(const char *command)
nperror("wait"); nperror("wait");
#ifdef _POSIX_VDISABLE #ifdef _POSIX_VDISABLE
if (!cancel_sigs && tcsetattr(0, TCSANOW, &term) == -1) if (cancel_sigs == 0 && tcsetattr(0, TCSANOW, &term) == -1)
nperror("tcsetattr"); nperror("tcsetattr");
#endif /* _POSIX_VDISABLE */ #endif /* _POSIX_VDISABLE */
@ -876,8 +873,7 @@ int open_pipe(const char *command)
} }
#endif /* NANO_SMALL */ #endif /* NANO_SMALL */
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
void do_mouse(void) void do_mouse(void)
{ {
MEVENT mevent; MEVENT mevent;
@ -968,7 +964,6 @@ void do_mouse(void)
} }
} }
#endif #endif
#endif
/* The user typed a printable character; add it to the edit buffer. */ /* The user typed a printable character; add it to the edit buffer. */
void do_char(char ch) void do_char(char ch)
@ -1225,6 +1220,11 @@ int do_enter(void)
* where we think the cursor is. * where we think the cursor is.
*/ */
if (current_y == editwinrows - 1) { if (current_y == editwinrows - 1) {
#ifndef NANO_SMALL
if (ISSET(SMOOTHSCROLL))
edit_update(current, NONE);
else
#endif
edit_update(current, CENTER); edit_update(current, CENTER);
reset_cursor(); reset_cursor();
} else { } else {
@ -1300,7 +1300,7 @@ int do_prev_word(void)
{ {
filestruct *old = current; filestruct *old = current;
assert(current != NULL); assert(current != NULL && current->data != NULL);
/* Skip letters in this word first. */ /* Skip letters in this word first. */
while (current_x >= 0 && isalnum((int)current->data[current_x])) while (current_x >= 0 && isalnum((int)current->data[current_x]))
@ -1529,9 +1529,9 @@ int do_wrap(filestruct *inptr)
temp->prev = inptr; temp->prev = inptr;
temp->next = inptr->next; temp->next = inptr->next;
temp->prev->next = temp; temp->prev->next = temp;
/* If !temp->next, then temp is the last line of the file, so we /* If temp->next is NULL, then temp is the last line of the
* must set filebot. */ * file, so we must set filebot. */
if (temp->next) if (temp->next != NULL)
temp->next->prev = temp; temp->next->prev = temp;
else else
filebot = temp; filebot = temp;
@ -1623,7 +1623,7 @@ int do_int_spell_fix(const char *word)
while (1) { while (1) {
/* make sure word is still mis-spelt (i.e. when multi-errors) */ /* make sure word is still mis-spelt (i.e. when multi-errors) */
if (findnextstr(TRUE, FALSE, fileage, beginx_top, word) != NULL) { if (findnextstr(TRUE, FALSE, fileage, beginx_top, word)) {
/* find whole words only */ /* find whole words only */
if (!is_whole_word(current_x, current->data, word)) if (!is_whole_word(current_x, current->data, word))
@ -1678,8 +1678,8 @@ int do_int_spell_fix(const char *word)
return TRUE; return TRUE;
} }
/* Integrated spell checking using 'spell' program. /* Integrated spell checking using 'spell' program. Return value: NULL
Return value: NULL for normal termination, otherwise the error string */ * for normal termination, otherwise the error string. */
char *do_int_speller(char *tempfile_name) char *do_int_speller(char *tempfile_name)
{ {
char *read_buff, *read_buff_ptr, *read_buff_word; char *read_buff, *read_buff_ptr, *read_buff_word;
@ -1841,7 +1841,7 @@ char *do_int_speller(char *tempfile_name)
read_buff_word = read_buff_ptr = read_buff; read_buff_word = read_buff_ptr = read_buff;
while (*read_buff_ptr) { while (*read_buff_ptr != '\0') {
if ((*read_buff_ptr == '\n') || (*read_buff_ptr == '\r')) { if ((*read_buff_ptr == '\n') || (*read_buff_ptr == '\r')) {
*read_buff_ptr = (char)NULL; *read_buff_ptr = (char)NULL;
@ -1883,8 +1883,8 @@ char *do_int_speller(char *tempfile_name)
return NULL; return NULL;
} }
/* External spell checking. /* External spell checking. Return value: NULL for normal termination,
Return value: NULL for normal termination, otherwise the error string */ * otherwise the error string. */
char *do_alt_speller(char *tempfile_name) char *do_alt_speller(char *tempfile_name)
{ {
int alt_spell_status, lineno_cur = current->lineno; int alt_spell_status, lineno_cur = current->lineno;
@ -1979,7 +1979,7 @@ int do_spell(void)
{ {
#ifdef DISABLE_SPELLER #ifdef DISABLE_SPELLER
nano_disabled_msg(); nano_disabled_msg();
return (TRUE); return TRUE;
#else #else
char *temp, *spell_msg = _("Generic error"); char *temp, *spell_msg = _("Generic error");
@ -2001,7 +2001,7 @@ int do_spell(void)
add_open_file(1); add_open_file(1);
#endif #endif
if (alt_speller) if (alt_speller != NULL)
spell_msg = do_alt_speller(temp); spell_msg = do_alt_speller(temp);
else else
spell_msg = do_int_speller(temp); spell_msg = do_int_speller(temp);
@ -2052,6 +2052,8 @@ size_t indent_length(const char *line)
* not be whitespace. */ * not be whitespace. */
int justify_format(int changes_allowed, filestruct *line, size_t skip) int justify_format(int changes_allowed, filestruct *line, size_t skip)
{ {
const char *punct = ".?!";
const char *brackets = "'\")}]>";
char *back, *front; char *back, *front;
/* These four asserts are assumptions about the input data. */ /* These four asserts are assumptions about the input data. */
@ -2073,8 +2075,6 @@ int justify_format(int changes_allowed, filestruct *line, size_t skip)
} }
/* these tests are safe since line->data + skip is not a space */ /* these tests are safe since line->data + skip is not a space */
if (*front == ' ' && *(front - 1) == ' ') { if (*front == ' ' && *(front - 1) == ' ') {
const char *brackets = _("'\")}]>");
const char *punct = _(".?!");
const char *bob = front - 2; const char *bob = front - 2;
remove_space = 1; remove_space = 1;
@ -2108,13 +2108,13 @@ int justify_format(int changes_allowed, filestruct *line, size_t skip)
while (line->data < back && *(back - 1) == ' ') while (line->data < back && *(back - 1) == ' ')
back--; back--;
if (line->data < back && *back == ' ' && if (line->data < back && *back == ' ' &&
(*(back-1) == '.' || *(back-1) == '!' || *(back-1) == '?')) strchr(punct, *(back - 1)) != NULL)
back++; back++;
if (!changes_allowed && back != front) if (!changes_allowed && back != front)
return 1; return 1;
/* This assert merely documents a fact about the loop above. */ /* This assert merely documents a fact about the loop above. */
assert(changes_allowed || back == front); assert(changes_allowed != 0 || back == front);
/* Now back is the new end of line->data. */ /* Now back is the new end of line->data. */
if (back != front) { if (back != front) {
@ -2364,7 +2364,7 @@ int do_justify(void)
/* This line is part of a paragraph. So we must search back to /* This line is part of a paragraph. So we must search back to
* the first line of this paragraph. First we check items 1) and * the first line of this paragraph. First we check items 1) and
* 3) above. */ * 3) above. */
while (current->prev && quotes_match(current->data, while (current->prev != NULL && quotes_match(current->data,
quote_len, IFREG(current->prev->data, &qreg))) { quote_len, IFREG(current->prev->data, &qreg))) {
size_t temp_id_len = size_t temp_id_len =
indent_length(current->prev->data + quote_len); indent_length(current->prev->data + quote_len);
@ -2392,7 +2392,7 @@ int do_justify(void)
/* There is no next paragraph, so nothing to justify. */ /* There is no next paragraph, so nothing to justify. */
if (current->next == NULL) { if (current->next == NULL) {
placewewant = 0; placewewant = 0;
if (current_y > editwinrows - 4) if (current_y > editwinrows - 1)
edit_update(current, CENTER); edit_update(current, CENTER);
else else
edit_refresh(); edit_refresh();
@ -2412,7 +2412,7 @@ int do_justify(void)
par_len = 1; par_len = 1;
indent_len = indent_length(line->data + quote_len); indent_len = indent_length(line->data + quote_len);
while (line->next && quotes_match(current->data, quote_len, while (line->next != NULL && quotes_match(current->data, quote_len,
IFREG(line->next->data, &qreg))) { IFREG(line->next->data, &qreg))) {
size_t temp_id_len = indent_length(line->next->data + quote_len); size_t temp_id_len = indent_length(line->next->data + quote_len);
@ -2453,8 +2453,7 @@ int do_justify(void)
* made. If there are, we do backup_lines(), which copies the * made. If there are, we do backup_lines(), which copies the
* original paragraph to the cutbuffer for unjustification, and * original paragraph to the cutbuffer for unjustification, and
* then calls justify_format() on the remaining lines. */ * then calls justify_format() on the remaining lines. */
if (first_mod_line == NULL && if (first_mod_line == NULL && justify_format(0, current, indent_len))
justify_format(0, current, indent_len))
first_mod_line = backup_lines(current, par_len, quote_len); first_mod_line = backup_lines(current, par_len, quote_len);
line_len = strlen(current->data); line_len = strlen(current->data);
@ -2557,6 +2556,11 @@ int do_justify(void)
#endif #endif
if (indent_len + break_pos == next_line_len) { if (indent_len + break_pos == next_line_len) {
line = current->next; line = current->next;
/* Don't destroy edittop! */
if (line == edittop)
edittop = current;
unlink_node(line); unlink_node(line);
delete_node(line); delete_node(line);
totlines--; totlines--;
@ -2588,7 +2592,7 @@ int do_justify(void)
renumber(first_mod_line); renumber(first_mod_line);
} }
if (current_y > editwinrows - 4) if (current_y > editwinrows - 1)
edit_update(current, CENTER); edit_update(current, CENTER);
else else
edit_refresh(); edit_refresh();
@ -2602,15 +2606,13 @@ int do_justify(void)
/* Now get a keystroke and see if it's unjustify; if not, unget the /* Now get a keystroke and see if it's unjustify; if not, unget the
* keystroke and return. */ * keystroke and return. */
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
/* If it was a mouse click, parse it with do_mouse() and it might /* If it was a mouse click, parse it with do_mouse() and it might
* become the unjustify key. Else give it back to the input stream. */ * become the unjustify key. Else give it back to the input stream. */
if ((i = wgetch(edit)) == KEY_MOUSE) if ((i = wgetch(edit)) == KEY_MOUSE)
do_mouse(); do_mouse();
else else
ungetch(i); ungetch(i);
#endif
#endif #endif
if ((i = wgetch(edit)) != NANO_UNJUSTIFY_KEY) { if ((i = wgetch(edit)) != NANO_UNJUSTIFY_KEY) {
@ -2833,7 +2835,7 @@ void handle_sigwinch(int s)
int result = 0; int result = 0;
struct winsize win; struct winsize win;
if (!tty) if (tty == NULL)
return; return;
fd = open(tty, O_RDWR); fd = open(tty, O_RDWR);
if (fd == -1) if (fd == -1)
@ -2933,9 +2935,11 @@ void do_toggle(const toggle *which)
case TOGGLE_SUSPEND_KEY: case TOGGLE_SUSPEND_KEY:
signal_init(); signal_init();
break; break;
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
case TOGGLE_MOUSE_KEY: case TOGGLE_MOUSE_KEY:
mouse_init(); mouse_init();
break; break;
#endif
case TOGGLE_NOHELP_KEY: case TOGGLE_NOHELP_KEY:
wclear(bottomwin); wclear(bottomwin);
wrefresh(bottomwin); wrefresh(bottomwin);
@ -2950,9 +2954,11 @@ void do_toggle(const toggle *which)
case TOGGLE_MAC_KEY: case TOGGLE_MAC_KEY:
UNSET(DOS_FILE); UNSET(DOS_FILE);
break; break;
#ifdef ENABLE_COLOR
case TOGGLE_SYNTAX_KEY: case TOGGLE_SYNTAX_KEY:
edit_refresh(); edit_refresh();
break; break;
#endif
} }
/* We are assuming here that shortcut_init() above didn't free and /* We are assuming here that shortcut_init() above didn't free and
@ -2968,21 +2974,21 @@ void do_toggle(const toggle *which)
/* This function returns the correct keystroke, given the A,B,C or D /* This function returns the correct keystroke, given the A,B,C or D
input key. This is a common sequence of many terms which send input key. This is a common sequence of many terms which send
Esc-O-[A-D] or Esc-[-[A-D]. */ Esc-O-[A-D] or Esc-[-[A-D]. */
int ABCD(int input) int abcd(int input)
{ {
switch (input) { switch (input) {
case 'A': case 'A':
case 'a': case 'a':
return (KEY_UP); return KEY_UP;
case 'B': case 'B':
case 'b': case 'b':
return (KEY_DOWN); return KEY_DOWN;
case 'C': case 'C':
case 'c': case 'c':
return (KEY_RIGHT); return KEY_RIGHT;
case 'D': case 'D':
case 'd': case 'd':
return (KEY_LEFT); return KEY_LEFT;
default: default:
return 0; return 0;
} }
@ -3007,7 +3013,7 @@ int main(int argc, char *argv[])
#ifdef HAVE_GETOPT_LONG #ifdef HAVE_GETOPT_LONG
int option_index = 0; int option_index = 0;
struct option long_options[] = { const struct option long_options[] = {
{"help", 0, 0, 'h'}, {"help", 0, 0, 'h'},
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
{"multibuffer", 0, 0, 'F'}, {"multibuffer", 0, 0, 'F'},
@ -3029,7 +3035,9 @@ int main(int argc, char *argv[])
#endif #endif
{"const", 0, 0, 'c'}, {"const", 0, 0, 'c'},
{"nofollow", 0, 0, 'l'}, {"nofollow", 0, 0, 'l'},
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
{"mouse", 0, 0, 'm'}, {"mouse", 0, 0, 'm'},
#endif
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
{"operatingdir", 1, 0, 'o'}, {"operatingdir", 1, 0, 'o'},
#endif #endif
@ -3060,16 +3068,11 @@ int main(int argc, char *argv[])
}; };
#endif #endif
/* Flag inits... */
SET(FOLLOW_SYMLINKS);
#ifndef NANO_SMALL
#ifdef ENABLE_NLS #ifdef ENABLE_NLS
setlocale(LC_ALL, ""); setlocale(LC_ALL, "");
bindtextdomain(PACKAGE, LOCALEDIR); bindtextdomain(PACKAGE, LOCALEDIR);
textdomain(PACKAGE); textdomain(PACKAGE);
#endif #endif
#endif
#ifdef ENABLE_NANORC #ifdef ENABLE_NANORC
{ {
@ -3151,13 +3154,10 @@ int main(int argc, char *argv[])
SET(NO_CONVERT); SET(NO_CONVERT);
break; break;
#endif #endif
case 'Q':
#ifndef DISABLE_JUSTIFY #ifndef DISABLE_JUSTIFY
case 'Q':
quotestr = optarg; quotestr = optarg;
break; break;
#else
usage();
exit(1);
#endif #endif
#ifdef HAVE_REGEX_H #ifdef HAVE_REGEX_H
case 'R': case 'R':
@ -3208,11 +3208,13 @@ int main(int argc, char *argv[])
break; break;
#endif #endif
case 'l': case 'l':
UNSET(FOLLOW_SYMLINKS); SET(NOFOLLOW_SYMLINKS);
break; break;
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
case 'm': case 'm':
SET(USE_MOUSE); SET(USE_MOUSE);
break; break;
#endif
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
case 'o': case 'o':
operating_dir = mallocstrcpy(operating_dir, optarg); operating_dir = mallocstrcpy(operating_dir, optarg);
@ -3249,14 +3251,11 @@ int main(int argc, char *argv[])
case 'v': case 'v':
SET(VIEW_MODE); SET(VIEW_MODE);
break; break;
case 'w':
#ifdef DISABLE_WRAPPING #ifdef DISABLE_WRAPPING
usage(); case 'w':
exit(0);
#else
SET(NO_WRAP); SET(NO_WRAP);
break; break;
#endif /* DISABLE_WRAPPING */ #endif
case 'x': case 'x':
SET(NO_HELP); SET(NO_HELP);
break; break;
@ -3281,8 +3280,8 @@ int main(int argc, char *argv[])
/* See if we were invoked with the name "pico" */ /* See if we were invoked with the name "pico" */
argv0 = strrchr(argv[0], '/'); argv0 = strrchr(argv[0], '/');
if ((argv0 && strstr(argv0, "pico")) if ((argv0 != NULL && strstr(argv0, "pico") != NULL)
|| (!argv0 && strstr(argv[0], "pico"))) || (argv0 == NULL && strstr(argv[0], "pico") != NULL))
SET(PICO_MODE); SET(PICO_MODE);
/* See if there's a non-option in argv (first non-option is the /* See if there's a non-option in argv (first non-option is the
@ -3326,7 +3325,9 @@ int main(int argc, char *argv[])
#endif #endif
window_init(); window_init();
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
mouse_init(); mouse_init();
#endif
if (!ISSET(ALT_KEYPAD)) { if (!ISSET(ALT_KEYPAD)) {
keypad(edit, TRUE); keypad(edit, TRUE);
@ -3374,7 +3375,7 @@ int main(int argc, char *argv[])
while (1) { while (1) {
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) || !defined(DISABLE_HELP) #if !defined(DISABLE_BROWSER) || !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = main_list; currshortcut = main_list;
#endif #endif
@ -3394,7 +3395,7 @@ int main(int argc, char *argv[])
kbinput = wgetch(edit); kbinput = wgetch(edit);
if ((kbinput <= 'D' && kbinput >= 'A') || if ((kbinput <= 'D' && kbinput >= 'A') ||
(kbinput <= 'd' && kbinput >= 'a')) (kbinput <= 'd' && kbinput >= 'a'))
kbinput = ABCD(kbinput); kbinput = abcd(kbinput);
else if (kbinput <= 'z' && kbinput >= 'j') else if (kbinput <= 'z' && kbinput >= 'j')
print_numlock_warning(); print_numlock_warning();
else if (kbinput <= 'S' && kbinput >= 'P') else if (kbinput <= 'S' && kbinput >= 'P')
@ -3513,7 +3514,7 @@ int main(int argc, char *argv[])
case 'b': case 'b':
case 'c': case 'c':
case 'd': case 'd':
kbinput = ABCD(kbinput); kbinput = abcd(kbinput);
break; break;
case 'H': case 'H':
kbinput = KEY_HOME; kbinput = KEY_HOME;
@ -3590,7 +3591,7 @@ int main(int argc, char *argv[])
/* Look through the main shortcut list to see if we've hit a /* Look through the main shortcut list to see if we've hit a
shortcut key */ shortcut key */
#if !defined(DISABLE_BROWSER) || !defined(DISABLE_MOUSE) || !defined (DISABLE_HELP) #if !defined(DISABLE_BROWSER) || !defined (DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
for (s = currshortcut; s != NULL && !keyhandled; s = s->next) { for (s = currshortcut; s != NULL && !keyhandled; s = s->next) {
#else #else
for (s = main_list; s != NULL && !keyhandled; s = s->next) { for (s = main_list; s != NULL && !keyhandled; s = s->next) {
@ -3628,12 +3629,8 @@ int main(int argc, char *argv[])
keyhandled = 1; keyhandled = 1;
} }
#ifndef USE_SLANG
/* Hack, make insert key do something useful, like insert file */ /* Hack, make insert key do something useful, like insert file */
if (kbinput == KEY_IC) { if (kbinput == KEY_IC) {
#else
if (0) {
#endif
do_insertkey: do_insertkey:
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
@ -3654,12 +3651,10 @@ int main(int argc, char *argv[])
/* Last gasp, stuff that's not in the main lists */ /* Last gasp, stuff that's not in the main lists */
if (!keyhandled) if (!keyhandled)
switch (kbinput) { switch (kbinput) {
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
case KEY_MOUSE: case KEY_MOUSE:
do_mouse(); do_mouse();
break; break;
#endif
#endif #endif
case 0: /* Erg */ case 0: /* Erg */

17
nano.h
View File

@ -39,7 +39,8 @@
#ifdef USE_SLANG /* Slang support enabled */ #ifdef USE_SLANG /* Slang support enabled */
#include <slcurses.h> #include <slcurses.h>
#define KEY_DC 0x113 #define KEY_IC SL_KEY_IC
#define KEY_DC SL_KEY_DELETE
#elif defined(HAVE_NCURSES_H) #elif defined(HAVE_NCURSES_H)
#include <ncurses.h> #include <ncurses.h>
#else /* Uh oh */ #else /* Uh oh */
@ -71,6 +72,15 @@
# endif # endif
#endif #endif
#if !defined(HAVE_STRCASECMP) || !defined(HAVE_STRNCASECMP)
# ifndef HAVE_STRCASECMP
# define strcasecmp strcmp
# endif
# ifndef HAVE_STRNCASECMP
# define strncasecmp strncmp
# endif
#endif
/* HP-UX 10 & 11 do not seem to support KEY_HOME and KEY_END */ /* HP-UX 10 & 11 do not seem to support KEY_HOME and KEY_END */
#ifndef KEY_HOME #ifndef KEY_HOME
#define KEY_HOME -1 #define KEY_HOME -1
@ -80,7 +90,6 @@
#define KEY_END -1 #define KEY_END -1
#endif /* KEY_END */ #endif /* KEY_END */
#define VERMSG "GNU nano " VERSION #define VERMSG "GNU nano " VERSION
#if defined(DISABLE_WRAPPING) && defined(DISABLE_JUSTIFY) #if defined(DISABLE_WRAPPING) && defined(DISABLE_JUSTIFY)
@ -191,7 +200,7 @@ typedef struct syntaxtype {
#define CONSTUPDATE (1<<4) #define CONSTUPDATE (1<<4)
#define NO_HELP (1<<5) #define NO_HELP (1<<5)
#define PICO_MODE (1<<6) #define PICO_MODE (1<<6)
#define FOLLOW_SYMLINKS (1<<7) #define NOFOLLOW_SYMLINKS (1<<7)
#define SUSPEND (1<<8) #define SUSPEND (1<<8)
#define NO_WRAP (1<<9) #define NO_WRAP (1<<9)
#define AUTOINDENT (1<<10) #define AUTOINDENT (1<<10)
@ -213,7 +222,7 @@ typedef struct syntaxtype {
#define NO_CONVERT (1<<26) #define NO_CONVERT (1<<26)
#define BACKUP_FILE (1<<27) #define BACKUP_FILE (1<<27)
#define NO_RCFILE (1<<28) #define NO_RCFILE (1<<28)
#define COLOR_SYNTAX (1<<28) #define COLOR_SYNTAX (1<<29)
/* Control key sequences, changing these would be very very bad */ /* Control key sequences, changing these would be very very bad */

11
proto.h
View File

@ -33,7 +33,9 @@ extern int wrap_at;
extern int editwinrows; extern int editwinrows;
extern int current_x, current_y, totlines; extern int current_x, current_y, totlines;
extern int placewewant; extern int placewewant;
#ifndef NANO_SMALL
extern int mark_beginx; extern int mark_beginx;
#endif
extern long totsize; extern long totsize;
extern int temp_opt; extern int temp_opt;
extern int wrap_at, flags, tabsize; extern int wrap_at, flags, tabsize;
@ -64,7 +66,10 @@ extern char *alt_speller;
extern struct stat fileinfo; extern struct stat fileinfo;
extern filestruct *current, *fileage, *edittop, *editbot, *filebot; extern filestruct *current, *fileage, *edittop, *editbot, *filebot;
extern filestruct *cutbuffer, *mark_beginbuf; extern filestruct *cutbuffer;
#ifndef NANO_SMALL
extern filestruct *mark_beginbuf;
#endif
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
extern openfilestruct *open_files; extern openfilestruct *open_files;
@ -215,7 +220,9 @@ void die_too_small(void);
void print_view_warning(void); void print_view_warning(void);
void global_init(int save_cutbuffer); void global_init(int save_cutbuffer);
void window_init(void); void window_init(void);
#if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
void mouse_init(void); void mouse_init(void);
#endif
#ifndef DISABLE_HELP #ifndef DISABLE_HELP
void help_init(void); void help_init(void);
#endif #endif
@ -300,7 +307,7 @@ void print_numlock_warning(void);
#ifndef NANO_SMALL #ifndef NANO_SMALL
void do_toggle(const toggle *which); void do_toggle(const toggle *which);
#endif #endif
int ABCD(int input); int abcd(int input);
/* Public functions in rcfile.c */ /* Public functions in rcfile.c */
#ifdef ENABLE_NANORC #ifdef ENABLE_NANORC

View File

@ -50,7 +50,7 @@ const static rcoption rcopts[] = {
{"fill", 0}, {"fill", 0},
#endif #endif
{"keypad", ALT_KEYPAD}, {"keypad", ALT_KEYPAD},
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
{"mouse", USE_MOUSE}, {"mouse", USE_MOUSE},
#endif #endif
#ifdef ENABLE_MULTIBUFFER #ifdef ENABLE_MULTIBUFFER
@ -59,7 +59,7 @@ const static rcoption rcopts[] = {
#ifndef NANO_SMALL #ifndef NANO_SMALL
{"noconvert", NO_CONVERT}, {"noconvert", NO_CONVERT},
#endif #endif
{"nofollow", FOLLOW_SYMLINKS}, {"nofollow", NOFOLLOW_SYMLINKS},
{"nohelp", NO_HELP}, {"nohelp", NO_HELP},
#ifndef DISABLE_WRAPPING #ifndef DISABLE_WRAPPING
{"nowrap", NO_WRAP}, {"nowrap", NO_WRAP},
@ -68,7 +68,7 @@ const static rcoption rcopts[] = {
{"operatingdir", 0}, {"operatingdir", 0},
#endif #endif
{"pico", PICO_MODE}, {"pico", PICO_MODE},
#ifndef NANO_SMALL #ifndef DISABLE_JUSTIFY
{"quotestr", 0}, {"quotestr", 0},
#endif #endif
#ifdef HAVE_REGEX_H #ifdef HAVE_REGEX_H
@ -403,7 +403,7 @@ void parse_colors(char *ptr)
else { else {
if (ptr == NULL || strncasecmp(ptr, "end=", 4)) { if (ptr == NULL || strncasecmp(ptr, "end=", 4)) {
rcfile_error(_ rcfile_error(_
("\n\t\"start=\" requires a corresponding \"end=\"")); ("\"start=\" requires a corresponding \"end=\""));
return; return;
} }
@ -455,7 +455,7 @@ void parse_rcfile(FILE *rcstream)
/* Else skip to the next space */ /* Else skip to the next space */
keyword = ptr; keyword = ptr;
ptr = parse_next_word(ptr); ptr = parse_next_word(ptr);
if (!ptr) if (ptr == NULL)
continue; continue;
/* Else try to parse the keyword */ /* Else try to parse the keyword */
@ -485,7 +485,7 @@ void parse_rcfile(FILE *rcstream)
fprintf(stderr, _("parse_rcfile: Parsing option %s\n"), fprintf(stderr, _("parse_rcfile: Parsing option %s\n"),
rcopts[i].name); rcopts[i].name);
#endif #endif
if (set == 1 || rcopts[i].flag == FOLLOW_SYMLINKS) { if (set == 1) {
if (!strcasecmp(rcopts[i].name, "tabsize") if (!strcasecmp(rcopts[i].name, "tabsize")
#ifndef DISABLE_OPERATINGDIR #ifndef DISABLE_OPERATINGDIR
|| !strcasecmp(rcopts[i].name, "operatingdir") || !strcasecmp(rcopts[i].name, "operatingdir")

View File

@ -30,6 +30,9 @@
#include "proto.h" #include "proto.h"
#include "nano.h" #include "nano.h"
static int past_editbuff;
/* findnextstr() is now searching lines not displayed */
/* Regular expression helper functions */ /* Regular expression helper functions */
#ifdef HAVE_REGEX_H #ifdef HAVE_REGEX_H
@ -117,14 +120,16 @@ int search_init(int replacing)
last_search. */ last_search. */
if (ISSET(PICO_MODE)) { if (ISSET(PICO_MODE)) {
if (backupstring == NULL || !strcmp(backupstring, last_search)) if (backupstring == NULL || !strcmp(backupstring, last_search)) {
backupstring = mallocstrcpy(backupstring, ""); backupstring = charalloc(1);
backupstring[0] = '\0';
}
} }
else if (backupstring == NULL) else if (backupstring == NULL)
backupstring = mallocstrcpy(backupstring, last_search); backupstring = mallocstrcpy(backupstring, last_search);
/* If using Pico messages, we do things the old fashioned way... */ /* If using Pico messages, we do things the old fashioned way... */
if (ISSET(PICO_MODE) && last_search[0]) { if (ISSET(PICO_MODE) && last_search[0] != '\0') {
buf = charalloc(COLS / 3 + 7); buf = charalloc(COLS / 3 + 7);
/* We use COLS / 3 here because we need to see more on the line */ /* We use COLS / 3 here because we need to see more on the line */
sprintf(buf, " [%.*s%s]", COLS / 3, last_search, sprintf(buf, " [%.*s%s]", COLS / 3, last_search,
@ -227,9 +232,6 @@ int is_whole_word(int curr_pos, const char *datastr, const char *searchword)
(sln == strlen(datastr) || !isalpha((int) datastr[sln])); (sln == strlen(datastr) || !isalpha((int) datastr[sln]));
} }
static int past_editbuff;
/* findnextstr() is now searching lines not displayed */
filestruct *findnextstr(int quiet, int bracket_mode, filestruct *findnextstr(int quiet, int bracket_mode,
const filestruct *begin, int beginx, const filestruct *begin, int beginx,
const char *needle) const char *needle)
@ -416,8 +418,7 @@ int do_search(void)
search_last_line = 0; search_last_line = 0;
didfind = findnextstr(FALSE, FALSE, current, current_x, answer); didfind = findnextstr(FALSE, FALSE, current, current_x, answer);
if ((fileptr == current) && (fileptr_x == current_x) && if ((fileptr == current) && (fileptr_x == current_x) && didfind != NULL)
didfind != NULL)
statusbar(_("This is the only occurrence")); statusbar(_("This is the only occurrence"));
search_abort(); search_abort();
@ -451,7 +452,7 @@ int replace_regexp(char *string, int create_flag)
* replacement using \1, \2, \3, etc. */ * replacement using \1, \2, \3, etc. */
c = last_replace; c = last_replace;
while (*c) { while (*c != '\0') {
if (*c != '\\') { if (*c != '\\') {
if (create_flag) if (create_flag)
*string++ = *c; *string++ = *c;
@ -532,7 +533,7 @@ char *replace_line(void)
strcat(copy, last_replace); strcat(copy, last_replace);
#ifdef HAVE_REGEX_H #ifdef HAVE_REGEX_H
else else
(void) replace_regexp(copy + current_x, 1); replace_regexp(copy + current_x, 1);
#endif #endif
/* The tail of the original line */ /* The tail of the original line */
@ -593,7 +594,7 @@ int do_replace_loop(const char *prevanswer, const filestruct *begin,
FALSE, begin, *beginx, prevanswer); FALSE, begin, *beginx, prevanswer);
/* No more matches. Done! */ /* No more matches. Done! */
if (!fileptr) if (fileptr == NULL)
break; break;
/* Make sure only whole words are found */ /* Make sure only whole words are found */
@ -616,7 +617,7 @@ int do_replace_loop(const char *prevanswer, const filestruct *begin,
replaceall = 1; replaceall = 1;
copy = replace_line(); copy = replace_line();
if (!copy) { if (copy == NULL) {
statusbar(_("Replace failed: unknown subexpression!")); statusbar(_("Replace failed: unknown subexpression!"));
replace_abort(); replace_abort();
return 0; return 0;
@ -773,7 +774,7 @@ int do_gotoline(int line, int save_pos)
current_x = 0; current_x = 0;
/* if save_pos is non-zero, don't change the cursor position when /* if save_pos is nonzero, don't change the cursor position when
updating the edit window */ updating the edit window */
if (save_pos) if (save_pos)
edit_update(current, NONE); edit_update(current, NONE);
@ -820,7 +821,7 @@ int do_find_bracket(void)
ch_under_cursor = current->data[current_x]; ch_under_cursor = current->data[current_x];
if ((!(pos = strchr(brackets, ch_under_cursor))) || (!((offset = pos - brackets) < 8))) { if (((pos = strchr(brackets, ch_under_cursor)) == NULL) || (((offset = pos - brackets) < 8) == 0)) {
statusbar(_("Not a bracket")); statusbar(_("Not a bracket"));
return 1; return 1;
} }
@ -850,7 +851,7 @@ int do_find_bracket(void)
while (1) { while (1) {
search_last_line = 0; search_last_line = 0;
if (findnextstr(1, 1, current, current_x, regexp_pat)) { if (findnextstr(1, 1, current, current_x, regexp_pat) != NULL) {
have_past_editbuff |= past_editbuff; have_past_editbuff |= past_editbuff;
if (current->data[current_x] == ch_under_cursor) /* found identical bracket */ if (current->data[current_x] == ch_under_cursor) /* found identical bracket */
count++; count++;

40
utils.c
View File

@ -32,10 +32,8 @@
int is_cntrl_char(int c) int is_cntrl_char(int c)
{ {
if (iscntrl(c) || ((c & 127) != 127 && iscntrl(c & 127))) return (-128 <= c && c < -96) || (0 <= c && c < 32) ||
return 1; (127 <= c && c < 160);
else
return 0;
} }
int num_of_digits(int n) int num_of_digits(int n)
@ -120,20 +118,20 @@ const char *revstristr(const char *haystack, const char *needle,
#endif /* !NANO_SMALL */ #endif /* !NANO_SMALL */
/* This is now mutt's version (called mutt_stristr) because it doesn't /* This is now mutt's version (called mutt_stristr) because it doesn't
use memory allocation to do a simple search (yuck). */ * use memory allocation to do a simple search (yuck). */
const char *stristr(const char *haystack, const char *needle) const char *stristr(const char *haystack, const char *needle)
{ {
const char *p, *q; const char *p, *q;
if (!haystack) if (haystack == NULL)
return NULL; return NULL;
if (!needle) if (needle == NULL)
return (haystack); return haystack;
while (*(p = haystack)) { while (*(p = haystack) != '\0') {
for (q = needle; *p && *q && tolower(*p) == tolower(*q); p++, q++) for (q = needle; *p != 0 && *q != 0 && tolower(*p) == tolower(*q); p++, q++)
; ;
if (!*q) if (*q == 0)
return haystack; return haystack;
haystack++; haystack++;
} }
@ -205,14 +203,14 @@ void *nmalloc(size_t howmuch)
/* Panic save? */ /* Panic save? */
if (!(r = malloc(howmuch))) if ((r = malloc(howmuch)) == NULL)
die(_("nano: malloc: out of memory!")); die(_("nano: malloc: out of memory!"));
return r; return r;
} }
/* We're going to need this too - Hopefully this will minimize /* We're going to need this too - Hopefully this will minimize the
the transition cost of moving to the appropriate function. */ * transition cost of moving to the appropriate function. */
char *charalloc(size_t howmuch) char *charalloc(size_t howmuch)
{ {
char *r = (char *)malloc(howmuch * sizeof(char)); char *r = (char *)malloc(howmuch * sizeof(char));
@ -227,7 +225,7 @@ void *nrealloc(void *ptr, size_t howmuch)
{ {
void *r; void *r;
if (!(r = realloc(ptr, howmuch))) if ((r = realloc(ptr, howmuch)) == NULL)
die(_("nano: realloc: out of memory!")); die(_("nano: realloc: out of memory!"));
return r; return r;
@ -240,10 +238,10 @@ char *mallocstrcpy(char *dest, const char *src)
if (src == dest) if (src == dest)
return dest; return dest;
if (dest) if (dest != NULL)
free(dest); free(dest);
if (!src) if (src == NULL)
return NULL; return NULL;
dest = charalloc(strlen(src) + 1); dest = charalloc(strlen(src) + 1);
@ -292,7 +290,7 @@ int check_wildcard_match(const char *text, const char *pattern)
retrypat = NULL; retrypat = NULL;
retrytext = NULL; retrytext = NULL;
while (*text || *pattern) { while (*text != '\0' || *pattern != '\0') {
ch = *pattern++; ch = *pattern++;
switch (ch) { switch (ch) {
@ -346,12 +344,12 @@ int check_wildcard_match(const char *text, const char *pattern)
default: default:
if (*text == ch) { if (*text == ch) {
if (*text) if (*text != '\0')
text++; text++;
break; break;
} }
if (*text) { if (*text != '\0') {
pattern = retrypat; pattern = retrypat;
text = ++retrytext; text = ++retrytext;
break; break;
@ -360,7 +358,7 @@ int check_wildcard_match(const char *text, const char *pattern)
return FALSE; return FALSE;
} }
if (!pattern) if (pattern == NULL)
return FALSE; return FALSE;
} }

77
winio.c
View File

@ -210,7 +210,7 @@ int nanogetstr(int allowtabs, const char *buf, const char *def,
else else
answer[0] = '\0'; answer[0] = '\0';
#if !defined(DISABLE_HELP) || !defined(DISABLE_MOUSE) #if !defined(DISABLE_HELP) || (!defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION))
currshortcut = s; currshortcut = s;
#endif #endif
@ -261,12 +261,10 @@ int nanogetstr(int allowtabs, const char *buf, const char *def,
case 545: /* Right alt again */ case 545: /* Right alt again */
break; break;
#endif #endif
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
case KEY_MOUSE: case KEY_MOUSE:
do_mouse(); do_mouse();
break; break;
#endif
#endif #endif
case NANO_HOME_KEY: case NANO_HOME_KEY:
case KEY_HOME: case KEY_HOME:
@ -572,8 +570,8 @@ void reset_cursor(void)
const filestruct *ptr = edittop; const filestruct *ptr = edittop;
size_t x; size_t x;
/* Yuck. This condition can be true after open_file when opening the /* Yuck. This condition can be true after open_file() when opening
* first file. */ * the first file. */
if (edittop == NULL) if (edittop == NULL)
return; return;
@ -640,8 +638,8 @@ void edit_add(const filestruct *fileptr, int yval, int start
while (k < start + COLS) { while (k < start + COLS) {
/* Note the fifth parameter to regexec. It says not to /* Note the fifth parameter to regexec. It says not to
* match the beginning-of-line character unless * match the beginning-of-line character unless
* k == 0. If regexec returns non-zero, there are * k == 0. If regexec returns nonzero, there are no
* no more matches in the line. */ * more matches in the line. */
if (regexec(&start_regexp, &fileptr->data[k], 1, if (regexec(&start_regexp, &fileptr->data[k], 1,
&startmatch, k == 0 ? 0 : REG_NOTBOL)) &startmatch, k == 0 ? 0 : REG_NOTBOL))
break; break;
@ -732,14 +730,12 @@ void edit_add(const filestruct *fileptr, int yval, int start
* fileptr and after the start. Is there an end after * fileptr and after the start. Is there an end after
* the start at all? We don't paint unterminated starts. */ * the start at all? We don't paint unterminated starts. */
end_line = fileptr; end_line = fileptr;
while (end_line != NULL && while (end_line != NULL && regexec(&end_regexp, end_line->data,
regexec(&end_regexp, end_line->data, 1, 1, &endmatch, 0))
&endmatch, 0))
end_line = end_line->next; end_line = end_line->next;
/* No end found, or it is too early. */ /* No end found, or it is too early. */
if (end_line == NULL || if (end_line == NULL || end_line->lineno < fileptr->lineno ||
end_line->lineno < fileptr->lineno ||
(end_line == fileptr && endmatch.rm_eo <= start)) (end_line == fileptr && endmatch.rm_eo <= start))
goto step_two; goto step_two;
@ -801,9 +797,8 @@ void edit_add(const filestruct *fileptr, int yval, int start
/* There is no end on this line. But we haven't /* There is no end on this line. But we haven't
* yet looked for one on later lines. */ * yet looked for one on later lines. */
end_line = fileptr->next; end_line = fileptr->next;
while (end_line != NULL && while (end_line != NULL && regexec(&end_regexp,
regexec(&end_regexp, end_line->data, 1, end_line->data, 1, &endmatch, 0))
&endmatch, 0))
end_line = end_line->next; end_line = end_line->next;
if (end_line != NULL) { if (end_line != NULL) {
assert(0 <= x_start && x_start < COLS); assert(0 <= x_start && x_start < COLS);
@ -900,7 +895,7 @@ void update_line(filestruct *fileptr, int index)
size_t pos; size_t pos;
size_t page_start; size_t page_start;
if (!fileptr) if (fileptr == NULL)
return; return;
line = fileptr->lineno - edittop->lineno; line = fileptr->lineno - edittop->lineno;
@ -996,9 +991,6 @@ void center_cursor(void)
/* Refresh the screen without changing the position of lines. */ /* Refresh the screen without changing the position of lines. */
void edit_refresh(void) void edit_refresh(void)
{ {
static int noloop = 0;
int nlines = 0, currentcheck = 0;
/* Neither of these conditions should occur, but they do. edittop is /* Neither of these conditions should occur, but they do. edittop is
* NULL when you open an existing file on the command line, and * NULL when you open an existing file on the command line, and
* ENABLE_COLOR is defined. Yuck. */ * ENABLE_COLOR is defined. Yuck. */
@ -1007,41 +999,36 @@ void edit_refresh(void)
if (edittop == NULL) if (edittop == NULL)
edittop = current; edittop = current;
if (current->lineno >= edittop->lineno + editwinrows)
/* Note that edit_update() changes edittop so that
* current->lineno = edittop->lineno + editwinrows / 2. Thus
* when it then calls edit_refresh(), there is no danger of
* getting an infinite loop. */
edit_update(current, CENTER);
else {
int nlines = 0;
/* Don't make the cursor jump around the screen whilst updating */ /* Don't make the cursor jump around the screen whilst updating */
leaveok(edit, TRUE); leaveok(edit, TRUE);
editbot = edittop; editbot = edittop;
while (nlines < editwinrows) { while (nlines < editwinrows) {
update_line(editbot, current_x); update_line(editbot, current_x);
if (editbot == current)
currentcheck = 1;
nlines++; nlines++;
if (editbot->next == NULL) if (editbot->next == NULL)
break; break;
editbot = editbot->next; editbot = editbot->next;
} }
/* If noloop == 1, then we already did an edit_update without finishing
this function. So we don't run edit_update again */
if (!currentcheck && !noloop) {
/* Then current has run off the screen... */
edit_update(current, CENTER);
noloop = 1;
} else if (noloop)
noloop = 0;
while (nlines < editwinrows) { while (nlines < editwinrows) {
mvwaddstr(edit, nlines, 0, hblank); mvwaddstr(edit, nlines, 0, hblank);
nlines++; nlines++;
} }
/* What the hell are we expecting to update the screen if this
/* What the hell are we expecting to update the screen if this isn't isn't here? Luck?? */
here? Luck?? */
wrefresh(edit); wrefresh(edit);
leaveok(edit, FALSE); leaveok(edit, FALSE);
} }
}
/* /*
* Same as above, but touch the window first, so everything is redrawn. * Same as above, but touch the window first, so everything is redrawn.
@ -1137,8 +1124,8 @@ int statusq(int tabs, const shortcut *s, const char *def,
/* /*
* Ask a simple yes/no question on the statusbar. Returns 1 for Y, 0 * Ask a simple yes/no question on the statusbar. Returns 1 for Y, 0
* for N, 2 for All (if all is non-zero when passed in) and -1 for * for N, 2 for All (if all is nonzero when passed in) and -1 for abort
* abort (^C). * (^C).
*/ */
int do_yesno(int all, int leavecursor, const char *msg, ...) int do_yesno(int all, int leavecursor, const char *msg, ...)
{ {
@ -1148,10 +1135,8 @@ int do_yesno(int all, int leavecursor, const char *msg, ...)
const char *yesstr; /* String of yes characters accepted */ const char *yesstr; /* String of yes characters accepted */
const char *nostr; /* Same for no */ const char *nostr; /* Same for no */
const char *allstr; /* And all, surprise! */ const char *allstr; /* And all, surprise! */
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
MEVENT mevent; MEVENT mevent;
#endif
#endif #endif
/* Yes, no and all are strings of any length. Each string consists of /* Yes, no and all are strings of any length. Each string consists of
@ -1204,8 +1189,7 @@ int do_yesno(int all, int leavecursor, const char *msg, ...)
kbinput = wgetch(edit); kbinput = wgetch(edit);
switch (kbinput) { switch (kbinput) {
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
case KEY_MOUSE: case KEY_MOUSE:
/* Look ma! We get to duplicate lots of code from do_mouse!! */ /* Look ma! We get to duplicate lots of code from do_mouse!! */
@ -1232,7 +1216,6 @@ int do_yesno(int all, int leavecursor, const char *msg, ...)
ungetch(yesnosquare[mevent.y][mevent.x / (COLS / 6)]); ungetch(yesnosquare[mevent.y][mevent.x / (COLS / 6)]);
} }
break; break;
#endif
#endif #endif
case NANO_CONTROL_C: case NANO_CONTROL_C:
ok = -2; ok = -2;
@ -1436,12 +1419,10 @@ int do_help(void)
const char *ptr = help_text; const char *ptr = help_text;
switch (kbinput) { switch (kbinput) {
#ifndef DISABLE_MOUSE #if !defined(DISABLE_MOUSE) && defined(NCURSES_MOUSE_VERSION)
#ifdef NCURSES_MOUSE_VERSION
case KEY_MOUSE: case KEY_MOUSE:
do_mouse(); do_mouse();
break; break;
#endif
#endif #endif
case 27: case 27:
kbinput = wgetch(edit); kbinput = wgetch(edit);