On Thu, Jan 14, 2016 at 3:44 PM, Ferlicot D. Cyril <cyril.ferlicot@gmail.com
wrote:
Le 14/01/2016 19:33, Mariano Martinez Peck a écrit :
Dear all,
I am happy to tell you I have a first prototype of the tool for executing OS processes:
https://github.com/marianopeck/OSSubprocess
As I said many times, the main idea was to be as much as possible FFI-based, only for executing OS commands and, from my point of view, a better end-user API. Also, as for the first step, I had to focus on Linux/OSX.
I would like to thank Pharo Consortium for the sponsor of this development effort. Here is the first milestone!
There are many things on my to-do but I think the code is ready for some usage, testing, code review and feedback!
All classes and all methods have comments and I have quite some unit tests. All tests are green in my OSX and a CentOS box.
*Important: you CANNOT have OSProcess installed in the same image as OSSubprocess. This is because I am reusing his SIGCHLD handler and for the time being both cannot coexist. *
Keep in mind that the tool may be unstable and that MAY mean a VM crash. So use with care, mostly the first time. If all tests passes, then there are much less chances of something going bad.
Important disclaimer: my tool (OSSubproccess from now onward) is HIGHLY influenced by a subset of the OSProcess project. There are parts which I even simply copied and adapted them (OSSPipe, OSSAttachableStream, OSSUnixProcessExitStatus). Other parts, I took them as inspiration (the idea of ThisOSProcess representing the VM process, the child watcher, and many others). In addition, I AM STILL USING (maybe as a first step?) some of the OSProcess PLUGIN (not OSProcess image side), such as the SIGCHLD handler or the creation of pipes.
In github url you have all the documentation of the project, included how to install it and use it.
*Finally, if you test it in a OS different than OSX and CentOS please share with me the results (about the tests).* Tomorrow the ConfigurationOf should also appear in the Catalog of Pharo 5.0.
Any feedback is appreciated.
Best,
-- Mariano http://marianopeck.wordpress.com
Hi,
Thank you for your work!
In Windows seven I got an error on loading.
Yes, sorry, no windows for the moment. Should work in OSX, Linux and other's Unix* as far as I can think of. At some point we may unify an API with ProcessWrapper but not right now (at least from my side).
Executed code in Pharo 5:
Metacello new configuration: 'OSSubprocess'; repository: 'github://marianopeck/OSSubprocess:master/repository'; version: #stable; load.
Stack:
ExternalLibraryFunction(Object)>>error: ExternalLibraryFunction(Object)>>externalCallFailed ExternalLibraryFunction(ExternalFunction)>>invokeWithArguments: OSSUnixSystemAccessor>>primitiveGetpid FFICalloutAPI>>function:module: OSSUnixSystemAccessor(Object)>>ffiCall: OSSUnixSystemAccessor>>primitiveGetpid OSSUnixSystemAccessor>>getPid OSSVMProcess>>initialize OSSVMProcess class>>initializeVMProcessInstance OSSVMProcess class>>initialize MCMethodDefinition>>postloadOver: [ :each | each postloadOver: (self obsoletionFor: each) ] in MCPackageLoader>>basicLoadDefinitions in Block: [ :each | each postloadOver: (self obsoletionFor: ...etc... [ :each | | newLabel | "Special handling for first and last element" (count = 0 or: [ count + 1 = size or: [ (Time millisecondsSince: lastUpdate) >= msecs ] ]) ifTrue: [ bar current: count. oldLabel = (newLabel := (labelBlock cull: each) ifNil: [ oldLabel ]) ifFalse: [ bar label: newLabel. oldLabel := newLabel ]. lastUpdate := Time millisecondClockValue ]. aBlock value: each. count := count + 1 ] in [ :bar | labelBlock := aStringOrBlock isString ifTrue: [ bar label: aStringOrBlock. [ :dummyItem | aStringOrBlock ] ] ifFalse: [ aStringOrBlock ]. self do: [ :each | | newLabel | "Special handling for first and last element" (count = 0 or: [ count + 1 = size or: [ (Time millisecondsSince: lastUpdate) >= msecs ] ]) ifTrue: [ bar current: count. oldLabel = (newLabel := (labelBlock cull: each) ifNil: [ oldLabel ]) ifFalse: [ bar label: newLabel. oldLabel := newLabel ]. lastUpdate := Time millisecondClockValue ]. aBlock value: each. count := count + 1 ] ] in OrderedCollection(Collection)>>do:displayingProgress:every: in Block: [ :each | ... OrderedCollection>>do: [ :bar | labelBlock := aStringOrBlock isString ifTrue: [ bar label: aStringOrBlock. [ :dummyItem | aStringOrBlock ] ] ifFalse: [ aStringOrBlock ]. self do: [ :each | | newLabel | "Special handling for first and last element" (count = 0 or: [ count + 1 = size or: [ (Time millisecondsSince: lastUpdate) >= msecs ] ]) ifTrue: [ bar current: count. oldLabel = (newLabel := (labelBlock cull: each) ifNil: [ oldLabel ]) ifFalse: [ bar label: newLabel. oldLabel := newLabel ]. lastUpdate := Time millisecondClockValue ]. aBlock value: each. count := count + 1 ] ] in OrderedCollection(Collection)>>do:displayingProgress:every: in Block: [ :bar | ... BlockClosure>>cull: [ ^ block cull: self ] in [ self prepareForRunning. CurrentJob value: self during: [ ^ block cull: self ] ] in Job>>run in Block: [ ^ block cull: self ] [ p psValueAt: index put: anObject. aBlock value ] in CurrentJob(DynamicVariable)>>value:during: in Block: [ p psValueAt: index put: anObject.... BlockClosure>>ensure: CurrentJob(DynamicVariable)>>value:during: CurrentJob class(DynamicVariable class)>>value:during: [ self prepareForRunning. CurrentJob value: self during: [ ^ block cull: self ] ] in Job>>run in Block: [ self prepareForRunning.... BlockClosure>>ensure: Job>>run MorphicUIManager(UIManager)>>displayProgress:from:to:during: ByteString(String)>>displayProgressFrom:to:during: OrderedCollection(Collection)>>do:displayingProgress:every: OrderedCollection(Collection)>>do:displayingProgress: MCPackageLoader>>basicLoadDefinitions
-- Cyril Ferlicot
165 Avenue Bretagne Lille 59000 France
-- Mariano http://marianopeck.wordpress.com