Date: Mon, 6 Oct 1997 22:52:58 BST From: Michael Ryan <mike@NetworX.ie> To: FreeBSD Bugs <bugs@freebsd.org> Subject: sprintf() and UUCP locking Message-ID: <ECS9710062258A@NetworX.ie>
next in thread | raw e-mail | index | archive | help
Probably nothing major here, but I came across three problems with
slattach in the FreeBSD 2.2.2 release:
(1) It links in /usr/src/sbin/startslip/uucplock.c for UUCP-style
locking, instead of using /usr/lib/libutil. (The Makefile
specifies -lutil alright, but this won't have any effect because
../startslip/uucplock.c is linked.
(2) The uu_lock() code which slattach subsequently uses, makes use
of sprintf() instead of snprintf() as with the /usr/lib/libutil
code. I know that slattach doesn't run suid-root but, from a
purist viewpoint, it shouldn't use sprintf().
Of course, startslip suffers the same problems as slattach.
My solution was to edit the Makefile and remove the reference to
startslip's uucplock.c:
---Cut here
sam:slattach# diff -c Makefile.orig Makefile
*** Makefile.orig Wed Sep 20 13:56:23 1995
--- Makefile Mon Oct 6 18:03:17 1997
***************
*** 1,14 ****
# @(#)Makefile 5.4 (Berkeley) 5/11/90
#
# $Header: /home/ncvs/src/sbin/slattach/Makefile,v 1.6 1995/09/20 12:56:23
ache Exp $
PROG= slattach
! SRCS= slattach.c uucplock.c
MAN8= slattach.8
MLINKS= slattach.8 slip.8
LDADD= -lutil
DPADD= ${LIBUTIL}
-
- .PATH: ${.CURDIR}/../startslip
.include <bsd.prog.mk>
--- 1,16 ----
# @(#)Makefile 5.4 (Berkeley) 5/11/90
#
# $Header: /home/ncvs/src/sbin/slattach/Makefile,v 1.6 1995/09/20 12:56:23
ache Exp $
+ #
+ #
+ # mr971006 Use standard uu_lock(); not one in 'startslip' package.
+ #
PROG= slattach
! SRCS= slattach.c
MAN8= slattach.8
MLINKS= slattach.8 slip.8
LDADD= -lutil
DPADD= ${LIBUTIL}
.include <bsd.prog.mk>
---End cut here
(3) When slattach runs (with the -L flag, the -z flag and -r flag), mgetty
goes apeshite. What's wrong is that, eventhough slattach uses UUCP locks
(which mgetty depends on), it fails to use them 'properly' as follows:
(a) mgetty starts, acquires the lock, inits the modem and releases
the lock.
(b) slattach starts subsequently. It acquires the lock in
acquire_line().
(c) Because redial_on_startup is true, sighup_handler() is called
from main().
(d) In sighup_handler(), the lock is released.
(e) The redial_cmd command is executed. This, in my case, is a
'chat' script which dials the remote location and completes the
SLIP login.
(f) The lock is re-acquired. (Note that acquire_line() is called as
well, but it doesn't have any bearing on the problem.)
The problem lies in steps (d) - (f), namely the lock has been removed for
the duration that the external redial program is executing.
Because of the way mgetty works, its select() call returns when chat starts
writing to the port. It then checks for the existence of the lock file
and, because it's not there (slattach has just released it) mgetty assumes
the port activity is due to an incoming call! mgetty then goes into a
hopeless loop of trying to set modem parameters, acquire its own lock on
the port and what not. Meanwhile, slattach tries to acquire the lock when
the redial command finishes, but probably can't because mgetty has created
the lock file.
My solution, was to simply disable the uu_unlock() and uu_lock() calls in
sighup_handler(); see below. This should be sufficient, although there is
the problem that the redial command may want to acquire the lock itself.
In this case, the -L flag couldn't be used with slattach, in which case
mgetty would run into the same problem after the redial command has
completed and SLIP datagrams started flowing. No clean solution here...
---Cut here
sam:slattach# diff -c slattach.c.orig slattach.c
*** slattach.c.orig Tue Mar 12 23:14:45 1996
--- slattach.c Mon Oct 6 18:39:02 1997
***************
*** 34,39 ****
--- 34,45 ----
* SUCH DAMAGE.
*/
+ /*
+ * mr971006 Disable device unlocking during execution of redial_cmd.
+ * <mike@NetworX.ie>
+ *
+ */
+
#ifndef lint
static char copyright[] =
"@(#) Copyright (c) 1988 Regents of the University of California.\n\
***************
*** 461,473 ****
--- 467,482 ----
dev, unit, redial_cmd);
acquire_line(); /* reopen dead line */
setup_line(CLOCAL);
+ #if 0
if (locked) {
if (uucp_lock)
uu_unlock(dvname); /* for redial */
locked = 0;
}
+ #endif
if (system(redial_cmd))
goto again;
+ #if 0
if (uucp_lock) {
if (uu_lock(dvname)) {
syslog(LOG_ERR, "can't relock %s after %s, abort
ing",
***************
*** 476,481 ****
--- 485,491 ----
}
locked = 1;
}
+ #endif
/* Now check again for carrier (dial command is done): */
if (!(modem_control & CLOCAL)) {
tty.c_cflag &= ~CLOCAL;
---End of cut here
Bye,
Mike
<mike@NetworX.ie>
---
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?ECS9710062258A>
