title: Why expect is able to interact with `getpass` call?
body: <p>I am surprised about way of working <code>getpass()</code>. I am using it in <code>python</code>, however I am aware of the fact that it is about <a href="https://linux.die.net/man/3/getpass" rel="nofollow noreferrer">https://linux.die.net/man/3/getpass</a> call in reality. Moreover, I am aware of the fact that <code>ssh-add</code> uses it as well.  </p>
  
  <p>It is not easy to think about from many causes.  </p>
  
  <ol>
  1. 
  </ol>
  
  <blockquote>
    <p>The getpass() function opens /dev/tty (the controlling terminal of the process), outputs the string prompt, turns off echoing, reads one line (the "password"), restores the terminal state and closes /dev/tty again. </p>
  </blockquote>
  
  <p>What does it mean? It opens new terminal? <code>/dev/tty/</code> is opened before <code>getpass</code> call?<br>
  What does it mean that it restore terminal state?   </p>
  
  <ol start="2">
  <li>Why does expect can work with <code>ssh-add</code> or <code>getpass</code> while as <code>echo</code> does not?<br>
  Let's consider:  </li>
  </ol>
  
  <pre><code>#getpass.py 
  import getpass
  
  password = getpass.getpass()
  print password
  </code></pre>
  
  <hr>
  
  <pre><code>    [user@host ~]$ python2.7 ~/getpass.py 
      Password: 
      somepassword
  </code></pre>
  
  <p>It works. Why? I was able to type password from keybord so I guess that it has read from <code>stdin</code>. After all, the promise was about reading password <code>/dev/tty</code>, not <code>stdin</code>.  </p>
  
  <hr>
  
  <pre><code>[user@host ~]$ python2.7 ~/getpass.py # we allow it to wait for password and let check to new bash session
  [user@host ~]$ # new bash session
  [user@host ~]$ python2.7 ~/getpass.py
  [user@host ~]$ pgrep python
  21502
  [user@host ~]$ ls -al /proc/21502/fd
  razem 0
  dr-x------ 2 user wheel  0 04-14 17:55 .
  dr-xr-xr-x 9 user wheel  0 04-14 17:53 ..
  lrwx------ 1 user wheel 64 04-14 17:55 0 -&gt; /dev/pts/6
  lrwx------ 1 user wheel 64 04-14 17:55 1 -&gt; /dev/pts/6
  lrwx------ 1 user wheel 64 04-14 17:55 2 -&gt; /dev/pts/6
  lrwx------ 1 user wheel 64 04-14 17:55 3 -&gt; /dev/tty
  [user@host ~]$ echo 'some_password' &gt; /proc/21502/fd/0 #stdin of python process
  [user@host ~]$ echo 'some_password' &gt; /proc/21502/fd/3
  some_password # it prins some_password here, I know why (driver of `/dev/tty` check which process call it) 
  </code></pre>
  
  <p>It does <strong>not</strong> work.<br>
  I have no idea how <code>expect</code> tool can work (I checked it and it works). Can anyone explain it, please?</p>