- 06 11月, 2014 40 次提交
-
-
由 Peter Hurley 提交于
When hanging up one end of a pty pair, there may be waiting readers/writers on the other end which may not exit, preventing tty_ldisc_lock_pair() from acquiring the other side's ldisc lock. Only acquire this side's ldisc lock; although this will no longer prevent the other side from writing new input, that input will not be processing until after the ldisc hangup is complete. Reported-by: NSasha Levin <sasha.levin@oracle.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
tty_ldisc_lock(), tty_ldisc_unlock(), and tty_ldisc_lock_nested() are low-level aliases for the underlying lock mechanism. Rename with double underscore to allow for new, higher level functions with those names. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
When releasing one end of a pty pair, that end may just have written to the other, which the input processing worker, flush_to_ldisc(), is still working on but has not completed the copy to the other end's read buffer. So input may not appear to be available to a waiting reader but yet TTY_OTHER_CLOSED is now observed. The n_tty line discipline has worked around this by waiting for input processing to complete and then re-checking if input is available before exiting with -EIO. Since the tty/ldisc lock reordering, the wait for input processing to complete can now occur during final close before setting TTY_OTHER_CLOSED. In this way, a waiting reader is guaranteed to see input available (if any) before observing TTY_OTHER_CLOSED. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
With the revised tty lock order and lockdep annotation, claiming the pty slave lock is now safe while still holding the pty master lock. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The tty_unhangup() function is not defined. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Eliminate the requirement of specifying the tty lock nesting at lock time; instead, set the lock subclass for slave ptys at pty install (normal ttys and master ptys use subclass 0). Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
When releasing the master pty, the slave pty also needs to be locked to prevent concurrent tty count changes for the slave pty and to ensure that only one parallel master and slave release observe the final close, and proceed to destruct the pty pair. Conversely, when releasing the slave pty, locking the master pty is not necessary (since the master's state can be inferred by the slave tty count). Introduce tty_lock_slave()/tty_unlock_slave() which acquires/releases the tty lock of the slave pty. Remove tty_lock_pair()/tty_unlock_pair(). Dropping the tty_lock is no longer required to re-establish a stable lock order. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The local o_tty variable in tty_release() is now accessed only when closing the pty master. Set o_tty to slave pty when closing pty master, otherwise NULL; use o_tty != NULL as replacement for pty_master. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Passing the 'other' tty to tty_release_checks() only makes sense for a pty pair; make o_tty scope local instead. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Passing the 'other' tty to tty_ldisc_release() only makes sense for a pty pair; make o_tty function local instead. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Perform work flush for both ends of a pty pair within tty_flush_works(), rather than calling twice. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
When the slave side closes and its tty count is 0, the pty pair can be destroyed; the master side must have already closed for the slave side tty count to be 0. Thus, only the pty master close must check if the slave side has closed by checking the slave tty count. Remove the pre-computed closing flags and check the actual count(s). Regular ttys are unaffected by this change. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Holding the tty_lock() is necessary to prevent concurrent changes to the tty count that may cause it to differ from the open file list count. The tty_lock() is already held at all call sites. NB: Note that the check for the pty master tty count is safe because the slave's tty_lock() is held while decrementing the pty master tty count. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Releasing the tty locks while waiting for the tty wait queues to be empty is no longer necessary nor desirable. Prior to "tty: Don't take tty_mutex for tty count changes", dropping the tty locks was necessary to reestablish the correct lock order between tty_mutex and the tty locks. Dropping the global tty_mutex was necessary; otherwise new ttys could not have been opened while waiting. However, without needing the global tty_mutex held, the tty locks for the releasing tty can now be held through the sleep. The sanity check is for abnormal conditions caused by kernel bugs, not for recoverable errors caused by misbehaving userspace; dropping the tty locks only allows the tty state to get more sideways. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Holding tty_mutex is no longer required to serialize changes to the tty_count or to prevent concurrent opens of closing ttys; tty_lock() is sufficient. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Now that re-open is not permitted for a legacy BSD pty master, using TTY_CLOSING to indicate when a tty can be torn-down is no longer necessary. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Holding tty_mutex for a tty re-open is no longer necessary since "tty: Clarify re-open behavior of master ptys". Because the slave tty count is no longer accessed by tty_reopen(), holding tty_mutex to prevent concurrent final tty_release() of the slave pty is not required. As with "tty: Re-open /dev/tty without tty_mutex", holding a tty kref until the tty_lock is acquired is sufficient to ensure the tty has not been freed, which, in turn, is sufficient to ensure the tty_lock can be safely acquired and the tty count can be safely retrieved. A non-zero tty count with the tty lock held guarantees that release_tty() has not run and cannot run concurrently with tty_reopen(). Change tty_driver_lookup_tty() to acquire the tty kref, which allows the tty_mutex to be dropped before acquiring the tty lock. Dropping the tty_mutex before attempting the tty_lock allows other ttys to be opened and released, without needing this tty_reopen() to complete. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Opening /dev/tty (ie., the controlling tty for the current task) is always a re-open of the underlying tty. Because holding the tty_lock is sufficient for safely re-opening a tty, and because having a tty kref is sufficient for safely acquiring the tty_lock [1], tty_open_current_tty() does not require holding tty_mutex. Repurpose tty_open_current_tty() to perform the re-open itself and refactor tty_open(). [1] Analysis of safely re-opening the current tty w/o tty_mutex get_current_tty() gets a tty kref from the already kref'ed tty value of current->signal->tty while holding the sighand lock for the current task. This guarantees that the tty pointer returned from get_current_tty() points to a tty which remains referenceable while holding the kref. Although release_tty() may run concurrently, and thus the driver reference may be removed, release_one_tty() cannot have run, and won't while holding the tty kref. This, in turn, guarantees the tty_lock() can safely be acquired (since tty->magic and tty->legacy_mutex are still a valid dereferences). The tty_lock() also gets a tty kref to prevent the tty_unlock() from dereferencing a released tty. Thus, the kref returned from get_current_tty() can be released. Lastly, the first operation of tty_reopen() is to check the tty count. If non-zero, this ensures release_tty() is not running concurrently, and the driver references have not been removed. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Opening the slave BSD pty first already returns -EIO from the slave pty_open(), which in turn causes the newly installed tty pair to be released before returning from tty_open(). However, this can also cause a parallel master BSD pty open to fail because the pty pair destruction may already been taking place in tty_release(). Failing at driver->install() if the slave pty is opened first ensures that a pty master open cannot fail, because the driver tables will not have been updated so tty_driver_lookup_tty() won't find the master pty (and attempt to "re-open" it). In turn, this guarantees that any tty with a tty->count == 0 is in final close (rather than never opened). Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Although perhaps not obvious, the TTY_CLOSING bit is set when the tty count has been decremented to 0 (which occurs while holding tty_lock). The only other case when tty count is 0 during a re-open is when a legacy BSD pty master has been opened in parallel but after the pty slave, which is unsupported and returns an error. Thus !tty->count contains the complete set of degenerate conditions under which a tty open fails. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Re-opening master ptys is not allowed. Once opened and for the remaining lifetime of the master pty, its tty count is 1. If its tty count has dropped to 0, then the master pty was closed and TTY_CLOSING was set, and destruction may begin imminently. Besides the normal case of a legacy BSD pty master being re-opened (which always returns -EIO), this code is only reachable in 2 degenerate cases: 1. The pty master is the controlling terminal (this is possible through the TIOCSCTTY ioctl). pty masters are not designed to be controlling terminals and it's an oversight that tiocsctty() ever let that happen. The attempted open of /dev/tty will always fail. No known program does this. 2. The legacy BSD pty slave was opened first. The slave open will fail in pty_open() and tty_release() will commence. But before tty_release() claims the tty_mutex, there is a very small window where a parallel master open might succeed. In a test of racing legacy BSD slave and master parallel opens, where: slave open attempts: 10000 success:4527 failure:5473 master open attempts: 11728 success:5789 failure:5939 only 8 master open attempts would have succeeded reaching this code and successfully opened the master pty. This case is not possible with SysV ptys. Always return -EIO if a master pty is re-opened or the slave is opened first and the master opened in parallel (for legacy BSD ptys). Furthermore, now that changing the slave's count is not required, the tty_lock is sufficient for preventing concurrent changes to the tty being re-opened (or failing re-opening). Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Now that tty_ldisc_hangup() does not drop the tty lock, it is no longer possible to observe TTY_HUPPING while holding the tty lock on another cpu. Remove TTY_HUPPING bit definition. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Dropping the tty lock to acquire the tty->ldisc_sem allows several race conditions (such as hangup while changing the ldisc) which requires extra states and testing. The ldisc_sem->tty_lock lock order has not been required since tty buffer ownership was moved to tty_port. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The tty->ldisc_sem write lock is sufficient for serializing changes to tty->ldisc; holding the tty lock is not required. Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Mike Skoog 提交于
Added recognition of EndRun Technologies PCIe PTP slave card and setup two ttySx ports for communication with the card for retrieval of PTP based time and to communicate with the card's Linux OS. Signed-off-by: NMike Skoog <mskoog@endruntechnologies.com> Signed-off-by: NMike Korreng <mkorreng@endruntechnologies.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The stale comment refers to lock behavior which was eliminated in commit 6d76bd26, n_tty: Make N_TTY ldisc receive path lockless. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Packet mode can only be set for a pty master, and a pty master is always in raw mode since its termios cannot be changed. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The pty master read() can miss the wake up for a packet mode status change. For example, CPU 0 | CPU 1 n_tty_read() | n_tty_packet_mode_flush() ... | . if (packet & link->ctrl_status) { | . /* no new ctrl_status ATM */ | . | spin_lock | ctrl_status |= TIOCPKT_FLUSHREAD | spin_unlock | wake_up(link->read_wait) } | set_current_state(TASK_INTERRUPTIBLE) | ... | The pty master read() will now sleep (assuming there is no input) having missed the read_wait wakeup. Set the task state before the condition test. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Updates to the packet mode enable require holding the ctrl_lock; the serialization prevents corruption of adjacent fields. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Because pty_set_pktmode() does not claim the slave's ctrl_lock to clear ->ctrl_status (to avoid unnecessary lock nesting), pty_set_pktmode() may accidentally erase new ->ctrl_status updates. For example, CPU 0 | CPU 1 pty_set_pktmode() | pty_start() spin_lock(master's ctrl_lock) | tty->packet = 1 | | if (tty->link->packet) | spin_lock(slave's ctrl_lock) | tty->ctrl_status = TIOCPKT_START tty->link->ctrl_status = 0 | Ensure the clear of ->ctrl_status occurs before packet mode is set (and observable on another cpu). Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The slave's ctrl_lock serializes updates to the ctrl_status field only, whereas the master's ctrl_lock serializes updates to the packet mode enable (ie., the master does not have ctrl_status and the slave does not have packet mode). Thus, claiming the slave's ctrl_lock to access ->packet is useless. Unlocked reads of ->packet are already smp-safe. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Interrupts are enabled in the n_tty_read() loop, ioctl(TIOCPKT) and pty driver flush_buffer() routine; no need to save and restore local interrupt state. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The tty driver's set_termios() method is called with interrupts enabled; there is no need to save and restore the local interrupt state. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Packet mode is unique to the pty driver; move the packet mode state change code from the generic tty ioctl handler to the pty driver. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The pty master's termios should never be set; currently, all code paths which call the driver's set_termios() method ensure that the pty slave's termios is being set. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The session and foreground process group pid references will be non-NULL if tiocsctty() is stealing the controlling tty from another session (ie., arg == 1 in tiocsctty()). Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Setting the controlling terminal for a session occurs with either the first open of a non-pty master tty or with ioctl(TIOCSCTTY). Since only the session leader can set the controlling terminal for a session (and the session leader cannot change), it is not necessary to prevent a process from attempting to set different ttys as the controlling terminal concurrently. So it's only necessary to prevent the same tty from becoming the controlling terminal for different session leaders. The tty_lock() is sufficient to prevent concurrent proc_set_tty() for the same tty. Remove the tty_mutex lock region; add tty_lock() to tiocsctty(). While this may appear to allow a race condition between opening the controlling tty via tty_open_current_tty() and stealing the controlling tty via ioctl(TIOCSCTTY, 1), that race condition already existed. Even if the tty_mutex prevented stealing the controlling tty while tty_open_current_tty() returned the original controlling tty, it cannot prevent stealing the controlling tty before tty_open() returns. Thus, tty_open() could already return a no-longer-controlling tty when opening /dev/tty. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
tiocspgrp() is the lone caller of session_of_pgrp(); relocate and limit to file scope. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
Claim a read lock on the tasklist_lock while setting the controlling terminal for the session leader. This fixes multiple races: 1. task_pgrp() and task_session() cannot be safely dereferenced, such as passing to get_pid(), without holding either rcu_read_lock() or tasklist_lock 2. setsid() unwisely allows any thread in the thread group to make the thread group leader the session leader; this makes the unlocked reads of ->signal->leader and signal->tty potentially unordered, stale or even have spurious values. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-
由 Peter Hurley 提交于
The tty parameter to __proc_set_tty() cannot be NULL; all call sites have already dereferenced tty. Signed-off-by: NPeter Hurley <peter@hurleysoftware.com> Reviewed-by: NAlan Cox <alan@linux.intel.com> Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
-