More fixes for executeCommand...
--- a/AbstractOperatingSystem.st Wed Jul 09 14:56:27 2003 +0200
+++ b/AbstractOperatingSystem.st Wed Jul 09 21:02:52 2003 +0200
@@ -866,7 +866,10 @@
extra pipes and shuffler processes are created, which stuff the data into
those internal stream(s).
Nil stream args will execute the command connected to ST/X's standard input, output or
- error resp. - i.e. usually, i/o will be from/to the terminal"
+ error resp. - i.e. usually, i/o will be from/to the terminal.
+
+ Set lineWise to true, if both error and output is sent to the same stream
+ and you don't want lines to be mangled."
|pid exitStatus sema pIn pOut pErr pAux externalInStream externalOutStream externalErrStream externalAuxStream
shuffledInStream shuffledOutStream shuffledErrStream shuffledAuxStream
@@ -927,12 +930,13 @@
pAux := ExternalStream makePipe.
auxStreamToClose := externalAuxStream := pAux at:1.
shuffledAuxStream := pAux at:2.
+ shuffledAuxStream buffered:false.
"/ start a reader process, shuffling data from the given
"/ auxStream to the pipe (which is connected to the commands aux)
auxShufflerProcess := [
[
- [anAuxStream atEnd] whileFalse:[
+ [anAuxStream readWait; atEnd] whileFalse:[
self shuffleFrom:anAuxStream to:shuffledAuxStream lineWise:false.
shuffledAuxStream flush
]
@@ -1049,196 +1053,9 @@
!
executeCommand:aCommandString inputFrom:anInStream outputTo:anOutStream errorTo:anErrStream auxFrom:anAuxStream inDirectory:dirOrNil lineWise:lineWise onError:aBlock
- "execute the unix command specified by the argument, aCommandString.
- The commandString is passed to a shell for execution - see the description of
- 'sh -c' in your UNIX manual.
- Return true if successful, or the value of aBlock if not.
- If not successfull, aBlock is called with an OsProcessStatus
- (containing the exit status) as argument.
- The given in, out and err streams may be arbitrary (Smalltalk-) streams;
- if any is not an external stream (which is required by the command),
- extra pipes and shuffler processes are created, which stuff the data into
- those internal stream(s).
- Nil stream args will execute the command connected to ST/X's standard input, output or
- error resp. - i.e. usually, i/o will be from/to the terminal"
-
- |pid exitStatus sema pIn pOut pErr pAux externalInStream externalOutStream externalErrStream externalAuxStream
- shuffledInStream shuffledOutStream shuffledErrStream shuffledAuxStream
- inputShufflerProcess outputShufflerProcess errorShufflerProcess auxShufflerProcess stopShufflers
- inStreamToClose outStreamToClose errStreamToClose auxStreamToClose terminateLock|
-
- terminateLock := Semaphore forMutualExclusion.
- ((externalInStream := anInStream) notNil
- and:[externalInStream isExternalStream not]) ifTrue:[
- pIn := ExternalStream makePipe.
- inStreamToClose := externalInStream := pIn at:1.
- shuffledInStream := pIn at:2.
- shuffledInStream buffered:false.
-
- "/ start a reader process, shuffling data from the given
- "/ inStream to the pipe (which is connected to the commands input)
- inputShufflerProcess := [
- [
- [anInStream atEnd] whileFalse:[
- self shuffleFrom:anInStream to:shuffledInStream lineWise:lineWise.
- shuffledInStream flush
- ]
- ] ensure:[
- shuffledInStream close
- ]
- ] forkNamed:'cmd input shuffler'.
- ].
- ((externalOutStream := anOutStream) notNil
- and:[externalOutStream isExternalStream not]) ifTrue:[
- pOut := ExternalStream makePipe.
- shuffledOutStream := (pOut at:1).
- outStreamToClose := externalOutStream := pOut at:2.
- lineWise ifTrue:[shuffledOutStream buffered:false].
- outputShufflerProcess :=
- [
- self shuffleAllFrom:shuffledOutStream to:anOutStream lineWise:lineWise lockWith:terminateLock.
- ] forkNamed:'cmd output shuffler'.
- ].
- (externalErrStream := anErrStream) notNil ifTrue:[
- anErrStream == anOutStream ifTrue:[
- externalErrStream := externalOutStream
- ] ifFalse:[
- anErrStream isExternalStream ifFalse:[
- pErr := ExternalStream makePipe.
- shuffledErrStream := (pErr at:1).
- errStreamToClose := externalErrStream := pErr at:2.
-
- lineWise ifTrue:[shuffledErrStream buffered:false].
- errorShufflerProcess :=
- [
- self shuffleAllFrom:shuffledErrStream to:anErrStream lineWise:lineWise lockWith:terminateLock.
- ] forkNamed:'cmd err-output shuffler'.
- ]
- ]
- ].
- ((externalAuxStream := anAuxStream) notNil
- and:[externalAuxStream isExternalStream not]) ifTrue:[
- pAux := ExternalStream makePipe.
- auxStreamToClose := externalAuxStream := pAux at:1.
- shuffledAuxStream := pAux at:2.
-
- "/ start a reader process, shuffling data from the given
- "/ auxStream to the pipe (which is connected to the commands aux)
- auxShufflerProcess := [
- [
- [anAuxStream atEnd] whileFalse:[
- self shuffleFrom:anAuxStream to:shuffledAuxStream lineWise:false.
- shuffledAuxStream flush
- ]
- ] ensure:[
- shuffledAuxStream close
- ]
- ] forkNamed:'cmd aux shuffler'.
- ].
-
- sema := Semaphore new name:'OS command wait'.
- pid := Processor
- monitor:[
- self
- startProcess:aCommandString
- inputFrom:externalInStream
- outputTo:externalOutStream
- errorTo:externalErrStream
- auxFrom:externalAuxStream
- inDirectory:dirOrNil
- ]
- action:[:status |
- status stillAlive ifFalse:[
- exitStatus := status.
- sema signal.
- self closePid:pid
- ]
- ].
-
- inStreamToClose notNil ifTrue:[
- inStreamToClose close
- ].
- errStreamToClose notNil ifTrue:[
- errStreamToClose close
- ].
- outStreamToClose notNil ifTrue:[
- outStreamToClose close
- ].
- auxStreamToClose notNil ifTrue:[
- auxStreamToClose close
- ].
-
- stopShufflers := [
- inputShufflerProcess notNil ifTrue:[
- terminateLock critical:[inputShufflerProcess terminate].
- inputShufflerProcess waitUntilTerminated
- ].
- auxShufflerProcess notNil ifTrue:[
- terminateLock critical:[auxShufflerProcess terminate].
- auxShufflerProcess waitUntilTerminated
- ].
- outputShufflerProcess notNil ifTrue:[
- terminateLock critical:[outputShufflerProcess terminate].
- outputShufflerProcess waitUntilTerminated.
- self shuffleRestFrom:shuffledOutStream to:anOutStream lineWise:lineWise.
- shuffledOutStream close.
- ].
- errorShufflerProcess notNil ifTrue:[
- terminateLock critical:[errorShufflerProcess terminate].
- errorShufflerProcess waitUntilTerminated.
- self shuffleRestFrom:shuffledErrStream to:anErrStream lineWise:lineWise.
- shuffledErrStream close.
- ].
- ].
-
- pid notNil ifTrue:[
- [
- sema wait.
- ] ifCurtailed:[
- "/ terminate the os-command (and all of its forked commands)
- self terminateProcessGroup:pid.
- self terminateProcess:pid.
- self closePid:pid.
- stopShufflers value.
- ]
- ] ifFalse:[
- exitStatus := self osProcessStatusClass processCreationFailure
- ].
- stopShufflers value.
- exitStatus success ifFalse:[
- ^ aBlock value:exitStatus
- ].
- ^ true
-
- "
- |outStream errStream|
-
- outStream := '' writeStream.
-
- OperatingSystem executeCommand:'ls -l'
- inputFrom:'abc' readStream
- outputTo:outStream
- errorTo:nil
- inDirectory:nil
- lineWise:true
- onError:[:exitStatus | ^ false].
- outStream contents
- "
-
- "
- |outStream errStream|
-
- outStream := '' writeStream.
-
- OperatingSystem executeCommand:'gpg -s --batch --no-tty --passphrase-fd 0 /tmp/passwd'
- inputFrom:'bla' readStream
- outputTo:outStream
- errorTo:nil
- inDirectory:nil
- lineWise:true
- onError:[:exitStatus | false].
- outStream contents
- "
+ ^ self executeCommand:aCommandString inputFrom:anInStream outputTo:anOutStream
+ errorTo:anErrStream auxFrom:anAuxStream environment:nil
+ inDirectory:dirOrNil lineWise:lineWise onError:aBlock
!
executeCommand:aCommandString inputFrom:anInStream outputTo:anOutStream errorTo:anErrStream inDirectory:dirOrNil lineWise:lineWise onError:aBlock
@@ -4652,7 +4469,7 @@
!AbstractOperatingSystem class methodsFor:'documentation'!
version
- ^ '$Header: /cvs/stx/stx/libbasic/AbstractOperatingSystem.st,v 1.97 2003-07-08 20:34:17 stefan Exp $'
+ ^ '$Header: /cvs/stx/stx/libbasic/AbstractOperatingSystem.st,v 1.98 2003-07-09 19:02:52 stefan Exp $'
! !
AbstractOperatingSystem initialize!