# Before `make install' is performed this script should be runnable with
# `make test'. After `make install' it should work as `perl test.pl'


#
# Copyright 1998 VMware, Inc.  All rights reserved. -- VMware Confidential
#


####################################################################
#
# Some generic code common to tests for both the VMware::Control and
# VMware::VmPerl modules
#
####################################################################

package main;

use strict;
use vars qw($loaded $verbose);

$verbose = 1;
if (defined($ENV{'MAKELEVEL'}) && $ENV{'MAKELEVEL'} > 1) {
    $verbose = 0;
}

sub verbose {
    return $verbose;
}

# The file containing definitions for the various vmcontrol constants
my $CONSTANTS_H_FILE = "vmcontrol_constants.h";

# Reads from the constants file and gets the value of the constant
sub get_constant_value {
    my $const = shift;
    my $val;
    local *FD;
    open(FD, "< $CONSTANTS_H_FILE") ||
	die "Failed to open $CONSTANTS_H_FILE.  Reason: $!\n";

    while (<FD>) {
	# Strip out comments on the same line
	s|//.*||;
	s|/\*.*\*/||;

	if (/\#define\s+$const\s+(-?[0-9]+)/) {
	    $val = $1;
	}
    }

    close(FD);

    if (!defined($val)) {
	die "Could not find constant $const in $CONSTANTS_H_FILE.\n";
    }
    return ($val);
}

# Check a specific Perl API constant against the value parsed from the
# header file.
sub test_constants {
    my %const_map = @_;
    my $count = 0;
    
    foreach my $e (keys(%const_map)) {
        my $def = $const_map{$e};
        my $val = get_constant_value($def);
        
#        print "Checking $def ($e) vs. $val\n";
        if ($e != $val) {
            die "error $def != $val\n";
        }
        $count++;
    }
    
    if ($count == 0) {
        die "error: no constants were tested.\n";
    }
}



####################################################################
#
# Define the list of constants to be tested for both the
# VMware::Control and VMware::VmPerl modules here.
#
####################################################################

#
# Format of constants table:
# First parameter is the constant value as to be used in Perl.
# Second parameter is the string to which it maps to in the header file.
#
# For now, the Perl constants appear exactly as they do in C.

my $TEST_CONSTANT_CODE = <<EOF;
sub test_all_constants {
    my \$id = shift;

    my %vm_error_constants =
        (
         VM_E_SUCCESS, "VM_E_SUCCESS",
         VM_E_NOMEM, "VM_E_NOMEM",
         VM_E_NETFAIL, "VM_E_NETFAIL",
         VM_E_INVALIDARGS, "VM_E_INVALIDARGS",
         VM_E_NOACCESS, "VM_E_NOACCESS",
         VM_E_NOTCONNECTED, "VM_E_NOTCONNECTED",
         VM_E_BADVERSION, "VM_E_BADVERSION",
         VM_E_TIMEOUT, "VM_E_TIMEOUT",
         VM_E_BADSTATE,  "VM_E_BADSTATE",
         VM_E_NOEXECVMAUTHD, "VM_E_NOEXECVMAUTHD",
         VM_E_NOPROPERTY, "VM_E_NOPROPERTY",
         VM_E_NOSUCHVM, "VM_E_NOSUCHVM",
         VM_E_ALREADYCONNECTED, "VM_E_ALREADYCONNECTED",
         VM_E_DISCONNECT, "VM_E_DISCONNECT",
         VM_E_BADRESPONSE, "VM_E_BADRESPONSE",
         VM_E_GARBAGE, "VM_E_GARBAGE",
         VM_E_NEEDINPUT, "VM_E_NEEDINPUT",
         VM_E_NOTSUPPORTED, "VM_E_NOTSUPPORTED",
         VM_E_INVALIDVM, "VM_E_INVALIDVM",
         VM_E_VMINITFAILED, "VM_E_VMINITFAILED",
         VM_E_VMEXISTS, "VM_E_VMEXISTS",
         VM_E_VMBUSY, "VM_E_VMBUSY",
         VM_E_INSUFFICIENT_RESOURCES, "VM_E_INSUFFICIENT_RESOURCES",
         VM_E_PROXYFAIL, "VM_E_PROXYFAIL",
         VM_E_UNSPECIFIED, "VM_E_UNSPECIFIED",
         );

    &main::test_constants(%vm_error_constants);
    print "ok \$id.4 (VM_E error constants)\n" if main::verbose();
    
    my %vm_timeout_constants =
        (
         VM_TIMEOUT_ID_DEFAULT, "VM_TIMEOUT_ID_DEFAULT",
         );
    
    &main::test_constants(%vm_timeout_constants);
    print "ok \$id.5 (VM_TIMEOUT constants)\n" if main::verbose();
    
    my %vm_execution_state_constants =
        (
         VM_EXECUTION_STATE_ON, "VM_EXECUTION_STATE_ON",
         VM_EXECUTION_STATE_OFF, "VM_EXECUTION_STATE_OFF",
         VM_EXECUTION_STATE_SUSPENDED, "VM_EXECUTION_STATE_SUSPENDED",
         VM_EXECUTION_STATE_STUCK, "VM_EXECUTION_STATE_STUCK",
         VM_EXECUTION_STATE_UNKNOWN, "VM_EXECUTION_STATE_UNKNOWN",
         );
    
    &main::test_constants(%vm_execution_state_constants);
    print "ok \$id.6 (VM_EXECUTION_STATE constants)\n" if main::verbose();
    
    my %vm_powerop_constants =
        (
         VM_POWEROP_MODE_HARD, "VM_POWEROP_MODE_HARD",
         VM_POWEROP_MODE_SOFT, "VM_POWEROP_MODE_SOFT",
         VM_POWEROP_MODE_TRYSOFT, "VM_POWEROP_MODE_TRYSOFT",
         );
    
    &main::test_constants(%vm_powerop_constants);
    print "ok \$id.7 (VM_POWEROP constants)\n" if main::verbose();
    
    my %vm_product_constants =
        (
         VM_PRODUCT_WS, "VM_PRODUCT_WS",
         VM_PRODUCT_GSX, "VM_PRODUCT_GSX",
         VM_PRODUCT_ESX, "VM_PRODUCT_ESX",
         VM_PRODUCT_UNKNOWN, "VM_PRODUCT_UNKNOWN",
         );
    
    &main::test_constants(%vm_product_constants);
    print "ok \$id.8 (VM_PRODUCT constants)\n" if main::verbose();
    
    my %vm_platform_constants =
        (
         VM_PLATFORM_WINDOWS, "VM_PLATFORM_WINDOWS",
         VM_PLATFORM_LINUX, "VM_PLATFORM_LINUX",
         VM_PLATFORM_VMNIX, "VM_PLATFORM_VMNIX",
         VM_PLATFORM_UNKNOWN, "VM_PLATFORM_UNKNOWN",
         );
    
    &main::test_constants(%vm_platform_constants);
    print "ok \$id.9 (VM_PLATFORM constants)\n" if main::verbose();
    
    my %vm_prodinfo_constants =
        (
         VM_PRODINFO_PRODUCT, "VM_PRODINFO_PRODUCT",
         VM_PRODINFO_PLATFORM, "VM_PRODINFO_PLATFORM",
         VM_PRODINFO_BUILD, "VM_PRODINFO_BUILD",
         VM_PRODINFO_VERSION_MAJOR, "VM_PRODINFO_VERSION_MAJOR",
         VM_PRODINFO_VERSION_MINOR, "VM_PRODINFO_VERSION_MINOR",
         VM_PRODINFO_VERSION_REVISION, "VM_PRODINFO_VERSION_REVISION",
         );
    
    &main::test_constants(%vm_prodinfo_constants);
    print "ok \$id.10 (VM_PRODINFO constants)\n" if main::verbose();
}
EOF



####################################################################
#
# Code to test for the VMware::Control API.
#
####################################################################

package VMware::Test::ControlTest;

use VMware::Control;
use VMware::Control::Server;
use VMware::Control::VM;

sub id {
    return "Control";
}

sub test {
    my $id = id();

    my $v = VMware::Control::version();
    print "ok $id.2 (API Version: ",$v,")\n" if main::verbose() && $v;
    print "not ok $id.2\n" if !$v;

    if (! $v) {
        exit 1;
    }

    my $vms = &VMware::Control::Server::new(undef, 0, undef, undef);

    print "ok $id.3 ($vms)\n" if main::verbose() && $vms;
    print "not ok $id.3 ($vms)\n" if ! $vms;

    if (! $vms) {
        exit 1;
    }

    # Load in code to test the constants and run the code itself
    eval <<EVAL;
$TEST_CONSTANT_CODE 
&test_all_constants("$id");
EVAL
    if ($@) {
	print $@;
    }
}




####################################################################
#
# Code to test for the VMware::VmPerl API.
#
####################################################################

package VMware::Test::VmPerlTest;

use VMware::VmPerl;
use VMware::VmPerl::Server;
use VMware::VmPerl::VM;

sub id {
    return "VmPerl";
}

sub test {
    my $id = id();

    my $vmp_v = VMware::VmPerl::version();
    print "ok $id.2 (API Version: ",$vmp_v,")\n" if main::verbose() && $vmp_v;
    print "not ok $id.2\n" if !$vmp_v;
    
    if (! $vmp_v) {
        exit 1;
    }
    
    my $vmp_vms = &VMware::VmPerl::Server::new();
    
    print "ok $id.3 ($vmp_vms)\n" if main::verbose() && $vmp_vms;
    print "not ok $id.3 ($vmp_vms)\n" if ! $vmp_vms;
    
    if (! $vmp_vms) {
        exit 1;
    }

    # Load in code to test the constants and run the code itself
    eval <<EVAL;
$TEST_CONSTANT_CODE 
&test_all_constants("$id");
EVAL
    if ($@) {
	print $@;
    }
}




####################################################################
#
# Code to start up the tests
#
####################################################################

package main;

BEGIN { $| = 1; }
END {print "not ok 1\n" unless $loaded;
     exit 1 unless $loaded; }

$loaded = 1;
print "ok 1\n" if verbose();

VMware::Test::ControlTest::test();
VMware::Test::VmPerlTest::test();

__END__


