# -*- coding: utf-8 -*-
# pylint: disable=C0302
"""
VirtualBox Validation Kit - Guest Control Tests.
"""
__copyright__ = \
"""
Copyright (C) 2010-2014 Oracle Corporation
This file is part of VirtualBox Open Source Edition (OSE), as
available from http://www.virtualbox.org. This file is free software;
General Public License (GPL) as published by the Free Software
Foundation, in version 2 as it comes in the "COPYING" file of the
VirtualBox OSE distribution. VirtualBox OSE is distributed in the
hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
The contents of this file may alternatively be used under the terms
of the Common Development and Distribution License Version 1.0
(CDDL) only, as it comes in the "COPYING.CDDL" file of the
VirtualBox OSE distribution, in which case the provisions of the
CDDL are applicable instead of those of the GPL.
You may elect to license modified versions of this file under the
terms and conditions of either the GPL or the CDDL or both.
"""
# Disable bitching about too many arguments per function.
# pylint: disable=R0913
## @todo Convert map() usage to a cleaner alternative Python now offers.
# pylint: disable=W0141
# disabling it.
# pylint: disable=R0903
# Standard Python imports.
import errno
import os
import random
import struct
import sys
import time
# Only the main script needs to modify the path.
try: __file__
g_ksValidationKitDir = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__))));
# Validation Kit imports.
"""
"""
"""
Appends and converts a byte sequence to this object;
handy for displaying a guest stream.
"""
"""
Provides the actual test environment. Should be kept
as generic as possible.
"""
## The desired Main API result.
## IGuest reference.
# Rest not used (yet).
"""
Provides credentials to pass to the guest.
"""
"""
Base class for all guest control tests.
Note: This test ASSUMES that working Guest Additions
were installed and running on the guest to be tested.
"""
## IGuestSession reference or None.
self.oGuestSession = None;
"""
Sets the test environment required for this test.
"""
"""
Creates (opens) a guest session.
Returns (True, IGuestSession) on success or (False, None) on failure.
"""
if self.oGuestSession is None:
if sName is None:
sName = "<untitled>";
try:
sName);
except:
# Just log, don't assume an error here (will be done in the main loop then).
return (False, None);
try:
#
# Be nice to Guest Additions < 4.3: They don't support session handling and
# therefore return WaitFlagNotSupported.
#
# Just log, don't assume an error here (will be done in the main loop then).
% (waitResult));
return (False, None);
except:
# Just log, don't assume an error here (will be done in the main loop then).
return (False, None);
else:
"""
Sets the current guest session and closes
an old one if necessary.
"""
if self.oGuestSession is not None:
self.closeSession();
return self.oGuestSession;
"""
Closes the guest session.
"""
if self.oGuestSession is not None:
try:
self.oGuestSession = None;
except:
# Just log, don't assume an error here (will be done in the main loop then).
return False;
return True;
"""
Test for copying files from the guest to the host.
"""
"""
Test for copying files from the host to the guest.
"""
"""
Test for directoryCreate call.
"""
"""
Test for the directoryCreateTemp call.
"""
def __init__(self, sDirectory = "", sTemplate = "", sUser = "", sPassword = "", fMode = 0, fSecure = False):
"""
Test for the directoryOpen call.
"""
"""
Test for the opening, reading and closing a certain directory.
"""
"""
Specifies exactly one guest control execution test.
Has a default timeout of 5 minutes (for safety).
"""
fWaitForExit = True):
"""
Test for the file exists API call (fileExists).
"""
"""
Test querying guest file information.
"""
"""
Test querying guest file information.
"""
"""
Test for the IGuestFile object.
"""
"""
Test for the file size query API call (fileQuerySize).
"""
"""
Tests reading from guest files.
"""
sSharingMode = "",
aBuf = None):
"""
Test the guest session handling.
"""
sSessionName = ""):
"""
Helper for returning the number of currently
opened guest sessions of a VM.
"""
return 0;
"""
Test the guest session environment.
"""
"""
Tests session file (IGuestFile) reference counting.
"""
"""
Tests session directory (IGuestDirectory) reference counting.
"""
"""
Tests session process (IGuestProcess) reference counting.
"""
"""
Test updating the Guest Additions inside the guest.
"""
"""
Base class for test results.
"""
## The overall test result.
"""
Test result for reading guest directories.
"""
"""
Holds a guest process execution test result,
including the exit code, status + aFlags.
"""
## The overall test result.
## Process exit stuff.
"""
Test result for stat'ing guest files.
"""
## @todo Add more information.
"""
Test result for reading + writing guest directories.
"""
"""
Test result for guest session counts.
"""
"""
Test result for guest session environment tests.
"""
"""
Sub-test driver for executing guest control (VBoxService, IGuest) tests.
"""
## @todo base.TestBase.
self.asTestsDef = \
[
'session_basic', 'session_env', 'session_file_ref', 'session_dir_ref', 'session_proc_ref', \
'exec_basic', 'exec_errorlevel', 'exec_timeout', \
'dir_create', 'dir_create_temp', 'dir_read', \
'file_remove', 'file_stat', 'file_read', 'file_write', \
'copy_to', 'copy_from', \
'update_additions'
];
iArg += 1;
return iArg + 1;
if s not in self.asTestsDef:
raise base.InvalidOption('The "--add-guest-ctrl-tests" value "%s" is not valid; valid values are: %s' \
return iNext;
return iArg;
return True;
"""
Executes the test.
Returns fRc, oTxsSession. The latter may have changed.
"""
# Do the testing.
## @todo Implement this.
#reporter.testStart('Session Directory References');
#fSkip = 'session_dir_ref' not in self.asTests;
#if fSkip == False:
# fRc, oTxsSession = self.testGuestCtrlSessionDirRefs(oSession, oTxsSession, oTestVm);
#reporter.testDone(fSkip);
# FIXME: Failing test.
# reporter.testStart('Copy to guest');
# fSkip = 'copy_to' not in self.asTests or fRc is False;
# if fSkip == False:
# fRc, oTxsSession = self.testGuestCtrlCopyTo(oSession, oTxsSession, oTestVm);
# reporter.testDone(fSkip);
# FIXME: Failing tests.
# reporter.testStart('File read');
# fSkip = 'file_read' not in self.asTests or fRc is False;
# if fSkip == False:
# fRc, oTxsSession = self.testGuestCtrlFileRead(oSession, oTxsSession, oTestVm);
# reporter.testDone(fSkip);
# reporter.testStart('File write');
# fSkip = 'file_write' not in self.asTests or fRc is False;
# if fSkip == False:
# fRc, oTxsSession = self.testGuestCtrlFileWrite(oSession, oTxsSession, oTestVm);
# reporter.testDone(fSkip);
# Skip test for updating Guest Additions if we run on a too old (Windows) guest.
return (fRc, oTxsSession);
"""
Helper function to copy a single file from the guest to the host.
"""
try:
if curProgress is not None:
try:
if iRc != 0:
except:
except:
# Just log, don't assume an error here (will be done in the main loop then).
return fRc;
"""
Helper function to copy a single file from host to the guest.
"""
try:
if curProgress is not None:
try:
if iRc != 0:
except:
else:
except:
# Just log, don't assume an error here (will be done in the main loop then).
return fRc;
"""
Copies files / directories to the host.
Source always contains the absolute path, subDir all paths
below it.
"""
## @todo r=bird: The use subDir and sSubDir in this method is extremely confusing!!
# Just follow the coding guidelines and ALWAYS use prefixes, please!
if sSrc == "" \
if subDir != "":
try:
#reporter.log2('Directory="%s", filter="%s", aFlags="%s"' % (sCurDir, sFilter, aFlags));
while fRc:
try:
#reporter.log2('\tSkipping "%s"' % (oFsObjInfo.name,));
continue; # Skip "." and ".." entries.
#reporter.log2('\tDirectory "%s"' % (oFsObjInfo.name,));
sDirCreate = sDst;
if subDir != "":
try:
if subDir != "":
except (OSError) as e:
pass;
else:
# Just log, don't assume an error here (will be done in the main loop then).
raise;
#reporter.log2('\tFile "%s"' % (oFsObjInfo.name,));
#reporter.log2('\tSymlink "%s" -- not tested yet' % oFsObjInfo.name);
pass;
else:
# No necessarily an error -- could be VBOX_E_OBJECT_NOT_FOUND. See reference.
#reporter.log2('\tNo more directory entries for "%s"' % (sCurDir,));
break
# Just log, don't assume an error here (will be done in the main loop then).
break;
except:
# Just log, don't assume an error here (will be done in the main loop then).
return fRc;
"""
Copies files / directories to the guest.
Source always contains the absolute path,
subDir all paths below it.
"""
if subDir != "":
# Note: Current test might want to test copying empty sources
try:
# Note: Symlinks intentionally not considered here.
break;
break;
break;
break;
except:
# Just log, don't assume an error here (will be done in the main loop then).
return False;
return fRc;
"""
Helper function to create a guest directory specified in
the current test.
"""
try:
if fDirExists is False \
# Directory does not exist but we want it to.
except:
# Just log, don't assume an error here (will be done in the main loop then).
# Directory creation failed, which was the expected result.
return fRc;
"""
Helper function to read a guest directory specified in
the current test.
"""
try:
#reporter.log2('Directory="%s", filter="%s", aFlags="%s"' % (sCurDir, sFilter, aFlags));
while fRc:
try:
#reporter.log2('\tSkipping "%s"' % oFsObjInfo.name);
continue; # Skip "." and ".." entries.
#reporter.log2('\tDirectory "%s"' % oFsObjInfo.name);
cDirs += 1;
if subDir != "":
#reporter.log2('\tFile "%s"' % oFsObjInfo.name);
cFiles += 1;
#reporter.log2('\tSymlink "%s" -- not tested yet' % oFsObjInfo.name);
pass;
else:
# No necessarily an error -- could be VBOX_E_OBJECT_NOT_FOUND. See reference.
#reporter.log2('\tNo more directory entries for "%s"' % (sCurDir,));
break
# Just log, don't assume an error here (will be done in the main loop then).
break;
except:
# Just log, don't assume an error here (will be done in the main loop then).
"""
Wrapper function around gctrlExecute to provide more sanity checking
when needed in actual execution tests.
"""
# Compare exit status / code on successful process execution.
return False;
# Compare test / result buffers on successful process execution.
return False;
else:
return False;
return False;
else:
return False;
return True;
"""
Helper function to execute a program on a guest, specified in
the current test.
"""
## @todo Compare execution timeouts!
#tsStart = base.timestampMilli();
try:
if curProc is not None:
reporter.log2('Wait result returned: %d, current process status is: %ld' % (waitResult, curProc.status));
## @todo Add vboxcon.ProcessWaitForFlag_StdIn.
while True:
try:
# Try stdout.
# Try stderr.
# Use stdin.
pass; #reporter.log2('Process (PID %ld) needs stdin data' % (curProc.pid,));
# Termination or error?
break;
except:
# Just skip reads which returned nothing.
pass;
reporter.log2('Process (PID %ld) %ld stdout, %ld stderr' % (curProc.PID, oTest.cbStdOut, oTest.cbStdErr));
except KeyboardInterrupt:
if curProc is not None:
except:
# Just log, don't assume an error here (will be done in the main loop then).
return fRc;
"""
Tests the guest session environment.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
aaTests = [
# No environment set.
# Invalid stuff.
# Key only.
# Values.
# Same stuff.
];
# Parameters.
curGuestSessionName = 'testGuestCtrlSessionEnvironment: Test #%d' % (i,);
break;
# Make sure environment is empty.
reporter.error('Test #%d failed: Initial session environment has %d vars, expected 0' % (i, len(curEnv)));
break;
try:
for (_, aEnv) in enumerate(curTest.aEnv): # Enumerate only will work with a sequence (e.g > 1 entries).
strKey = '';
strValue = '';
try:
curGuestSession.environmentSet(strKey, strValue); # No return (e.g. boolean) value available thru wrapper.
except:
# Setting environment variables might fail (e.g. if empty name specified). Check.
break;
else:
try:
break;
# Getting back an empty value when specifying an invalid key is fine.
except UnicodeDecodeError: # Might happen on unusal values, fine.
'expected "%s" (key: "%s")' \
break;
except:
if strKey == "" \
else:
continue;
# Set the same stuff again, this time all at once using the array.
try:
## @todo No return (e.g. boolean) value available thru wrapper.
#curGuestSession.environmentSetArray(curTest.aEnv);
pass;
except:
# Setting environment variables might fail (e.g. if empty name specified). Check.
break;
else:
## @todo Get current system environment and add it to curRes.cNumVars before comparing!
break;
break;
except:
break;
return (fRc, oTxsSession);
"""
Tests the guest session handling.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
aaTests = [
# Invalid parameters.
[ tdTestSession(),
# User account without a passwort - forbidden.
# Wrong credentials.
# Note: On Guest Additions < 4.3 this always succeeds because these don't
# support creating dedicated sessions. Instead, guest process creation
# then will fail. See note below.
# Correct credentials.
];
# Parameters.
curGuestSessionName = 'testGuestCtrlSession: Test #%d' % (i);
# See note about < 4.3 Guest Additions above.
if curGuestSession is not None \
if fRc2:
# On Guest Additions < 4.3 getSessionCount() always will return 1, so skip the
# check then.
break;
if curGuestSession is not None \
break;
break;
return (False, oTxsSession);
# Multiple sessions.
# Actually, this is 32, but we don't test session 0.
multiSession = {};
multiSession[i] = tdTestSession(sUser = sUser, sPassword = sPassword, sSessionName = 'MultiSession #%d' % (i,));
if curSessionCount is not i:
break;
if i < iMaxGuestSessions:
else:
break;
if curSessionCount is not iMaxGuestSessions:
% (iMaxGuestSessions, curSessionCount));
return (False, oTxsSession);
reporter.log2('MultiSession #%d count is %d' % (i, multiSession[i].getSessionCount(self.oTstDrv.oVBoxMgr),));
break;
if curSessionCount is not 1:
try:
# Make sure that accessing the first opened guest session does not work anymore because we just removed (closed) it.
reporter.error('Accessing first removed MultiSession should not be possible, got name="%s"' % (curSessionName,));
except:
try:
# Try Accessing last opened session which did not get removed yet.
if curSessionCount is not 0:
except:
## @todo Test session timeouts.
return (fRc, oTxsSession);
"""
Tests the guest session file reference handling.
"""
sUser = "Administrator";
sPassword = "password";
sDomain = "";
sFile = "C:\\windows\\system32\\kernel32.dll";
# Number of stale guest files to create.
cStaleFiles = 10;
try:
"testGuestCtrlSessionFileRefs");
#
# Be nice to Guest Additions < 4.3: They don't support session handling and
# therefore return WaitFlagNotSupported.
#
# Just log, don't assume an error here (will be done in the main loop then).
% (waitResult));
return (False, oTxsSession);
#
# Open guest files and "forget" them (stale entries).
# For them we don't have any references anymore intentionally.
#
try:
# Note: Use a timeout in the call above for not letting the stale processes
# hanging around forever. This can happen if the installed Guest Additions
# do not support terminating guest processes.
except:
break;
if fRc:
if cFiles != cStaleFiles:
if fRc:
#
# Open non-stale files and close them again.
#
aaFiles = [];
try:
except:
break;
if fRc:
if fRc:
try:
except:
break;
# Here we count the stale files (that is, files we don't have a reference
# anymore for) and the opened and then closed non-stale files (that we still keep
# a reference in aaFiles[] for).
if cFiles != cStaleFiles:
% (cFiles, cStaleFiles));
if fRc:
#
# Check if all (referenced) non-stale files now are in "closed" state.
#
try:
except:
break;
if fRc:
# Now try to close the session and see what happens.
except:
return (fRc, oTxsSession);
#def testGuestCtrlSessionDirRefs(self, oSession, oTxsSession, oTestVm):
# """
# Tests the guest session directory reference handling.
# """
# fRc = True;
# return (fRc, oTxsSession);
"""
Tests the guest session process reference handling.
"""
sUser = "Administrator";
sPassword = "password";
sDomain = "";
sCmd = "C:\\windows\\system32\\cmd.exe";
sArgs = [];
# Number of stale guest processes to create.
cStaleProcs = 10;
try:
"testGuestCtrlSessionProcRefs");
#
# Be nice to Guest Additions < 4.3: They don't support session handling and
# therefore return WaitFlagNotSupported.
#
# Just log, don't assume an error here (will be done in the main loop then).
% (waitResult));
return (False, oTxsSession);
#
# Fire off forever-running processes and "forget" them (stale entries).
# For them we don't have any references anymore intentionally.
#
try:
sArgs, [], \
30 * 1000);
# Note: Use a timeout in the call above for not letting the stale processes
# hanging around forever. This can happen if the installed Guest Additions
# do not support terminating guest processes.
except:
break;
if fRc:
if cProcs != cStaleProcs:
if fRc:
#
# Fire off non-stale processes and wait for termination.
#
aaProcs = [];
try:
sArgs, [], \
[], \
0); # Infinite timeout.
except:
break;
if fRc:
try:
' resulted in status %ld, expected %ld' \
except:
break;
# Here we count the stale processes (that is, processes we don't have a reference
# anymore for) and the started + terminated non-stale processes (that we still keep
# a reference in aaProcs[] for).
% (cProcs, cStaleProcs));
if fRc:
#
# Check if all (referenced) non-stale processes now are in "terminated" state.
#
if fRc:
# Fire off blocking processes which are terminated via terminate().
aaProcs = [];
try:
sArgs, [], \
[], 30 * 1000);
# Note: Use a timeout in the call above for not letting the stale processes
# hanging around forever. This can happen if the installed Guest Additions
# do not support terminating guest processes.
except:
break;
if fRc:
try:
except: # Termination might not be supported, just skip and log it.
if cProcs != (cStaleProcs * 2): # Still should be 20 processes because we terminated the 10 newest ones.
# Now try to close the session and see what happens.
except:
return (fRc, oTxsSession);
"""
Tests the basic execution feature.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
# Outputting stuff.
sImageOut = "C:\\windows\\system32\\cmd.exe";
else:
return (False, oTxsSession);
aaInvalid = [
# Invalid parameters.
# Non-existent / invalid image.
# Use an invalid format string.
# More stuff.
# Enable as soon as ERROR_BAD_DEVICE is implemented.
#[ tdTestExec(sCmd = "CON", sUser = sUser, sPassword = sPassword),
# tdTestResultExec(fRc = False) ]
];
aaExec = [
# Basic executon.
[ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'dir', '/S', 'c:\\windows\\system32\\kernel32.dll' ],
[ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'dir', '/S', 'c:\\windows\\system32\\nonexist.dll' ],
# Paths with spaces.
## @todo Get path of installed Guest Additions. Later.
aArgs = [ 'version' ],
# StdOut.
# StdErr.
# StdOut + StdErr.
# FIXME: Failing tests.
# Environment variables.
# [ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'set', 'TEST_NONEXIST' ],
# sUser = sUser, sPassword = sPassword),
# tdTestResultExec(fRc = True, iExitCode = 1) ]
# [ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'set', 'windir' ],
# sUser = sUser, sPassword = sPassword,
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, sBuf = 'windir=C:\\WINDOWS\r\n') ],
# [ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'set', 'TEST_FOO' ],
# sUser = sUser, sPassword = sPassword,
# aEnv = [ 'TEST_FOO=BAR' ],
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, sBuf = 'TEST_FOO=BAR\r\n') ],
# [ tdTestExec(sCmd = sImageOut, aArgs = [ '/C', 'set', 'TEST_FOO' ],
# sUser = sUser, sPassword = sPassword,
# aEnv = [ 'TEST_FOO=BAR', 'TEST_BAZ=BAR' ],
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, sBuf = 'TEST_FOO=BAR\r\n') ]
## @todo Create some files (or get files) we know the output size of to validate output length!
## @todo Add task which gets killed at some random time while letting the guest output something.
];
# Manual test, not executed automatically.
aaManual = [
else:
# Build up the final test array for the first batch.
aaTests = [];
if aaExec is not None:
#
# Single execution stuff. Nice for debugging.
#
if fManual:
else:
else:
else:
return (fRc, oTxsSession);
else:
return (fRc, oTxsSession);
#
# First batch: One session per guest process.
#
break;
break;
break;
# No sessions left?
if cSessions is not 0:
return (fRc, oTxsSession);
#
# Second batch: One session for *all* guest processes.
#
try:
curGuestSession = oGuest.createSession(sUser, sPassword, '', 'testGuestCtrlExec: One session for all tests');
try:
% (waitResult));
return (False, oTxsSession);
except:
# Just log, don't assume an error here (will be done in the main loop then).
return (False, oTxsSession);
# Note: Not waiting for the guest session to start here
# is intentional. This must be handled by the process execution
# call then.
break;
try:
curGuestSession = None;
except:
# Just log, don't assume an error here (will be done in the main loop then).
except:
# No sessions left?
if cSessions is not 0:
return (fRc, oTxsSession);
"""
Tests handling of error levels from started guest processes.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
# Outputting stuff.
sImage = "C:\\windows\\system32\\cmd.exe";
else:
return (False, oTxsSession);
aaTests = [];
# Simple.
# FIXME: Failing tests.
# With stdout.
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\windows\\system32' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut ]),
# tdTestResultExec(fRc = True, iExitCode = 0) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-file' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-dir\\' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ],
# With stderr.
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\windows\\system32' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 0) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-file' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-dir\\' ],
# sUser = sUser, sPassword = sPassword, aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\windows\\system32' ],
# sUser = sUser, sPassword = sPassword,
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 0) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-file' ],
# sUser = sUser, sPassword = sPassword,
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ],
# [ tdTestExec(sCmd = sImage, aArgs = [ '/C', 'dir', 'c:\\nonexisting-dir\\' ],
# sUser = sUser, sPassword = sPassword,
# aFlags = [ vboxcon.ProcessCreateFlag_WaitForStdOut, vboxcon.ProcessCreateFlag_WaitForStdErr ]),
# tdTestResultExec(fRc = True, iExitCode = 1) ]
## @todo Test stdin!
]);
else:
break;
break;
return (fRc, oTxsSession);
"""
Tests handling of timeouts of started guest processes.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
sDomain = "";
# Outputting stuff.
sImage = "C:\\windows\\system32\\cmd.exe";
else:
return (False, oTxsSession);
try:
# Create a process which never terminates and should timeout when
# waiting for termination.
try:
[], [], 30 * 1000);
if fRc:
else:
if fRc:
reporter.error('Waiting for process 1 did not time out when it should, got wait result %ld' % (waitRes,));
else:
## @todo Add curProc.terminate() as soon as it's implemented.
except:
# Create a lengthly running guest process which will be killed by VBoxService on the
# guest because it ran out of execution time (5 seconds).
if fRc:
try:
[], [], 5 * 1000);
if fRc:
% (waitRes,));
if fRc:
else:
## @todo Add curProc.terminate() as soon as it's implemented.
except:
except:
return (fRc, oTxsSession);
"""
Tests creation of guest directories.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
sScratch = "C:\\Temp\\vboxtest\\testGuestCtrlDirCreate\\";
aaTests = [];
# Invalid stuff.
# More unusual stuff.
# Creating directories.
[ tdTestDirCreate(sUser = sUser, sPassword = sPassword, sDirectory = os.path.join(sScratch, 'foo\\bar\\baz'),
[ tdTestDirCreate(sUser = sUser, sPassword = sPassword, sDirectory = os.path.join(sScratch, 'foo\\bar\\baz'),
# Long (+ random) stuff.
# Following two should fail on Windows (paths too long). Both should timeout.
]);
else:
break;
break;
return (fRc, oTxsSession);
"""
Tests creation of temporary directories.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
# if oTestVm.isWindows():
# sScratch = "C:\\Temp\\vboxtest\\testGuestCtrlDirCreateTemp\\";
aaTests = [];
# Invalid stuff.
fMode = 1234),
# More unusual stuff.
sDirectory = 'z:\\'),
sDirectory = '\\\\uncrulez\\foo'),
# Non-existing stuff.
sDirectory = 'c:\\Apps\\nonexisting\\foo'),
# FIXME: Failing test. Non Windows path
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'bar',
# tdTestResult(fRc = False) ]
]);
else:
# FIXME: Failing tests.
# aaTests.extend([
# Non-secure variants.
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'X',
# sDirectory = sScratch),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'X',
# sDirectory = sScratch),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fMode = 0700),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fMode = 0700),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fMode = 0755),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fMode = 0755),
# tdTestResult(fRc = True) ],
# Secure variants.
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch, fSecure = True),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch, fSecure = True),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch, fSecure = True),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch, fSecure = True),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fSecure = True, fMode = 0700),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fSecure = True, fMode = 0700),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fSecure = True, fMode = 0755),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = 'XXX',
# sDirectory = sScratch,
# fSecure = True, fMode = 0755),
# tdTestResult(fRc = True) ],
# Random stuff.
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword,
# sTemplate = "XXX-".join(random.choice(string.ascii_lowercase) for i in range(32)),
# sDirectory = sScratch,
# fSecure = True, fMode = 0755),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = "".join('X' for i in range(32)),
# sDirectory = sScratch,
# fSecure = True, fMode = 0755),
# tdTestResult(fRc = True) ],
# [ tdTestDirCreateTemp(sUser = sUser, sPassword = sPassword, sTemplate = "".join('X' for i in range(128)),
# sDirectory = sScratch,
# fSecure = True, fMode = 0755),
# tdTestResult(fRc = True) ]
# ]);
break;
sDirTemp = "";
try:
except:
break;
else:
reporter.logXcpt('Creating temp directory "%s" failed expectedly, skipping:' % (curTest.sDirectory,));
if sDirTemp != "":
break;
return (fRc, oTxsSession);
"""
Tests opening and reading (enumerating) guest directories.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
aaTests = [];
# Invalid stuff.
[ tdTestDirRead(sUser = sUser, sPassword = sPassword, sDirectory = 'C:\\Windows', aFlags = [ 1234 ]),
[ tdTestDirRead(sUser = sUser, sPassword = sPassword, sDirectory = 'C:\\Windows', sFilter = '*.foo'),
# More unusual stuff.
# Non-existing stuff.
]);
# Reading directories.
]);
else:
break;
break;
break;
else:
break;
return (fRc, oTxsSession);
"""
Tests removing guest files.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
aaTests = [];
# Invalid stuff.
[ tdTestFileRemove(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows'), tdTestResult(fRc = False) ],
[ tdTestFileRemove(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows'), tdTestResult(fRc = False) ],
# More unusual stuff.
[ tdTestFileRemove(sUser = sUser, sPassword = sPassword, sFile = 'z:\\'), tdTestResult(fRc = False) ],
# Non-existing stuff.
# Try to delete system files.
]);
# Try delete some unimportant media stuff.
# Second attempt should fail.
]);
else:
break;
try:
except:
break;
else:
return (fRc, oTxsSession);
"""
Tests querying file information through stat.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
aaTests = [];
# Invalid stuff.
# More unusual stuff.
# Non-existing stuff.
]);
# Directories; should fail.
# Regular files.
[ tdTestFileStat(sUser = sUser, sPassword = sPassword, sFile = 'c:\\Windows\\system32\\kernel32.dll'),
]);
else:
break;
fileObjInfo = None;
try:
except:
break;
else:
reporter.logXcpt('Querying file information for "%s" failed expectedly, skipping:' % (curTest.sFile,));
if fileObjInfo is not None:
reporter.error('Test #%d failed: Got file type %ld, expected %ld' % (i, eFileType, curRes.eFileType));
break;
reporter.error('Test #%d failed: Got %ld bytes size, expected %ld bytes' % (i, cbFile, curRes.cbSize));
break;
## @todo Add more checks later.
return (fRc, oTxsSession);
"""
Tests reading from guest files.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
return (False, oTxsSession);
aaTests = [];
# Invalid stuff.
# Wrong open mode.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = '\\\\uncrulez\\non-existing.file', \
# Wrong disposition.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = '\\\\uncrulez\\non-existing.file', \
# Opening non-existing file when it should exist.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = '\\\\uncrulez\\non-existing.file', \
]);
# Create a file which must not exist (but it hopefully does).
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows\\System32\\calc.exe', \
# Open a file which must exist.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows\\System32\\kernel32.dll', \
# Try truncating a file which already is opened with a different sharing mode (and thus should fail).
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows\\System32\\kernel32.dll', \
]);
# Reading from beginning.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows\\System32\\eula.txt', \
# Reading from offset.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = 'C:\\Windows\\System32\\eula.txt', \
]);
reporter.log('Testing #%d, sFile="%s", cbToReadWrite=%d, sOpenMode="%s", sDisposition="%s", cbOffset=%ld ...' % \
(i, curTest.sFile, curTest.cbToReadWrite, curTest.sOpenMode, curTest.sDisposition, curTest.cbOffset));
break;
try:
else:
if fRc \
## @todo Split this up in 64K reads. Later.
## @todo Test timeouts.
if fRc:
# Test final offset.
except:
break;
return (fRc, oTxsSession);
"""
Tests writing to guest files.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
sScratch = "C:\\Temp\\vboxtest\\testGuestCtrlFileWrite\\";
return (False, oTxsSession);
aaTests = [];
cScratchBuf = 512;
# Write to a non-existing file.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = sScratch + 'testGuestCtrlFileWrite.txt', \
aBuf = aScratchBuf),
]);
# Append the same amount of data to the just created file.
[ tdTestFileReadWrite(sUser = sUser, sPassword = sPassword, sFile = sScratch + 'testGuestCtrlFileWrite.txt', \
]);
reporter.log('Testing #%d, sFile="%s", cbToReadWrite=%d, sOpenMode="%s", sDisposition="%s", cbOffset=%ld ...' % \
(i, curTest.sFile, curTest.cbToReadWrite, curTest.sOpenMode, curTest.sDisposition, curTest.cbOffset));
break;
try:
else:
if fRc \
## @todo Split this up in 64K writes. Later.
## @todo Test timeouts.
if fRc:
# Verify written content by seeking back to the initial offset and
# re-read & compare the written data.
try:
except:
if fRc \
if fRc:
if fRc \
# Test final offset.
except:
break;
return (fRc, oTxsSession);
"""
Tests copying files from host to the guest.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
sScratch = "C:\\Temp\\vboxtest\\testGuestCtrlCopyTo\\";
return (False, oTxsSession);
# Some stupid trickery to guess the location of the iso.
sVBoxValidationKitISO = os.path.abspath(os.path.join(os.path.dirname(__file__), '../../VBoxValidationKit.iso'));
sVBoxValidationKitISO = os.path.abspath(os.path.join(os.path.dirname(__file__), '../../VBoxTestSuite.iso'));
break;
break;
else:
aaTests = [];
# Destination missing.
# Source missing.
# Copying single files.
# Destination is a directory, should fail.
## @todo Add testing the CopyTo flags here!
]);
## @todo Check for Windows (7) host.
# Copying directories with contain files we don't have read access to.
# Copying directories with regular files.
]);
else:
break;
## @todo Verify the copied results (size, checksum?).
pass;
else:
break;
return (fRc, oTxsSession);
"""
Tests copying files from guest to the host.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
try:
except OSError as e:
return (False, oTxsSession);
aaTests = [];
# Destination missing.
aFlags = [ 1234 ] ),
# Source missing.
aFlags = [ 1234 ] ),
# Nothing to copy (sDst is empty / unreachable).
## @todo Add testing the CopyFrom aFlags here!
]);
# FIXME: Failing test.
# Copying single files.
# [ tdTestCopyFrom(sUser = sUser, sPassword = sPassword, sSrc = 'C:\\Windows\\system32\\ole32.dll',
# sDst = 'C:\\non-exist\\'), tdTestResult(fRc = False) ],
# [ tdTestCopyFrom(sUser = sUser, sPassword = sPassword, sSrc = 'C:\\Windows\\system32\\ole32.dll',
# sDst = 'C:\\non\\exist\\'), tdTestResult(fRc = False) ],
# [ tdTestCopyFrom(sUser = sUser, sPassword = sPassword, sSrc = 'C:\\Windows\\system32\\ole32.dll',
# sDst = 'C:\\non\\exist\\renamedfile.dll'), tdTestResult(fRc = False) ],
# [ tdTestCopyFrom(sUser = sUser, sPassword = sPassword, sSrc = 'C:\\Windows\\system32\\ole32.dll',
# sDst = os.path.join(sScratch, 'renamedfile.dll')), tdTestResult(fRc = True) ],
# [ tdTestCopyFrom(sUser = sUser, sPassword = sPassword, sSrc = 'C:\\Windows\\system32\\ole32.dll',
# sDst = os.path.join(sScratch, 'renamedfile.dll')), tdTestResult(fRc = True) ],
# Destination is a directory, should fail.
# Copying directories.
## @todo Add testing the CopyFrom aFlags here!
]);
else:
break;
## @todo Verify the copied results (size, checksum?).
pass;
else:
break;
return (fRc, oTxsSession);
"""
Tests updating the Guest Additions inside the guest.
"""
sUser = "Administrator";
else:
sUser = "vbox";
sPassword = "password";
# Some stupid trickery to guess the location of the iso.
sVBoxValidationKitISO = os.path.abspath(os.path.join(os.path.dirname(__file__), '../../VBoxValidationKit.iso'));
sVBoxValidationKitISO = os.path.abspath(os.path.join(os.path.dirname(__file__), '../../VBoxTestSuite.iso'));
break;
break;
else:
try:
except OSError as e:
return (False, oTxsSession);
aaTests = [];
# Source is missing.
# Wrong aFlags.
[ tdTestUpdateAdditions(sUser = sUser, sPassword = sPassword, sSrc = self.oTstDrv.getGuestAdditionsIso(),
aFlags = [ 1234 ]),
# Non-existing .ISO.
# Wrong .ISO.
# The real thing.
[ tdTestUpdateAdditions(sUser = sUser, sPassword = sPassword, sSrc = self.oTstDrv.getGuestAdditionsIso()),
# Test the (optional) installer arguments. This will extract the
# installer into our guest's scratch directory.
[ tdTestUpdateAdditions(sUser = sUser, sPassword = sPassword, sSrc = self.oTstDrv.getGuestAdditionsIso(),
# Some debg ISO. Only enable locally.
#[ tdTestUpdateAdditions(sUser = sUser, sPassword = sPassword,
# sSrc = "V:\\Downloads\\VBoxGuestAdditions-r80354.iso"),
# tdTestResult(fRc = True) ]
]);
else:
break;
try:
curProgress = curTest.oTest.oGuest.updateGuestAdditions(curTest.sSrc, curTest.aArgs, curTest.aFlags);
if curProgress is not None:
try:
if iRc != 0:
except:
except:
# Just log, don't assume an error here (will be done in the main loop then).
if fRc:
## @todo Verify if Guest Additions were really updated (build, revision, ...).
pass;
else:
break;
return (fRc, oTxsSession);
"""
Guest control using VBoxService on the guest.
"""
#
# Overridden methods.
#
"""
Shows the testdriver usage.
"""
return rc;
"""
Parses the testdriver arguments from the command line.
"""
else:
return iArg + 1;
return False;
#
# Test execution helpers.
#
"""
Runs the specified VM thru the tests.
Returns a success indicator on the general test execution. This is not
the actual test result.
"""
if oSession is not None:
if not fManual:
else:
# Cleanup.
if not fManual:
else:
return fRc;
"""
Helper function to report an error of a
given progress object.
"""
if progress is None:
else:
if errInfo:
return False;
"""
Helper function to return the remaining time (in ms)
based from a timeout value and the start time (both in ms).
"""
if msTimeout is 0:
return 0xFFFFFFFE; # Wait forever.
return 0; # No time left.
def testGuestCtrlManual(self, oSession, oTxsSession, oTestVm): # pylint: disable=R0914,R0915,W0613,W0612
"""
For manually testing certain bits.
"""
sUser = 'Administrator';
sPassword = 'password';
"", "Manual Test");
sCmd = 'c:\\windows\\system32\\cmd.exe';
aEnv = [];
aFlags = [];
for _ in range(100):
oGuestSession = None;
return (fRc, oTxsSession);
if __name__ == '__main__':