56
56
<p>Specialized pipe class for use by <code>executeCommand</code>.</p>
57
57
<p>The <a href="CedarBackup2.util-module.html#executeCommand"
58
58
class="link"><code>executeCommand</code></a> function needs a specialized
59
way of interacting with a pipe that isn't satisfied by the standard
60
<code>Popen3</code> and <code>Popen4</code> classes in
61
<code>popen2</code>. First, <code>executeCommand</code> only reads from
62
the pipe, and never writes to it. Second, <code>executeCommand</code>
63
needs a way to discard all output written to <code>stderr</code>, as a
64
means of simulating the shell <code>2>/dev/null</code> construct.</p>
65
<p>This class inherits from <code>Popen4</code>. If the
66
<code>ignoreStderr</code> flag is passed in as <code>False</code>, then
67
the standard <code>Popen4</code> constructor will be called and
68
<code>stdout</code> and <code>stderr</code> will be intermingled in the
70
<p>Otherwise, we'll call a custom version of the constructor which was
71
basically stolen from the real constructor in
72
<code>python2.3/Lib/popen2.py</code>. This custom constructor will
73
redirect the <code>stderr</code> file descriptor to
74
<code>/dev/null</code>. I've done this based on a suggestion from Donn
75
Cave on comp.lang.python.</p>
76
<p>In either case, the <code>tochild</code> file object is always closed
77
before returning from the constructor, since it is never needed by
78
<code>executeCommand</code>.</p>
79
<p>I really wish there were a prettier way to do this. Unfortunately, I
80
need access to the guts of the constructor implementation because of the
81
way the pipe process is forked, etc. It doesn't work to just call the
82
superclass constructor and then modify a few things afterwards. Even
83
worse, I have to access private <code>popen2</code> module members
84
<code>_cleanup</code> and <code>_active</code> in order to duplicate the
86
Hopefully this whole thing will continue to work properly. At least we
87
can use the other <code>subprocess.Popen</code>-based implementation when
88
that class is available.
59
way of interacting with a pipe. First, <code>executeCommand</code> only
60
reads from the pipe, and never writes to it. Second,
61
<code>executeCommand</code> needs a way to discard all output written to
62
<code>stderr</code>, as a means of simulating the shell
63
<code>2>/dev/null</code> construct.</p>
64
All of this functionality is provided (in Python 2.4 or later) by the
65
<code>subprocess.Popen</code> class, so when that class is available,
66
we'll use it. Otherwise, there's another implementation based on
67
<code>popen2.Popen4</code>, which unfortunately only works on UNIX
91
<p><b>Copyright:</b> Some of this code, prior to customization, was originally part of the
92
Python 2.3 codebase. Python code is copyright (c) 2001, 2002 Python
93
Software Foundation; All Rights Reserved.
97
72
<!-- =========== START OF METHOD SUMMARY =========== -->
98
73
<table class="summary" border="1" cellpadding="3" cellspacing="0" width="100%" bgcolor="white">
105
80
<span class=summary-sig-arg>ignoreStderr</span>)</span></code>
107
82
<tr bgcolor="#e8f0f8" class="group">
108
<th colspan="2"> Inherited from Popen3</th></tr>
109
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
110
<td><code><span class="summary-sig"><a href="popen2.Popen3-class.html#poll" class="summary-sig-name"><code>poll</code></a>(<span class=summary-sig-arg>self</span>)</span></code>
112
Return the exit status of the child process if it has finished, or -1
113
if it hasn't finished yet.</td></tr>
114
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
115
<td><code><span class="summary-sig"><a href="popen2.Popen3-class.html#wait" class="summary-sig-name"><code>wait</code></a>(<span class=summary-sig-arg>self</span>)</span></code>
117
Wait for and return the exit status of the child process.</td></tr>
121
<!-- =========== START OF CLASS VARIABLE SUMMARY =========== -->
122
<table class="summary" border="1" cellpadding="3" cellspacing="0" width="100%" bgcolor="white">
123
<tr bgcolor="#70b0f0" class="summary">
124
<th colspan="2">Class Variable Summary</th></tr>
125
<tr bgcolor="#e8f0f8" class="group">
126
<th colspan="2"> Inherited from Popen4</th></tr>
127
<tr><td align="right" valign="top" width="15%"><font size="-1"><code>NoneType</code></font></td>
128
<td><b><a href="popen2.Popen4-class.html#childerr"><code>childerr</code></a></b> = <span title="None">None </span></td></tr>
129
<tr bgcolor="#e8f0f8" class="group">
130
<th colspan="2"> Inherited from Popen3</th></tr>
131
<tr><td align="right" valign="top" width="15%"><font size="-1"><code>int</code></font></td>
132
<td><b><a href="popen2.Popen3-class.html#sts"><code>sts</code></a></b> = <span title="-1">-1 </span></td></tr>
83
<th colspan="2"> Inherited from Popen</th></tr>
84
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
85
<td><code><span class="summary-sig"><a href="subprocess.Popen-class.html#communicate" class="summary-sig-name"><code>communicate</code></a>(<span class=summary-sig-arg>self</span>,
86
<span class=summary-sig-arg>input</span>)</span></code>
88
Interact with process: Send data to stdin.</td></tr>
89
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
90
<td><code><span class="summary-sig"><a href="subprocess.Popen-class.html#poll" class="summary-sig-name"><code>poll</code></a>(<span class=summary-sig-arg>self</span>)</span></code>
92
Check if child process has terminated.</td></tr>
93
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
94
<td><code><span class="summary-sig"><a href="subprocess.Popen-class.html#wait" class="summary-sig-name"><code>wait</code></a>(<span class=summary-sig-arg>self</span>)</span></code>
96
Wait for child process to terminate.</td></tr>
97
<tr bgcolor="#e8f0f8" class="group">
98
<th colspan="2"> Inherited from object</th></tr>
99
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
100
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__delattr__" class="summary-sig-name"><code>__delattr__</code></a>(<span class="summary-sig-vararg">...</span>)</span></code>
102
x.__delattr__('name') <==> del x.name</td></tr>
103
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
104
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__getattribute__" class="summary-sig-name"><code>__getattribute__</code></a>(<span class="summary-sig-vararg">...</span>)</span></code>
106
x.__getattribute__('name') <==> x.name</td></tr>
107
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
108
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__hash__" class="summary-sig-name"><code>__hash__</code></a>(<span class=summary-sig-arg>x</span>)</span></code>
110
x.__hash__() <==> hash(x)</td></tr>
111
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
112
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__new__" class="summary-sig-name"><code>__new__</code></a>(<span class=summary-sig-arg>T</span>,
113
<span class=summary-sig-arg>S</span>,
114
<span class="summary-sig-vararg">...</span>)</span></code>
116
T.__new__(S, ...) -> a new object with type S, a subtype of T</td></tr>
117
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
118
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__reduce__" class="summary-sig-name"><code>__reduce__</code></a>(<span class="summary-sig-vararg">...</span>)</span></code>
120
helper for pickle</td></tr>
121
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
122
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__reduce_ex__" class="summary-sig-name"><code>__reduce_ex__</code></a>(<span class="summary-sig-vararg">...</span>)</span></code>
124
helper for pickle</td></tr>
125
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
126
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__repr__" class="summary-sig-name"><code>__repr__</code></a>(<span class=summary-sig-arg>x</span>)</span></code>
128
x.__repr__() <==> repr(x)</td></tr>
129
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
130
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__setattr__" class="summary-sig-name"><code>__setattr__</code></a>(<span class="summary-sig-vararg">...</span>)</span></code>
132
x.__setattr__('name', value) <==> x.name = value</td></tr>
133
<tr><td align="right" valign="top" width="15%"><font size="-1"> </font></td>
134
<td><code><span class="summary-sig"><a href="__builtin__.object-class.html#__str__" class="summary-sig-name"><code>__str__</code></a>(<span class=summary-sig-arg>x</span>)</span></code>
136
x.__str__() <==> str(x)</td></tr>