mirror of
https://https.git.savannah.gnu.org/git/bash.git
synced 2026-06-27 23:53:18 +02:00
commit bash-20210211 snapshot
This commit is contained in:
@@ -9576,3 +9576,31 @@ builtins/read.def
|
||||
Fixes bug reported by Koichi Murase <myoga.murase@gmail.com>, but
|
||||
there may be a different fix coming
|
||||
|
||||
Makefile.in,builtins/Makefile.in
|
||||
- fix up dependencies, especially on builtins.h and builtext.h
|
||||
|
||||
|
||||
2/12
|
||||
----
|
||||
lib/readline/input.c
|
||||
- rl_read_key: if we set rl_done == 1, set RL_STATE_DONE as well
|
||||
Reported by Koichi Murase <myoga.murase@gmail.com>
|
||||
|
||||
lib/readline/isearch.c
|
||||
- _rl_search_getchar: only call _rl_read_mbstring if rl_read_key returns
|
||||
>= 0, avoid some work
|
||||
|
||||
lib/readline/vi_mode.c
|
||||
- _rl_vi_callback_change_char,_rl_vi_change_char: don't overwrite the
|
||||
last replacement string if _rl_vi_callback_getchar returns -1.
|
||||
It will likely make no difference, since the next read will return
|
||||
an error or EOF, but being careful
|
||||
- rl_vi_overstrike: if _rl_overwrite_char doesn't return 0, break out
|
||||
of the loop
|
||||
|
||||
lib/readline/text.c
|
||||
- _rl_overwrite_char: return 1 if _rl_read_mbstring returns < 0 so
|
||||
we don't try to insert garbage
|
||||
|
||||
bashline.c
|
||||
- posix_edit_macros: handle rl_read_key() returning <= 0
|
||||
|
||||
+19
-4
@@ -1206,7 +1206,7 @@ trap.o: general.h xmalloc.h bashtypes.h variables.h arrayfunc.h conftypes.h arra
|
||||
trap.o: quit.h ${BASHINCDIR}/maxpath.h unwind_prot.h dispose_cmd.h parser.h
|
||||
trap.o: make_cmd.h subst.h sig.h pathnames.h externs.h execute_cmd.h
|
||||
trap.o: signames.h $(DEFSRC)/common.h
|
||||
trap.o: ${DEFDIR}/builtext.h jobs.h
|
||||
trap.o: ${DEFDIR}/builtext.h builtins.h jobs.h
|
||||
unwind_prot.o: config.h bashtypes.h bashansi.h ${BASHINCDIR}/ansi_stdlib.h command.h ${BASHINCDIR}/stdc.h
|
||||
unwind_prot.o: general.h xmalloc.h unwind_prot.h quit.h sig.h
|
||||
unwind_prot.o: ${BASHINCDIR}/ocache.h ${BASHINCDIR}/chartypes.h error.h
|
||||
@@ -1283,18 +1283,24 @@ alias.o: ${BASHINCDIR}/chartypes.h
|
||||
|
||||
pcomplib.o: config.h bashansi.h ${BASHINCDIR}/ansi_stdlib.h bashtypes.h
|
||||
pcomplib.o: ${BASHINCDIR}/stdc.h hashlib.h pcomplete.h shell.h syntax.h
|
||||
pcomplib.o: bashjmp.h command.h general.h xmalloc.h error.h variables.h arrayfunc.h conftypes.h quit.h
|
||||
pcomplib.o: bashjmp.h command.h general.h xmalloc.h error.h variables.h
|
||||
pcomplib.o: arrayfunc.h conftypes.h quit.h
|
||||
pcomplib.o: unwind_prot.h dispose_cmd.h make_cmd.h subst.h sig.h pathnames.h
|
||||
pcomplib.o: externs.h ${BASHINCDIR}/maxpath.h assoc.h array.h
|
||||
pcomplib.o: ${BASHINCDIR}/posixjmp.h ${BASHINCDIR}/ocache.h ${BASHINCDIR}/chartypes.h
|
||||
|
||||
pcomplete.o: config.h bashansi.h ${BASHINCDIR}/ansi_stdlib.h bashtypes.h
|
||||
pcomplete.o: ${BASHINCDIR}/stdc.h hashlib.h pcomplete.h shell.h syntax.h
|
||||
pcomplete.o: bashjmp.h command.h general.h xmalloc.h error.h variables.h arrayfunc.h conftypes.h quit.h
|
||||
pcomplete.o: bashjmp.h command.h general.h xmalloc.h error.h variables.h
|
||||
pcomplete.o: execute_cmd.h pathexp.h arrayfunc.h conftypes.h quit.h trap.h
|
||||
pcomplete.o: jobs.h siglist.h bashline.h alias.h
|
||||
pcomplete.o: ${BASHINCDIR}/posixwait.h ${BASHINCDIR}/unionwait.h
|
||||
pcomplete.o: ${BASHINCDIR}/posixtime.h ${BASHINCDIR}/posixstat.h
|
||||
pcomplete.o: unwind_prot.h dispose_cmd.h make_cmd.h subst.h sig.h pathnames.h
|
||||
pcomplete.o: externs.h ${BASHINCDIR}/maxpath.h execute_cmd.h
|
||||
pcomplete.o: ${BASHINCDIR}/shmbutil.h ${BASHINCDIR}/shmbchar.h
|
||||
pcomplete.o: ${DEFDIR}/builtext.h
|
||||
pcomplete.o: builtins.h ${DEFDIR}/builtext.h ${DEFSRC}/common.h
|
||||
pcomplete.o: ${GLOB_LIBSRC}/glob.h ${GLOB_LIBSRC}/strmatch.h
|
||||
|
||||
# library support files
|
||||
|
||||
@@ -1352,6 +1358,10 @@ variables.o: $(RL_LIBSRC)/rltypedefs.h
|
||||
jobs.o: $(RL_LIBSRC)/keymaps.h $(RL_LIBSRC)/chardefs.h
|
||||
jobs.o: $(RL_LIBSRC)/readline.h $(RL_LIBSRC)/rlstdc.h
|
||||
jobs.o: $(RL_LIBSRC)/rltypedefs.h
|
||||
pcomplete.o: $(RL_LIBSRC)/rlconf.h
|
||||
pcomplete.o: $(RL_LIBSRC)/keymaps.h $(RL_LIBSRC)/rlstdc.h
|
||||
pcomplete.o: $(RL_LIBSRC)/chardefs.h $(RL_LIBSRC)/readline.h
|
||||
pcomplete.o: $(RL_LIBSRC)/rltypedefs.h ${RL_LIBSRC}/rlmbutil.h
|
||||
|
||||
shell.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
variables.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
@@ -1359,12 +1369,14 @@ subst.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
bashline.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
bashhist.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
y.tab.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
pcomplete.o: $(HIST_LIBSRC)/history.h $(HIST_LIBSRC)/rlstdc.h
|
||||
|
||||
bashline.o: $(TILDE_LIBSRC)/tilde.h
|
||||
bracecomp.o: $(TILDE_LIBSRC)/tilde.h
|
||||
execute_cmd.o: $(TILDE_LIBSRC)/tilde.h
|
||||
general.o: $(TILDE_LIBSRC)/tilde.h
|
||||
mailcheck.o: $(TILDE_LIBSRC)/tilde.h
|
||||
pcomplete.o: $(TILDE_LIBSRC)/tilde.h
|
||||
shell.o: $(TILDE_LIBSRC)/tilde.h
|
||||
subst.o: $(TILDE_LIBSRC)/tilde.h
|
||||
variables.o: $(TILDE_LIBSRC)/tilde.h
|
||||
@@ -1488,6 +1500,7 @@ builtins/declare.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.
|
||||
builtins/declare.o: shell.h syntax.h bashjmp.h ${BASHINCDIR}/posixjmp.h sig.h unwind_prot.h variables.h arrayfunc.h conftypes.h quit.h
|
||||
builtins/declare.o: dispose_cmd.h make_cmd.h subst.h externs.h ${BASHINCDIR}/stdc.h
|
||||
builtins/declare.o: $(DEFSRC)/bashgetopt.h pathnames.h flags.h
|
||||
builtins/declare.o: ${DEFDIR}/builtext.h
|
||||
builtins/echo.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.h xmalloc.h ${BASHINCDIR}/maxpath.h
|
||||
builtins/echo.o: shell.h syntax.h bashjmp.h ${BASHINCDIR}/posixjmp.h sig.h unwind_prot.h variables.h arrayfunc.h conftypes.h quit.h
|
||||
builtins/echo.o: dispose_cmd.h make_cmd.h subst.h externs.h ${BASHINCDIR}/stdc.h
|
||||
@@ -1512,6 +1525,7 @@ builtins/exit.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.h x
|
||||
builtins/exit.o: shell.h syntax.h bashjmp.h ${BASHINCDIR}/posixjmp.h sig.h unwind_prot.h variables.h arrayfunc.h conftypes.h quit.h
|
||||
builtins/exit.o: dispose_cmd.h make_cmd.h subst.h externs.h ${BASHINCDIR}/stdc.h
|
||||
builtins/exit.o: pathnames.h execute_cmd.h
|
||||
builtins/exit.o: ${DEFDIR}/builtext.h
|
||||
builtins/fc.o: bashtypes.h ${BASHINCDIR}/posixstat.h
|
||||
builtins/fc.o: bashansi.h ${BASHINCDIR}/ansi_stdlib.h builtins.h command.h ${BASHINCDIR}/stdc.h
|
||||
builtins/fc.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.h xmalloc.h ${BASHINCDIR}/maxpath.h
|
||||
@@ -1570,6 +1584,7 @@ builtins/pushd.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.h
|
||||
builtins/pushd.o: quit.h dispose_cmd.h make_cmd.h subst.h externs.h ${BASHINCDIR}/stdc.h
|
||||
builtins/pushd.o: shell.h syntax.h bashjmp.h ${BASHINCDIR}/posixjmp.h sig.h unwind_prot.h variables.h arrayfunc.h conftypes.h
|
||||
builtins/pushd.o: $(DEFSRC)/common.h pathnames.h
|
||||
builtins/pushd.o: ${DEFDIR}/builtext.h
|
||||
builtins/read.o: command.h config.h ${BASHINCDIR}/memalloc.h error.h general.h xmalloc.h ${BASHINCDIR}/maxpath.h
|
||||
builtins/read.o: quit.h dispose_cmd.h make_cmd.h subst.h externs.h ${BASHINCDIR}/stdc.h
|
||||
builtins/read.o: shell.h syntax.h bashjmp.h ${BASHINCDIR}/posixjmp.h sig.h unwind_prot.h variables.h arrayfunc.h conftypes.h
|
||||
|
||||
@@ -1028,6 +1028,8 @@ posix_edit_macros (count, key)
|
||||
char alias_name[3], *alias_value, *macro;
|
||||
|
||||
c = rl_read_key ();
|
||||
if (c <= 0)
|
||||
return 0;
|
||||
alias_name[0] = '_';
|
||||
alias_name[1] = c;
|
||||
alias_name[2] = '\0';
|
||||
|
||||
@@ -447,6 +447,8 @@ read_builtin (list)
|
||||
if (code)
|
||||
{
|
||||
sigalrm_seen = 0;
|
||||
sigprocmask (SIG_SETMASK, &prevset, (sigset_t *)0);
|
||||
|
||||
/* Tricky. The top of the unwind-protect stack is the free of
|
||||
input_string. We want to run all the rest and use input_string,
|
||||
so we have to save input_string temporarily, run the unwind-
|
||||
@@ -477,6 +479,7 @@ read_builtin (list)
|
||||
add_unwind_protect (bashline_reset_event_hook, (char *)NULL);
|
||||
}
|
||||
#endif
|
||||
sigprocmask (SIG_BLOCK, (sigset_t *)0, &prevset);
|
||||
falarm (tmsec, tmusec);
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -37,7 +37,7 @@ typedef struct _shtimer
|
||||
|
||||
procenv_t jmpenv;
|
||||
|
||||
void (*handler) (struct _shtimer *); /* XXX - unused right now */
|
||||
int (*tm_handler) (struct _shtimer *); /* called on timeout if set */
|
||||
PTR_T *data; /* reserved */
|
||||
} sh_timer;
|
||||
|
||||
|
||||
@@ -497,6 +497,7 @@ rl_read_key (void)
|
||||
if ((r = rl_gather_tyi ()) < 0) /* XXX - EIO */
|
||||
{
|
||||
rl_done = 1;
|
||||
RL_SETSTATE (RL_STATE_DONE);
|
||||
return (errno == EIO ? (RL_ISSTATE (RL_STATE_READCMD) ? READERR : EOF) : '\n');
|
||||
}
|
||||
else if (r > 0) /* read something */
|
||||
|
||||
@@ -318,7 +318,7 @@ _rl_search_getchar (_rl_search_cxt *cxt)
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
/* This ends up with C (and LASTC) being set to the last byte of the
|
||||
multibyte character. In most cases c == lastc == mb[0] */
|
||||
if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
|
||||
if (c >= 0 && MB_CUR_MAX > 1 && rl_byte_oriented == 0)
|
||||
c = cxt->lastc = _rl_read_mbstring (cxt->lastc, cxt->mb, MB_LEN_MAX);
|
||||
#endif
|
||||
|
||||
|
||||
+8
-25
@@ -222,6 +222,9 @@ _rl_handle_signal (int sig)
|
||||
switch (sig)
|
||||
{
|
||||
case SIGINT:
|
||||
/* We will end up blocking SIGTTOU while we are resetting the tty, so
|
||||
watch out for this if it causes problems. We could prevent this by
|
||||
setting block_sig to 1 without modifying SET. */
|
||||
_rl_reset_completion_state ();
|
||||
rl_free_line_state ();
|
||||
#if defined (READLINE_CALLBACKS)
|
||||
@@ -242,8 +245,11 @@ _rl_handle_signal (int sig)
|
||||
this even if we've been stopped on SIGTTOU, since we handle signals
|
||||
when we have returned from the signal handler and the signal is no
|
||||
longer blocked. */
|
||||
sigaddset (&set, SIGTTOU);
|
||||
block_sig = 1;
|
||||
if (block_sig == 0)
|
||||
{
|
||||
sigaddset (&set, SIGTTOU);
|
||||
block_sig = 1;
|
||||
}
|
||||
# endif
|
||||
#endif /* SIGTSTP */
|
||||
/* Any signals that should be blocked during cleanup should go here. */
|
||||
@@ -285,19 +291,6 @@ _rl_handle_signal (int sig)
|
||||
|
||||
/* We don't have to bother unblocking the signal because we are not
|
||||
running in a signal handler context. */
|
||||
#if 0
|
||||
#if defined (HAVE_POSIX_SIGNALS)
|
||||
/* Make sure this signal is not blocked when we resend it to the
|
||||
calling application. */
|
||||
sigemptyset (&set);
|
||||
sigprocmask (SIG_BLOCK, (sigset_t *)NULL, &set);
|
||||
sigdelset (&set, sig);
|
||||
#else /* !HAVE_POSIX_SIGNALS */
|
||||
# if defined (HAVE_BSD_SIGNALS)
|
||||
omask = sigblock (0);
|
||||
# endif /* HAVE_BSD_SIGNALS */
|
||||
#endif /* !HAVE_POSIX_SIGNALS */
|
||||
#endif
|
||||
|
||||
#if defined (__EMX__)
|
||||
signal (sig, SIG_ACK);
|
||||
@@ -311,16 +304,6 @@ _rl_handle_signal (int sig)
|
||||
|
||||
/* We don't need to modify the signal mask now that this is not run in
|
||||
a signal handler context. */
|
||||
#if 0
|
||||
/* Let the signal that we just sent through if it is blocked. */
|
||||
#if defined (HAVE_POSIX_SIGNALS)
|
||||
sigprocmask (SIG_SETMASK, &set, (sigset_t *)NULL);
|
||||
#else /* !HAVE_POSIX_SIGNALS */
|
||||
# if defined (HAVE_BSD_SIGNALS)
|
||||
sigsetmask (omask & ~(sigmask (sig)));
|
||||
# endif /* HAVE_BSD_SIGNALS */
|
||||
#endif /* !HAVE_POSIX_SIGNALS */
|
||||
#endif
|
||||
|
||||
rl_reset_after_signal ();
|
||||
}
|
||||
|
||||
@@ -919,8 +919,11 @@ _rl_overwrite_char (int count, int c)
|
||||
int k;
|
||||
|
||||
/* Read an entire multibyte character sequence to insert COUNT times. */
|
||||
k = 1;
|
||||
if (count > 0 && MB_CUR_MAX > 1 && rl_byte_oriented == 0)
|
||||
k = _rl_read_mbstring (c, mbkey, MB_LEN_MAX);
|
||||
if (k < 0)
|
||||
return 1;
|
||||
#endif
|
||||
|
||||
rl_begin_undo_group ();
|
||||
|
||||
@@ -2036,6 +2036,9 @@ _rl_vi_callback_change_char (_rl_callback_generic_arg *data)
|
||||
char mb[MB_LEN_MAX+1];
|
||||
|
||||
c = _rl_vi_callback_getchar (mb, MB_LEN_MAX);
|
||||
if (c < 0)
|
||||
return -1;
|
||||
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
|
||||
strncpy (_rl_vi_last_replacement, mb, MB_LEN_MAX);
|
||||
@@ -2044,9 +2047,6 @@ _rl_vi_callback_change_char (_rl_callback_generic_arg *data)
|
||||
_rl_vi_last_replacement[0] = c;
|
||||
_rl_vi_last_replacement[MB_LEN_MAX] = '\0'; /* XXX */
|
||||
|
||||
if (c < 0)
|
||||
return -1;
|
||||
|
||||
_rl_callback_func = 0;
|
||||
_rl_want_redisplay = 1;
|
||||
|
||||
@@ -2077,6 +2077,8 @@ rl_vi_change_char (int count, int key)
|
||||
else
|
||||
{
|
||||
c = _rl_vi_callback_getchar (mb, MB_LEN_MAX);
|
||||
if (c < 0)
|
||||
return -1;
|
||||
#ifdef HANDLE_MULTIBYTE
|
||||
if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
|
||||
strncpy (_rl_vi_last_replacement, mb, MB_LEN_MAX);
|
||||
@@ -2113,7 +2115,8 @@ rl_vi_overstrike (int count, int key)
|
||||
|
||||
if (count > 0)
|
||||
{
|
||||
_rl_overwrite_char (count, key);
|
||||
if (_rl_overwrite_char (count, key) != 0)
|
||||
return (1);
|
||||
vi_replace_count += count;
|
||||
}
|
||||
|
||||
|
||||
+41
-17
@@ -43,34 +43,51 @@
|
||||
extern int errno;
|
||||
#endif /* !errno */
|
||||
|
||||
#ifndef FREE
|
||||
#define FREE(s) do { if (s) free (s); } while (0)
|
||||
#endif
|
||||
|
||||
extern unsigned int falarm (unsigned int, unsigned int);
|
||||
|
||||
sh_timer *
|
||||
shtimer_alloc (void)
|
||||
{
|
||||
sh_timer *r;
|
||||
static void shtimer_zero (sh_timer *);
|
||||
|
||||
r = (sh_timer *)xmalloc (sizeof (sh_timer));
|
||||
shtimer_flush (r);
|
||||
return r;
|
||||
}
|
||||
|
||||
void
|
||||
shtimer_flush (sh_timer *t)
|
||||
static void
|
||||
shtimer_zero (sh_timer *t)
|
||||
{
|
||||
t->tmout.tv_sec = 0;
|
||||
t->tmout.tv_usec = 0;
|
||||
|
||||
t->fd = t->flags = t->alrmflag = 0;
|
||||
t->fd = -1;
|
||||
t->flags = t->alrmflag = 0;
|
||||
|
||||
t->alrm_handler = t->old_handler = 0;
|
||||
|
||||
memset (t->jmpenv, '\0', sizeof (t->jmpenv));
|
||||
|
||||
t->handler = 0;
|
||||
t->tm_handler = 0;
|
||||
t->data = 0;
|
||||
}
|
||||
|
||||
sh_timer *
|
||||
shtimer_alloc (void)
|
||||
{
|
||||
sh_timer *t;
|
||||
|
||||
t = (sh_timer *)xmalloc (sizeof (sh_timer));
|
||||
shtimer_zero (t);
|
||||
return t;
|
||||
}
|
||||
|
||||
void
|
||||
shtimer_flush (sh_timer *t)
|
||||
{
|
||||
/* The caller can manage t->data arbitrarily as long as it frees and sets
|
||||
t->data to 0 before calling this function. Otherwise, we do what we can
|
||||
to avoid memleaks. */
|
||||
FREE (t->data);
|
||||
shtimer_zero (t);
|
||||
}
|
||||
|
||||
void
|
||||
shtimer_dispose (sh_timer *t)
|
||||
{
|
||||
@@ -120,6 +137,7 @@ shtimer_unset (sh_timer *t)
|
||||
{
|
||||
set_signal_handler (SIGALRM, t->old_handler);
|
||||
t->flags &= ~SHTIMER_SIGSET;
|
||||
t->old_handler = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -163,7 +181,7 @@ shtimer_chktimeout (sh_timer *t)
|
||||
int
|
||||
shtimer_select (sh_timer *t)
|
||||
{
|
||||
int r;
|
||||
int r, nfd;
|
||||
sigset_t blocked_sigs, prevmask;
|
||||
struct timeval now, tv;
|
||||
fd_set readfds;
|
||||
@@ -191,6 +209,8 @@ shtimer_select (sh_timer *t)
|
||||
{
|
||||
if (t->flags & SHTIMER_LONGJMP)
|
||||
sh_longjmp (t->jmpenv, 1);
|
||||
else if (t->tm_handler)
|
||||
return ((*t->tm_handler) (t));
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
@@ -211,14 +231,16 @@ shtimer_select (sh_timer *t)
|
||||
sigemptyset (&prevmask);
|
||||
#endif /* !HAVE_PSELECT */
|
||||
|
||||
nfd = (t->fd >= 0) ? t->fd + 1 : 0;
|
||||
FD_ZERO (&readfds);
|
||||
FD_SET (t->fd, &readfds);
|
||||
if (t->fd >= 0)
|
||||
FD_SET (t->fd, &readfds);
|
||||
|
||||
#if defined (HAVE_PSELECT)
|
||||
r = pselect(t->fd + 1, &readfds, (fd_set *)0, (fd_set *)0, &ts, &blocked_sigs);
|
||||
r = pselect(nfd, &readfds, (fd_set *)0, (fd_set *)0, &ts, &blocked_sigs);
|
||||
#else
|
||||
sigprocmask (SIG_SETMASK, &blocked_sigs, &prevmask);
|
||||
r = select(t->fd + 1, &readfds, (fd_set *)0, (fd_set *)0, &tv);
|
||||
r = select(nfd, &readfds, (fd_set *)0, (fd_set *)0, &tv);
|
||||
sigprocmask (SIG_SETMASK, &prevmask, NULL);
|
||||
#endif
|
||||
|
||||
@@ -226,6 +248,8 @@ shtimer_select (sh_timer *t)
|
||||
return r; /* caller will handle */
|
||||
else if (r == 0 && (t->flags & SHTIMER_LONGJMP))
|
||||
sh_longjmp (t->jmpenv, 1);
|
||||
else if (r == 0 && t->tm_handler)
|
||||
return ((*t->tm_handler) (t));
|
||||
else
|
||||
return r;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user