VirtualBox

source: vbox/trunk/src/VBox/ValidationKit/tests/storage/remoteexecutor.py@ 64847

Last change on this file since 64847 was 64847, checked in by vboxsync, 8 years ago

ValdiationKit/storaage: Increase the timeout for the benchmarks to 2 hourse because running the complete benchmark with QCOW exceeds the timeout. The 4K block size hurts performance too much

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 8.3 KB
Line 
1# -*- coding: utf-8 -*-
2# $Id: remoteexecutor.py 64847 2016-12-13 12:42:29Z vboxsync $
3
4"""
5VirtualBox Validation Kit - Storage benchmark, test execution helpers.
6"""
7
8__copyright__ = \
9"""
10Copyright (C) 2016 Oracle Corporation
11
12This file is part of VirtualBox Open Source Edition (OSE), as
13available from http://www.virtualbox.org. This file is free software;
14you can redistribute it and/or modify it under the terms of the GNU
15General Public License (GPL) as published by the Free Software
16Foundation, in version 2 as it comes in the "COPYING" file of the
17VirtualBox OSE distribution. VirtualBox OSE is distributed in the
18hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
19
20The contents of this file may alternatively be used under the terms
21of the Common Development and Distribution License Version 1.0
22(CDDL) only, as it comes in the "COPYING.CDDL" file of the
23VirtualBox OSE distribution, in which case the provisions of the
24CDDL are applicable instead of those of the GPL.
25
26You may elect to license modified versions of this file under the
27terms and conditions of either the GPL or the CDDL or both.
28"""
29__version__ = "$Revision: 64847 $"
30
31
32# Standard Python imports.
33import array;
34import os;
35import shutil;
36import StringIO
37import subprocess;
38
39# Validation Kit imports.
40from common import utils;
41from testdriver import reporter;
42
43class StdInOutBuffer(object):
44 """ Standard input output buffer """
45
46 def __init__(self, sInput = None):
47 self.sInput = StringIO.StringIO();
48 if sInput is not None:
49 self.sInput.write(self._toString(sInput));
50 self.sInput.seek(0);
51 self.sOutput = '';
52
53 def _toString(self, sText):
54 """
55 Converts any possible array to
56 a string.
57 """
58 if isinstance(sText, array.array):
59 try:
60 return sText.tostring();
61 except:
62 pass;
63 else:
64 return sText;
65
66 def read(self, cb):
67 """file.read"""
68 return self.sInput.read(cb);
69
70 def write(self, sText):
71 """file.write"""
72 self.sOutput += self._toString(sText);
73 return None;
74
75 def getOutput(self):
76 """
77 Returns the output of the buffer.
78 """
79 return self.sOutput;
80
81 def close(self):
82 """ file.close """
83 return;
84
85class RemoteExecutor(object):
86 """
87 Helper for executing tests remotely through TXS or locally
88 """
89
90 def __init__(self, oTxsSession = None, asBinaryPaths = None, sScratchPath = None):
91 self.oTxsSession = oTxsSession;
92 self.asPaths = asBinaryPaths;
93 if self.asPaths is None:
94 self.asPaths = [ ];
95 self.sScratchPath = sScratchPath
96
97 def _isFile(self, sFile):
98 """
99 Checks whether a file exists.
100 """
101 if self.oTxsSession is not None:
102 return self.oTxsSession.syncIsFile(sFile);
103 else:
104 return os.path.isfile(sFile);
105
106 def _getBinaryPath(self, sBinary):
107 """
108 Returns the complete path of the given binary if found
109 from the configured search path or None if not found.
110 """
111 for sPath in self.asPaths:
112 sFile = sPath + '/' + sBinary;
113 if self._isFile(sFile):
114 return sFile;
115 return None;
116
117 def _sudoExecuteSync(self, asArgs, sInput):
118 """
119 Executes a sudo child process synchronously.
120 Returns a tuple [True, 0] if the process executed successfully
121 and returned 0, otherwise [False, rc] is returned.
122 """
123 reporter.log('Executing [sudo]: %s' % (asArgs, ));
124 reporter.flushall();
125 try:
126 oProcess = utils.sudoProcessPopen(asArgs, stdout=subprocess.PIPE, stdin=subprocess.PIPE,
127 shell = False, close_fds = False);
128
129 sOutput, _ = oProcess.communicate(sInput);
130 iExitCode = oProcess.poll();
131
132 if iExitCode is not 0:
133 print(sOutput);
134 raise subprocess.CalledProcessError(iExitCode, asArgs);
135 except:
136 reporter.errorXcpt();
137 return (False, None);
138 reporter.log('Exit code [sudo]: %s (%s)' % (True, asArgs));
139 return (True, str(sOutput));
140
141 def _execLocallyOrThroughTxs(self, sExec, asArgs, sInput, cMsTimeout):
142 """
143 Executes the given program locally or through TXS based on the
144 current config.
145 """
146 fRc = False;
147 sOutput = None;
148 if self.oTxsSession is not None:
149 oStdOut = StdInOutBuffer();
150 oStdIn = None;
151 if sInput is not None:
152 oStdIn = StdInOutBuffer(sInput);
153 else:
154 oStdIn = '/dev/null'; # pylint: disable=R0204
155 fRc = self.oTxsSession.syncExecEx(sExec, (sExec,) + asArgs,
156 oStdIn = oStdIn, oStdOut = oStdOut,
157 cMsTimeout = cMsTimeout);
158 sOutput = oStdOut.getOutput();
159 else:
160 fRc, sOutput = self._sudoExecuteSync([sExec, ] + list(asArgs), sInput);
161 return (fRc, sOutput);
162
163 def execBinary(self, sExec, asArgs, sInput = None, cMsTimeout = 3600000):
164 """
165 Executes the given binary with the given arguments
166 providing some optional input through stdin and
167 returning whether the process exited successfully and the output
168 in a string.
169 """
170
171 fRc = True;
172 sOutput = None;
173 sBinary = self._getBinaryPath(sExec);
174 if sBinary is not None:
175 fRc, sOutput = self._execLocallyOrThroughTxs(sBinary, asArgs, sInput, cMsTimeout);
176 else:
177 fRc = False;
178 return (fRc, sOutput);
179
180 def execBinaryNoStdOut(self, sExec, asArgs, sInput = None):
181 """
182 Executes the given binary with the given arguments
183 providing some optional input through stdin and
184 returning whether the process exited successfully.
185 """
186 fRc, _ = self.execBinary(sExec, asArgs, sInput);
187 return fRc;
188
189 def copyFile(self, sLocalFile, sFilename, cMsTimeout = 30000):
190 """
191 Copies the local file to the remote destination
192 if configured
193
194 Returns a file ID which can be used as an input parameter
195 to execBinary() resolving to the real filepath on the remote side
196 or locally.
197 """
198 sFileId = None;
199 if self.oTxsSession is not None:
200 sFileId = '${SCRATCH}/' + sFilename;
201 fRc = self.oTxsSession.syncUploadFile(sLocalFile, sFileId, cMsTimeout);
202 if not fRc:
203 sFileId = None;
204 else:
205 sFileId = self.sScratchPath + '/' + sFilename;
206 try:
207 shutil.copy(sLocalFile, sFileId);
208 except:
209 sFileId = None;
210
211 return sFileId;
212
213 def copyString(self, sContent, sFilename, cMsTimeout = 30000):
214 """
215 Creates a file remotely or locally with the given content.
216
217 Returns a file ID which can be used as an input parameter
218 to execBinary() resolving to the real filepath on the remote side
219 or locally.
220 """
221 sFileId = None;
222 if self.oTxsSession is not None:
223 sFileId = '${SCRATCH}/' + sFilename;
224 fRc = self.oTxsSession.syncUploadString(sContent, sFileId, cMsTimeout);
225 if not fRc:
226 sFileId = None;
227 else:
228 sFileId = self.sScratchPath + '/' + sFilename;
229 try:
230 oFile = open(sFileId, 'wb');
231 oFile.write(sContent);
232 oFile.close();
233 except:
234 sFileId = None;
235
236 return sFileId;
237
238 def mkDir(self, sDir, fMode = 0700, cMsTimeout = 30000):
239 """
240 Creates a new directory at the given location.
241 """
242 fRc = True;
243 if self.oTxsSession is not None:
244 fRc = self.oTxsSession.syncMkDir(sDir, fMode, cMsTimeout);
245 else:
246 fRc = self.execBinaryNoStdOut('mkdir', ('-m', format(fMode, 'o'), sDir));
247
248 return fRc;
249
250 def rmDir(self, sDir, cMsTimeout = 30000):
251 """
252 Removes the given directory.
253 """
254 fRc = True;
255 if self.oTxsSession is not None:
256 fRc = self.oTxsSession.syncRmDir(sDir, cMsTimeout);
257 else:
258 fRc = self.execBinaryNoStdOut('rmdir', (sDir,));
259
260 return fRc;
261
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette