| 16 | 
           rodolico | 
           1 | 
           #!/usr/bin/env perl
  | 
        
        
           | 20 | 
           rodolico | 
           2 | 
           use warnings;
  | 
        
        
           | 26 | 
           rodolico | 
           3 | 
           use strict;  
  | 
        
        
           | 2 | 
           rodolico | 
           4 | 
              | 
        
        
            | 
            | 
           5 | 
           # sysinfo
  | 
        
        
            | 
            | 
           6 | 
           # Author: R. W. Rodolico
  | 
        
        
            | 
            | 
           7 | 
           # Primary client portion of sysinfo system. Will collect information about its current
  | 
        
        
            | 
            | 
           8 | 
           # host and create a report containing the information. This report can then be processed
  | 
        
        
            | 
            | 
           9 | 
           # by process_sysinfo.pl on the collection computer.
  | 
        
        
            | 
            | 
           10 | 
           # output file consists of an XML file of the form:
  | 
        
        
            | 
            | 
           11 | 
           #  <sysinfo3.0.0>
  | 
        
        
            | 
            | 
           12 | 
           #    <diskinfo name='/dev/xvda3'>
  | 
        
        
            | 
            | 
           13 | 
           #      <fstype>ext3</fstype>
  | 
        
        
            | 
            | 
           14 | 
           #      <mount>/home</mount>
  | 
        
        
            | 
            | 
           15 | 
           #      <size>51606140</size>
  | 
        
        
            | 
            | 
           16 | 
           #      <used>331472</used>
  | 
        
        
            | 
            | 
           17 | 
           #    </diskinfo>
  | 
        
        
            | 
            | 
           18 | 
           #    <network name='eth0'>
  | 
        
        
            | 
            | 
           19 | 
           #      <address>192.168.1.3</address>
  | 
        
        
            | 
            | 
           20 | 
           #      <ip6address>fe80::216:3eff:fefb:4e10</ip6address>
  | 
        
        
            | 
            | 
           21 | 
           #      <ip6networkbits>64</ip6networkbits>
  | 
        
        
            | 
            | 
           22 | 
           #      <mac>00:16:3e:fb:4e:10</mac>
  | 
        
        
            | 
            | 
           23 | 
           #      <mtu>1500</mtu>
  | 
        
        
            | 
            | 
           24 | 
           #      <netmask>255.255.255.0</netmask>
  | 
        
        
            | 
            | 
           25 | 
           #    </network>
  | 
        
        
            | 
            | 
           26 | 
           #    <operatingsystem>
  | 
        
        
            | 
            | 
           27 | 
           #      <codename>squeeze</codename>
  | 
        
        
            | 
            | 
           28 | 
           #      <description>Debian GNU/Linux 6.0.4 (squeeze)</description>
  | 
        
        
            | 
            | 
           29 | 
           #      <distribution>Debian</distribution>
  | 
        
        
            | 
            | 
           30 | 
           #      <kernel>2.6.32-5-xen-686</kernel>
  | 
        
        
            | 
            | 
           31 | 
           #      <os_name>Linux</os_name>
  | 
        
        
            | 
            | 
           32 | 
           #      <os_version>Linux version 2.6.32-5-xen-686 (Debian 2.6.32-41) (ben@decadent.org.uk) (gcc version 4.3.5 (Debian 4.3.5-4) ) #1 SMP Mon Jan 16 19:46:09 UTC 2012</os_version>
  | 
        
        
            | 
            | 
           33 | 
           #      <release>6.0.4</release>
  | 
        
        
            | 
            | 
           34 | 
           #    </operatingsystem>
  | 
        
        
            | 
            | 
           35 | 
           #    <pci name='0000:00:00.0'>
  | 
        
        
            | 
            | 
           36 | 
           #      <class>RAM memory</class>
  | 
        
        
            | 
            | 
           37 | 
           #      <device>MCP55 Memory Controller</device>
  | 
        
        
            | 
            | 
           38 | 
           #      <rev>a2</rev>
  | 
        
        
            | 
            | 
           39 | 
           #      <sdevice>Device cb84</sdevice>
  | 
        
        
            | 
            | 
           40 | 
           #      <slot>0000:00:00.0</slot>
  | 
        
        
            | 
            | 
           41 | 
           #      <svendor>nVidia Corporation</svendor>
  | 
        
        
            | 
            | 
           42 | 
           #      <vendor>nVidia Corporation</vendor>
  | 
        
        
            | 
            | 
           43 | 
           #    </pci>
  | 
        
        
            | 
            | 
           44 | 
           #    <report>
  | 
        
        
            | 
            | 
           45 | 
           #      <client>Staffmasters</client>
  | 
        
        
            | 
            | 
           46 | 
           #      <date>2012-05-01 03:00</date>
  | 
        
        
            | 
            | 
           47 | 
           #      <version>2.0.0</version>
  | 
        
        
            | 
            | 
           48 | 
           #    </report>
  | 
        
        
            | 
            | 
           49 | 
           #    <software name='aptitude'>
  | 
        
        
            | 
            | 
           50 | 
           #      <description>terminal-based package manager (terminal interface only)</description>
  | 
        
        
            | 
            | 
           51 | 
           #      <version>0.6.3-3.2+squeeze1</version>
  | 
        
        
            | 
            | 
           52 | 
           #    </software>
  | 
        
        
            | 
            | 
           53 | 
           #    <system>
  | 
        
        
            | 
            | 
           54 | 
           #      <cpu_speed>1800.103</cpu_speed>
  | 
        
        
            | 
            | 
           55 | 
           #      <cpu_sub>i686</cpu_sub>
  | 
        
        
            | 
            | 
           56 | 
           #      <cpu_type>GenuineIntel</cpu_type>
  | 
        
        
            | 
            | 
           57 | 
           #      <hostname>backup.staffmasters.local</hostname>
  | 
        
        
            | 
            | 
           58 | 
           #      <last_boot>1333259809</last_boot>
  | 
        
        
            | 
            | 
           59 | 
           #      <memory>520852</memory>
  | 
        
        
            | 
            | 
           60 | 
           #      <num_cpu>1</num_cpu>
  | 
        
        
            | 
            | 
           61 | 
           #    </system>
  | 
        
        
            | 
            | 
           62 | 
           #  </sysinfo3.0.0>
  | 
        
        
            | 
            | 
           63 | 
              | 
        
        
            | 
            | 
           64 | 
              | 
        
        
            | 
            | 
           65 | 
           #
  | 
        
        
            | 
            | 
           66 | 
           # Version 1.3 20071104
  | 
        
        
            | 
            | 
           67 | 
           # added capability of e-mailing the results by itself and external configuration file
  | 
        
        
            | 
            | 
           68 | 
              | 
        
        
            | 
            | 
           69 | 
           # Version 1.3.1 20071110
  | 
        
        
            | 
            | 
           70 | 
           # added du -sk to explicitly do directory sizes in 'k'. Also, fixed some documentation
  | 
        
        
            | 
            | 
           71 | 
              | 
        
        
            | 
            | 
           72 | 
           # Version 1.3.3 20081104
  | 
        
        
            | 
            | 
           73 | 
           # modified hostname to hostname -f, and allowed user to place custom value in configuration file
  | 
        
        
            | 
            | 
           74 | 
           # also, modified to go with Debian standards in preparation to creating a debian package.
  | 
        
        
            | 
            | 
           75 | 
              | 
        
        
            | 
            | 
           76 | 
           # Version 2.0 20081208
  | 
        
        
            | 
            | 
           77 | 
           # Modified to use different libraries for different OS's in preparation to porting to Windows
  | 
        
        
            | 
            | 
           78 | 
           # Uses different packages based on which OS it is on.
  | 
        
        
            | 
            | 
           79 | 
              | 
        
        
            | 
            | 
           80 | 
           # Version 3.0 20120923
  | 
        
        
            | 
            | 
           81 | 
           # Major revision. Most internal intelligence pulled out and put into modules and data transfer format has been changed to YAML
  | 
        
        
            | 
            | 
           82 | 
           #
  | 
        
        
            | 
            | 
           83 | 
           # Base system only pulls client name, machine name and machine number, all of which can be set in the configuration file
  | 
        
        
            | 
            | 
           84 | 
           # if the value is not set, it attempts various means to determine the values and, if it fails, aborts with an error message
  | 
        
        
            | 
            | 
           85 | 
           #    client name -- REQUIRED, must come from configuration file
  | 
        
        
            | 
            | 
           86 | 
           #    machine name --  REQUIRED, if not set via conf file, attempts hostname command (hostname -f) or module getHostName
  | 
        
        
            | 
            | 
           87 | 
           #    machine number -- REQUIRED, if not set via conf file, attempts "echo `hostname -f`-clientname | md5sum" or module getSerial
  | 
        
        
            | 
            | 
           88 | 
           # modules are stored in "configuration directory/modules" (/etc/sysinfo/modules on most Linux systems) and are processed in 
  | 
        
        
            | 
            | 
           89 | 
           # standard sort order (case sensitive). 
  | 
        
        
            | 
            | 
           90 | 
           # Module filenames may contain alpha-numeric, underscore and the period only (files containing other characters are ignored).
  | 
        
        
            | 
            | 
           91 | 
           # Modules should set their exit code to 0 for success, and non-zero for failure
  | 
        
        
            | 
            | 
           92 | 
           # Modules should return 0 or more tab delimited, newline terminated strings, processed as one record per line
  | 
        
        
            | 
            | 
           93 | 
           # A module return string line is processed as follows:
  | 
        
        
            | 
            | 
           94 | 
           #     category \t [category \t ...] \t key \t value
  | 
        
        
            | 
            | 
           95 | 
           # example:
  | 
        
        
            | 
            | 
           96 | 
           #    System \t num_cpu \t 1
  | 
        
        
            | 
            | 
           97 | 
           #    System \t Users \t root \t /root/
  | 
        
        
            | 
            | 
           98 | 
           # (note, if non-zero exit code returned, return value is assumed to be error message and is printed to STDERR) 
  | 
        
        
            | 
            | 
           99 | 
           # sysinfo stores the result in a hash, using categories as the keys (case sensitive), thus, the above results in
  | 
        
        
            | 
            | 
           100 | 
           # $store{'System'}{'num_cpu'} = '1';
  | 
        
        
            | 
            | 
           101 | 
           # $store{'System'}{'Users'}{'root'} = '/root';
  | 
        
        
            | 
            | 
           102 | 
           # upon completion, sysinfo converts the $store hash into an XML or YAML string for transfer
  | 
        
        
            | 
            | 
           103 | 
           # It then sends it to the main server as defined in the conf file.
  | 
        
        
            | 
            | 
           104 | 
           # NOTE: YAML is hand crafted to kill any requirements for external libraries
  | 
        
        
            | 
            | 
           105 | 
           # see sub hashToYAML for details
  | 
        
        
            | 
            | 
           106 | 
              | 
        
        
           | 9 | 
           rodolico | 
           107 | 
           # Version 3.0.1 20160321
  | 
        
        
            | 
            | 
           108 | 
           # Renamed to sysinfo-client to not conflict with Linux package sysinfo
  | 
        
        
            | 
            | 
           109 | 
           # created installer in Perl to not rely on package managers
  | 
        
        
            | 
            | 
           110 | 
           # default path for configuration file changed to /etc/camp/sysinfo-client.conf
  | 
        
        
            | 
            | 
           111 | 
           # $VERSION changed to $DATA_VERSION to not conflict with $main::VERSION (script version vs data format version)
  | 
        
        
           | 13 | 
           rodolico | 
           112 | 
           #
  | 
        
        
            | 
            | 
           113 | 
           # Version 3.1.0 20160401
  | 
        
        
            | 
            | 
           114 | 
           # module and script dirs now arrays to be searched. Idea is that default
  | 
        
        
            | 
            | 
           115 | 
           #    modules/scripts are in installdir/modules or installdir/scripts, and
  | 
        
        
            | 
            | 
           116 | 
           #    user supplied are in /etc/scripts and /etc/modules
  | 
        
        
           | 14 | 
           rodolico | 
           117 | 
           # Tightened up the file systems checks, requiring all scripts and modules
  | 
        
        
            | 
            | 
           118 | 
           #    be set 0700 at least, and owned by root
  | 
        
        
           | 18 | 
           rodolico | 
           119 | 
           # Transport layers now an array, and if one fails to send the report, the others
  | 
        
        
            | 
            | 
           120 | 
           #    are tried in turn
  | 
        
        
           | 14 | 
           rodolico | 
           121 | 
           # Worked on logic for sendReport to give better error checking.
  | 
        
        
            | 
            | 
           122 | 
           # Doing a search for the configuration file matching cwd, then /etc/camp, then /usr/local/etc/camp
  | 
        
        
           | 21 | 
           rodolico | 
           123 | 
           # Self documenting, ie a key for software\tsysinfo-client\version\current version is inserted
  | 
        
        
           | 28 | 
           rodolico | 
           124 | 
           #
  | 
        
        
            | 
            | 
           125 | 
           # Version 3.1.1 20160915 RWR
  | 
        
        
            | 
            | 
           126 | 
           # set use strict and use warnings, then fixed errors
  | 
        
        
           | 37 | 
           rodolico | 
           127 | 
           #
  | 
        
        
            | 
            | 
           128 | 
           # Version 3.1.2 20160922 RWR
  | 
        
        
            | 
            | 
           129 | 
           # $exitCode 1 (not applicable to this machine) does not throw warning
  | 
        
        
            | 
            | 
           130 | 
           #
  | 
        
        
           | 42 | 
           rodolico | 
           131 | 
           # Version 3.1.3 20161010 RWR
  | 
        
        
            | 
            | 
           132 | 
           # Removed extra use warnings
  | 
        
        
           | 47 | 
           rodolico | 
           133 | 
           #
  | 
        
        
            | 
            | 
           134 | 
           # Version 3.1.4 20161023 RWR
  | 
        
        
            | 
            | 
           135 | 
           # Would error out if moduledir does not exist, added a return
  | 
        
        
           | 51 | 
           rodolico | 
           136 | 
           #
  | 
        
        
            | 
            | 
           137 | 
           # Version 3.1.5 20170327 RWR
  | 
        
        
            | 
            | 
           138 | 
           # On freeBSD systems, was looking in wrong place for configuration file
  | 
        
        
           | 59 | 
           rodolico | 
           139 | 
           #
  | 
        
        
            | 
            | 
           140 | 
           # Version 3.2.0 20180320 RWR
  | 
        
        
           | 62 | 
           rodolico | 
           141 | 
           # Major change in the configuration file format; All entries are loaded into 
  | 
        
        
            | 
            | 
           142 | 
           # hash %configuration, so clientname is no longer $clientname, but is now
  | 
        
        
            | 
            | 
           143 | 
           # $configuration{'clientname'}
  | 
        
        
            | 
            | 
           144 | 
           # NOT backwards compatible
  | 
        
        
           | 59 | 
           rodolico | 
           145 | 
           # changed configuration to be loaded into hash (vs directly loaded into variables)
  | 
        
        
            | 
            | 
           146 | 
           # added UUID to configuration file
  | 
        
        
           | 62 | 
           rodolico | 
           147 | 
           #
  | 
        
        
            | 
            | 
           148 | 
           # Version 3.2.1 20180424 RWR
  | 
        
        
            | 
            | 
           149 | 
           # Finally got a semi-stable version of this running. Fixed a bunch of bugs
  | 
        
        
            | 
            | 
           150 | 
           # and appears to be working correctly.
  | 
        
        
           | 9 | 
           rodolico | 
           151 | 
              | 
        
        
           | 62 | 
           rodolico | 
           152 | 
              | 
        
        
           | 2 | 
           rodolico | 
           153 | 
           # Following are global variables overridden if configuration file exists
  | 
        
        
            | 
            | 
           154 | 
              | 
        
        
           | 76 | 
           rodolico | 
           155 | 
           my $TESTING = 0; # level's 0 (none) to 4 defined and increase verbosity while decreasing functionality
  | 
        
        
           | 62 | 
           rodolico | 
           156 | 
           our $VERSION = '3.2.1';
  | 
        
        
           | 9 | 
           rodolico | 
           157 | 
              | 
        
        
           | 2 | 
           rodolico | 
           158 | 
           my $indentLevel = 2; # number of spaces to indent per level in XML or YAML
  | 
        
        
            | 
            | 
           159 | 
              | 
        
        
            | 
            | 
           160 | 
           $indentLevel = 3 if $TESTING;
  | 
        
        
            | 
            | 
           161 | 
           if ($TESTING) {
  | 
        
        
            | 
            | 
           162 | 
              use Data::Dumper;
  | 
        
        
            | 
            | 
           163 | 
           }
  | 
        
        
            | 
            | 
           164 | 
              | 
        
        
           | 13 | 
           rodolico | 
           165 | 
           # paths to search for configuration file
  | 
        
        
           | 51 | 
           rodolico | 
           166 | 
           my @confFileSearchPath = ( '.', '/etc/camp/sysinfo-client', '/etc/camp', '/usr/local/etc/camp/sysinfo-client' );
  | 
        
        
           | 2 | 
           rodolico | 
           167 | 
              | 
        
        
           | 13 | 
           rodolico | 
           168 | 
           my $configurationFile = 'sysinfo-client.conf'; # name of the configuration file
  | 
        
        
           | 2 | 
           rodolico | 
           169 | 
              | 
        
        
            | 
            | 
           170 | 
           my $reportDate = &getReportDate; # set report date
  | 
        
        
            | 
            | 
           171 | 
              | 
        
        
           | 59 | 
           rodolico | 
           172 | 
           my %configuration = (
  | 
        
        
           | 61 | 
           rodolico | 
           173 | 
              'moduleDirs' => [], # search paths for modules
  | 
        
        
            | 
            | 
           174 | 
              'scriptDirs' => [], # search paths for scripts
  | 
        
        
           | 59 | 
           rodolico | 
           175 | 
              'clientName' => '',  # Required!! Must be set in conf file (no defaults)
  | 
        
        
            | 
            | 
           176 | 
              'serialNumber' => '', # serial number of machine
  | 
        
        
            | 
            | 
           177 | 
              'UUID'         => '', # UUID of machine
  | 
        
        
           | 61 | 
           rodolico | 
           178 | 
              'transports'   => [], # hash with various transports
  | 
        
        
            | 
            | 
           179 | 
              'hostname' => &getHostName() # fully qualified host name of machine
  | 
        
        
           | 59 | 
           rodolico | 
           180 | 
           )
  | 
        
        
            | 
            | 
           181 | 
           ;
  | 
        
        
           | 2 | 
           rodolico | 
           182 | 
              | 
        
        
           | 9 | 
           rodolico | 
           183 | 
           my $DATA_VERSION = '3.0.0'; # used in sending the data file. sets version of XML/YAML data file
  | 
        
        
           | 2 | 
           rodolico | 
           184 | 
              | 
        
        
           | 13 | 
           rodolico | 
           185 | 
              | 
        
        
            | 
            | 
           186 | 
              | 
        
        
           | 2 | 
           rodolico | 
           187 | 
           #######################################################
  | 
        
        
            | 
            | 
           188 | 
           #
  | 
        
        
           | 13 | 
           rodolico | 
           189 | 
           # findFile( $filename, @directories )
  | 
        
        
            | 
            | 
           190 | 
           #
  | 
        
        
            | 
            | 
           191 | 
           # Locates a file by searching sequentially in one or more
  | 
        
        
            | 
            | 
           192 | 
           # directories, returning the first one found
  | 
        
        
            | 
            | 
           193 | 
           # 
  | 
        
        
            | 
            | 
           194 | 
           # Returns '' if not found
  | 
        
        
            | 
            | 
           195 | 
           #
  | 
        
        
            | 
            | 
           196 | 
           #######################################################
  | 
        
        
            | 
            | 
           197 | 
              | 
        
        
            | 
            | 
           198 | 
           sub findFile {
  | 
        
        
           | 59 | 
           rodolico | 
           199 | 
              my ( $filename, $directories ) = @_;
  | 
        
        
            | 
            | 
           200 | 
              for ( my $i = 0; $i < scalar( @{$directories} ); $i++ ) {
  | 
        
        
            | 
            | 
           201 | 
                 my $confFile = $$directories[$i] . '/' . $filename;
  | 
        
        
           | 13 | 
           rodolico | 
           202 | 
                 return $confFile if ( -f $confFile );
  | 
        
        
            | 
            | 
           203 | 
              }
  | 
        
        
            | 
            | 
           204 | 
              return '';
  | 
        
        
            | 
            | 
           205 | 
           }
  | 
        
        
            | 
            | 
           206 | 
              | 
        
        
            | 
            | 
           207 | 
              | 
        
        
            | 
            | 
           208 | 
           #######################################################
  | 
        
        
            | 
            | 
           209 | 
           #
  | 
        
        
           | 2 | 
           rodolico | 
           210 | 
           # loadConfigurationFile($confFile)
  | 
        
        
            | 
            | 
           211 | 
           #
  | 
        
        
            | 
            | 
           212 | 
           # Loads configuration file defined by $configurationFile, and dies if not available
  | 
        
        
            | 
            | 
           213 | 
           # Reads entire contents into memory where it is eval'd in main program
  | 
        
        
            | 
            | 
           214 | 
           # Parameters: configuration file fully path/file name
  | 
        
        
            | 
            | 
           215 | 
           # NOTE: conf file must be a valid Perl file
  | 
        
        
            | 
            | 
           216 | 
           #
  | 
        
        
            | 
            | 
           217 | 
           #######################################################
  | 
        
        
            | 
            | 
           218 | 
              | 
        
        
            | 
            | 
           219 | 
           sub loadConfigurationFile {
  | 
        
        
           | 14 | 
           rodolico | 
           220 | 
              my ( $fileName, @searchPath ) = @_;
  | 
        
        
           | 13 | 
           rodolico | 
           221 | 
              my $confFile;
  | 
        
        
           | 59 | 
           rodolico | 
           222 | 
              if ( $confFile = &findFile( $fileName, \@searchPath ) ) {
  | 
        
        
           | 61 | 
           rodolico | 
           223 | 
                 print "Opening configuration from $confFile\n" if $TESTING > 2;
  | 
        
        
           | 13 | 
           rodolico | 
           224 | 
                 open CONFFILE, "<$confFile" or die "Can not open configuration file $confFile: $!\n";
  | 
        
        
            | 
            | 
           225 | 
                 my $confFileContents = join( '', <CONFFILE> ); # just slurp it into memory
  | 
        
        
            | 
            | 
           226 | 
                 close CONFFILE;
  | 
        
        
            | 
            | 
           227 | 
                 return ($confFileContents);
  | 
        
        
            | 
            | 
           228 | 
              }
  | 
        
        
           | 14 | 
           rodolico | 
           229 | 
              die "Can not find $fileName in any of " . join( "\n\t", @searchPath ) . "\n";
  | 
        
        
           | 2 | 
           rodolico | 
           230 | 
           }
  | 
        
        
            | 
            | 
           231 | 
              | 
        
        
            | 
            | 
           232 | 
           #######################################################
  | 
        
        
            | 
            | 
           233 | 
           #
  | 
        
        
            | 
            | 
           234 | 
           # sendResults( $parameters, $message, $scriptDirectory )
  | 
        
        
            | 
            | 
           235 | 
           #
  | 
        
        
            | 
            | 
           236 | 
           # Sends results of run to server using external script. If external
  | 
        
        
            | 
            | 
           237 | 
           # script not defined, just print to STDOUT
  | 
        
        
            | 
            | 
           238 | 
           #
  | 
        
        
            | 
            | 
           239 | 
           # Parameters
  | 
        
        
            | 
            | 
           240 | 
           #  $parameters - a hash containing the information necessary to make the transfer
  | 
        
        
            | 
            | 
           241 | 
           #  $message - the message to be sent
  | 
        
        
            | 
            | 
           242 | 
           #  $scriptDirectory - path (not filename) of script to be executed
  | 
        
        
            | 
            | 
           243 | 
           # 
  | 
        
        
            | 
            | 
           244 | 
           # $parameters contains different key/value pairs depending on the script used
  | 
        
        
            | 
            | 
           245 | 
           #             for example, a stand-alone SMTP script may need a username/password,
  | 
        
        
            | 
            | 
           246 | 
           #             smtp server name, port number, from and to address
  | 
        
        
            | 
            | 
           247 | 
           #             while an http transfer may only need a script name
  | 
        
        
            | 
            | 
           248 | 
           #             See the individual scripts to determine what parameters need to be
  | 
        
        
            | 
            | 
           249 | 
           #             filled in.
  | 
        
        
            | 
            | 
           250 | 
           #             The only required parameter is 'sendScript' which must contain the
  | 
        
        
            | 
            | 
           251 | 
           #             name of the script to execute (and it must be located in $scriptDirectory)
  | 
        
        
            | 
            | 
           252 | 
           # SCRIPT must contain one sub named doit, that accepts three parameters, the hash, 
  | 
        
        
            | 
            | 
           253 | 
           #       the message, and, optionally, the script directory
  | 
        
        
            | 
            | 
           254 | 
           #
  | 
        
        
            | 
            | 
           255 | 
           # If script not defined, just dump to STDOUT. With a properly set up cron job, the output
  | 
        
        
            | 
            | 
           256 | 
           # would then be sent via e-mail to an administrative account, possibly root
  | 
        
        
            | 
            | 
           257 | 
           #
  | 
        
        
            | 
            | 
           258 | 
           #######################################################
  | 
        
        
            | 
            | 
           259 | 
           sub sendResults {
  | 
        
        
           | 62 | 
           rodolico | 
           260 | 
              my ( $globals, $transports, $message, $scriptDirectory ) = @_;
  | 
        
        
            | 
            | 
           261 | 
           #   die Dumper( $transports );
  | 
        
        
            | 
            | 
           262 | 
              foreach my $key ( @$transports ) {
  | 
        
        
            | 
            | 
           263 | 
                 if ( $key->{'sendScript'} ) {
  | 
        
        
            | 
            | 
           264 | 
                    print "Trying to find file " . $key->{'sendScript'} . " in " . join( "\n\t", @{$scriptDirectory} ) . "\n" if $TESTING > 2;;
  | 
        
        
            | 
            | 
           265 | 
                    my $sendScript = &findFile( $key->{'sendScript'}, $scriptDirectory );
  | 
        
        
           | 19 | 
           rodolico | 
           266 | 
                    if ( $sendScript ) {
  | 
        
        
           | 18 | 
           rodolico | 
           267 | 
                       # load the chosen script into memory
  | 
        
        
            | 
            | 
           268 | 
                       require $sendScript;
  | 
        
        
           | 19 | 
           rodolico | 
           269 | 
                       # merge the globals in
  | 
        
        
            | 
            | 
           270 | 
                       while ( my ( $gkey, $value ) = each %$globals ) { 
  | 
        
        
           | 62 | 
           rodolico | 
           271 | 
                          $key->{$gkey} = $value; 
  | 
        
        
           | 19 | 
           rodolico | 
           272 | 
                       }
  | 
        
        
           | 20 | 
           rodolico | 
           273 | 
                       # do variable substitution for any values which need it
  | 
        
        
           | 62 | 
           rodolico | 
           274 | 
                       foreach my $thisOne ( keys %{$key} ) {
  | 
        
        
           | 76 | 
           rodolico | 
           275 | 
                          print "$thisOne\n" if $TESTING > 3;
  | 
        
        
           | 62 | 
           rodolico | 
           276 | 
                          if ( $key->{$thisOne} =~ m/(\$configuration\{'hostname'\})|(\$reportDate)|(\$configuration\{'clientName'\})|(\$configuration\{'serialNumber'\})/ ) {
  | 
        
        
            | 
            | 
           277 | 
                             $key->{$thisOne} = eval "\"$key->{$thisOne}\"";
  | 
        
        
           | 20 | 
           rodolico | 
           278 | 
                          }
  | 
        
        
            | 
            | 
           279 | 
                       }
  | 
        
        
            | 
            | 
           280 | 
              | 
        
        
           | 62 | 
           rodolico | 
           281 | 
                       #%$transports{$key}{keys %$globals} = values %$globals;
  | 
        
        
            | 
            | 
           282 | 
                       #print Dumper( $$transports[$key] );
  | 
        
        
           | 20 | 
           rodolico | 
           283 | 
                       #next;
  | 
        
        
           | 18 | 
           rodolico | 
           284 | 
                       # execute the "doit" sub from that script
  | 
        
        
           | 62 | 
           rodolico | 
           285 | 
                       if ( $TESTING > 3 ) {
  | 
        
        
            | 
            | 
           286 | 
                          print $message;
  | 
        
        
            | 
            | 
           287 | 
                       } else {
  | 
        
        
            | 
            | 
           288 | 
                          my $return = &doit( $key, $message );
  | 
        
        
            | 
            | 
           289 | 
                          return $return if ( $return == 1 );
  | 
        
        
            | 
            | 
           290 | 
                       }
  | 
        
        
           | 18 | 
           rodolico | 
           291 | 
                    } else {
  | 
        
        
           | 62 | 
           rodolico | 
           292 | 
                       print "Could not find " . $$transports[$key]{'sendScript'} . ", trying next transport\n";
  | 
        
        
           | 18 | 
           rodolico | 
           293 | 
                    } # if..else
  | 
        
        
            | 
            | 
           294 | 
                 } # if
  | 
        
        
            | 
            | 
           295 | 
              } # foreach
  | 
        
        
            | 
            | 
           296 | 
              # if we made it here, we have not sent the report, so just return it to the user
  | 
        
        
           | 62 | 
           rodolico | 
           297 | 
              #print $message;
  | 
        
        
           | 16 | 
           rodolico | 
           298 | 
              return 1;
  | 
        
        
           | 2 | 
           rodolico | 
           299 | 
           }
  | 
        
        
            | 
            | 
           300 | 
              | 
        
        
            | 
            | 
           301 | 
           #######################################################
  | 
        
        
            | 
            | 
           302 | 
           #
  | 
        
        
            | 
            | 
           303 | 
           # getReportDate
  | 
        
        
            | 
            | 
           304 | 
           #
  | 
        
        
            | 
            | 
           305 | 
           # return current system date as YYYY-MM-DD HH:MM:SS
  | 
        
        
            | 
            | 
           306 | 
           #
  | 
        
        
            | 
            | 
           307 | 
           #######################################################
  | 
        
        
            | 
            | 
           308 | 
           sub getReportDate {
  | 
        
        
           | 28 | 
           rodolico | 
           309 | 
              my ($second, $minute, $hour, $dayOfMonth, $month, $year) = localtime();
  | 
        
        
           | 2 | 
           rodolico | 
           310 | 
              return sprintf( "%4u-%02u-%02u %02u:%02u:%02u", $year+1900, $month+1, $dayOfMonth, $hour, $minute, $second );
  | 
        
        
            | 
            | 
           311 | 
           }
  | 
        
        
            | 
            | 
           312 | 
              | 
        
        
            | 
            | 
           313 | 
           #######################################################
  | 
        
        
            | 
            | 
           314 | 
           #
  | 
        
        
            | 
            | 
           315 | 
           # getHostName
  | 
        
        
            | 
            | 
           316 | 
           #
  | 
        
        
            | 
            | 
           317 | 
           # return hostname from hostname -f
  | 
        
        
            | 
            | 
           318 | 
           #
  | 
        
        
            | 
            | 
           319 | 
           #######################################################
  | 
        
        
            | 
            | 
           320 | 
           sub getHostName {
  | 
        
        
           | 28 | 
           rodolico | 
           321 | 
              my $hostname = `hostname -f`;
  | 
        
        
           | 2 | 
           rodolico | 
           322 | 
              chomp $hostname;
  | 
        
        
            | 
            | 
           323 | 
              return $hostname;
  | 
        
        
            | 
            | 
           324 | 
           }
  | 
        
        
            | 
            | 
           325 | 
              | 
        
        
            | 
            | 
           326 | 
           #######################################################
  | 
        
        
            | 
            | 
           327 | 
           #
  | 
        
        
           | 18 | 
           rodolico | 
           328 | 
           # escapeForYAML
  | 
        
        
           | 2 | 
           rodolico | 
           329 | 
           #
  | 
        
        
           | 18 | 
           rodolico | 
           330 | 
           # Escapes values put into YAML report
  | 
        
        
           | 2 | 
           rodolico | 
           331 | 
           #
  | 
        
        
            | 
            | 
           332 | 
           #######################################################
  | 
        
        
            | 
            | 
           333 | 
           sub escapeForYAML {
  | 
        
        
            | 
            | 
           334 | 
              my $value = shift;
  | 
        
        
            | 
            | 
           335 | 
              $value =~ s/'/\\'/gi; # escape single quotes
  | 
        
        
            | 
            | 
           336 | 
              $value =~ s/"/\\"/gi; # escape double quotes
  | 
        
        
            | 
            | 
           337 | 
              # pound sign indicates start of a comment and thus loses part
  | 
        
        
            | 
            | 
           338 | 
              # of strings. Surrounding it by double quotes in next statement
  | 
        
        
            | 
            | 
           339 | 
              # allows 
  | 
        
        
            | 
            | 
           340 | 
              $value = '"' . $value . '"' if ( $value =~ m/[#:]/ );
  | 
        
        
            | 
            | 
           341 | 
              return $value;
  | 
        
        
            | 
            | 
           342 | 
           }
  | 
        
        
            | 
            | 
           343 | 
              | 
        
        
            | 
            | 
           344 | 
           #######################################################
  | 
        
        
            | 
            | 
           345 | 
           #
  | 
        
        
            | 
            | 
           346 | 
           # hashToYAML( $hashRef, $indent )
  | 
        
        
            | 
            | 
           347 | 
           #
  | 
        
        
            | 
            | 
           348 | 
           # Converts a hash to a YAML string
  | 
        
        
            | 
            | 
           349 | 
           #
  | 
        
        
            | 
            | 
           350 | 
           # NOTE: This routine recursively calls itself for every level
  | 
        
        
            | 
            | 
           351 | 
           #       in the hash
  | 
        
        
            | 
            | 
           352 | 
           #
  | 
        
        
            | 
            | 
           353 | 
           # Parameters
  | 
        
        
            | 
            | 
           354 | 
           #     $hashref - reference (address) of a hash
  | 
        
        
            | 
            | 
           355 | 
           #     $indent  - current indent level, defaults to 0
  | 
        
        
            | 
            | 
           356 | 
           #
  | 
        
        
            | 
            | 
           357 | 
           # Even though there are some very good libraries that do this
  | 
        
        
            | 
            | 
           358 | 
           # I chose to hand-code it so sysinfo can be run with no libraries
  | 
        
        
            | 
            | 
           359 | 
           # loaded. I chose to NOT do a full implementation, so special chars
  | 
        
        
            | 
            | 
           360 | 
           # that would normally be escaped are not in here. 
  | 
        
        
            | 
            | 
           361 | 
           # However, I followed all the RFC for the values that were given, so
  | 
        
        
            | 
            | 
           362 | 
           # assume any YAML reader can parse this
  | 
        
        
            | 
            | 
           363 | 
           # NOTE: YAML appears to give a resulting file 1/3 smaller than the above
  | 
        
        
            | 
            | 
           364 | 
           #       XML, and compresses down in like manner
  | 
        
        
            | 
            | 
           365 | 
           #
  | 
        
        
            | 
            | 
           366 | 
           #######################################################
  | 
        
        
            | 
            | 
           367 | 
           sub hashToYAML {
  | 
        
        
            | 
            | 
           368 | 
              my ($hashRef, $indent) = @_;
  | 
        
        
            | 
            | 
           369 | 
              $indent = 0 unless $indent; # default to 0 if not defined
  | 
        
        
            | 
            | 
           370 | 
              | 
        
        
            | 
            | 
           371 | 
              my $output; # where the output is stored
  | 
        
        
            | 
            | 
           372 | 
              foreach my $key ( keys %$hashRef ) { # for each key in the current reference
  | 
        
        
            | 
            | 
           373 | 
                 print "Looking at $key\n" if $TESTING > 3;
  | 
        
        
            | 
            | 
           374 | 
                 # see http://www.perlmonks.org/?node_id=175651 for isa function
  | 
        
        
            | 
            | 
           375 | 
                 if ( UNIVERSAL::isa( $$hashRef{$key}, 'HASH' ) ) { # is the value another hash?
  | 
        
        
            | 
            | 
           376 | 
                       # NOTE: unlike xml, indentation is NOT optional in YAML, so the following line verifies $indentlevel is non-zero
  | 
        
        
            | 
            | 
           377 | 
                       #       and, if it is, uses a default 3 character indentation
  | 
        
        
            | 
            | 
           378 | 
                       $output .= (' ' x $indent ) . &escapeForYAML($key) . ":\n" . # key, plus colon, plus newline
  | 
        
        
            | 
            | 
           379 | 
                               &hashToYAML( $$hashRef{$key}, $indent+($indentLevel ? $indentLevel : 3) ) . # add results of recursive call
  | 
        
        
            | 
            | 
           380 | 
                               "\n";
  | 
        
        
            | 
            | 
           381 | 
                 } elsif ( UNIVERSAL::isa( $$hashRef{$key}, 'ARRAY' ) ) { # is it an array? ignore it
  | 
        
        
            | 
            | 
           382 | 
                 } else { # it is a scalar, so just do <key>value</key>
  | 
        
        
            | 
            | 
           383 | 
                    $output .= (' ' x $indent ) . &escapeForYAML($key) . ': ' . &escapeForYAML($$hashRef{$key}) . "\n";
  | 
        
        
            | 
            | 
           384 | 
                 }
  | 
        
        
            | 
            | 
           385 | 
              }
  | 
        
        
            | 
            | 
           386 | 
              return $output;
  | 
        
        
            | 
            | 
           387 | 
           }
  | 
        
        
            | 
            | 
           388 | 
              | 
        
        
            | 
            | 
           389 | 
              | 
        
        
            | 
            | 
           390 | 
           #######################################################
  | 
        
        
            | 
            | 
           391 | 
           #
  | 
        
        
            | 
            | 
           392 | 
           # tabDelimitedToHash ($hashRef, $tabdelim)
  | 
        
        
            | 
            | 
           393 | 
           #
  | 
        
        
            | 
            | 
           394 | 
           # Takes a tab delimited multi line string and adds it
  | 
        
        
            | 
            | 
           395 | 
           # to a hash. The final field in each line is considered to
  | 
        
        
            | 
            | 
           396 | 
           # be the value, and all prior fields are considered to be
  | 
        
        
            | 
            | 
           397 | 
           # hierachial keys.
  | 
        
        
            | 
            | 
           398 | 
           #
  | 
        
        
            | 
            | 
           399 | 
           # Parameters
  | 
        
        
            | 
            | 
           400 | 
           #     $hashref - reference (address) of a hash
  | 
        
        
            | 
            | 
           401 | 
           #     $tabdelim - A tab delimited, newline terminated set of records
  | 
        
        
            | 
            | 
           402 | 
           #
  | 
        
        
            | 
            | 
           403 | 
           #
  | 
        
        
            | 
            | 
           404 | 
           #######################################################
  | 
        
        
            | 
            | 
           405 | 
           sub tabDelimitedToHash {
  | 
        
        
            | 
            | 
           406 | 
              my ($hashRef, $tabdelim) = @_;
  | 
        
        
            | 
            | 
           407 | 
              foreach my $line ( split( "\n", $tabdelim ) ) { # split on newlines, then process each line in turn
  | 
        
        
            | 
            | 
           408 | 
                 $line =~ s/'/\\'/gi; # escape single quotes
  | 
        
        
           | 28 | 
           rodolico | 
           409 | 
                 my @fields = split( / *\t */, $line ); # get all the field values into array
  | 
        
        
           | 2 | 
           rodolico | 
           410 | 
                 my $theValue = pop @fields; # the last one is the value, so save it
  | 
        
        
            | 
            | 
           411 | 
                 # now, we build a Perl statement that would create the assignment. The goal is
  | 
        
        
            | 
            | 
           412 | 
                 # to have a string that says something like $$hashRef{'key'}{'key'} = $value;
  | 
        
        
            | 
            | 
           413 | 
                 # then, eval that.
  | 
        
        
            | 
            | 
           414 | 
                 my $command = '$$hashRef'; # start with the name of the dereferenced hash (parameter 1)
  | 
        
        
            | 
            | 
           415 | 
                 while (my $key = shift @fields) { # while we have a key, from left to right
  | 
        
        
            | 
            | 
           416 | 
                    $command .= '{' . "'$key'" . '}'; # build it as {'key'} concated to string
  | 
        
        
            | 
            | 
           417 | 
                 }
  | 
        
        
            | 
            | 
           418 | 
                 $command .= "='$theValue';"; # add the assignment
  | 
        
        
            | 
            | 
           419 | 
                 #print STDERR "$command\n"; 
  | 
        
        
            | 
            | 
           420 | 
                 eval $command; # eval the string to make the actual assignment
  | 
        
        
            | 
            | 
           421 | 
              }
  | 
        
        
            | 
            | 
           422 | 
           }
  | 
        
        
            | 
            | 
           423 | 
              | 
        
        
            | 
            | 
           424 | 
           #######################################################
  | 
        
        
            | 
            | 
           425 | 
           #
  | 
        
        
           | 13 | 
           rodolico | 
           426 | 
           # validatePermission ( $file )
  | 
        
        
            | 
            | 
           427 | 
           #
  | 
        
        
            | 
            | 
           428 | 
           # Checks that file is owned by root, and has permission
  | 
        
        
            | 
            | 
           429 | 
           # 0700 or less
  | 
        
        
            | 
            | 
           430 | 
           # 
  | 
        
        
            | 
            | 
           431 | 
           # Returns empty string on success, error message
  | 
        
        
            | 
            | 
           432 | 
           # on failure
  | 
        
        
            | 
            | 
           433 | 
           #
  | 
        
        
            | 
            | 
           434 | 
           #######################################################
  | 
        
        
            | 
            | 
           435 | 
              | 
        
        
            | 
            | 
           436 | 
           sub validatePermission {
  | 
        
        
            | 
            | 
           437 | 
              my $file = shift;
  | 
        
        
           | 14 | 
           rodolico | 
           438 | 
              my $return;
  | 
        
        
           | 13 | 
           rodolico | 
           439 | 
              # must be owned by root
  | 
        
        
           | 28 | 
           rodolico | 
           440 | 
              my $owner = (stat($file))[4];
  | 
        
        
           | 13 | 
           rodolico | 
           441 | 
              $return .= " - Bad Owner [$owner]" if $owner;
  | 
        
        
            | 
            | 
           442 | 
              # must not have any permissions for group or world
  | 
        
        
            | 
            | 
           443 | 
              # ie, 0700 or less
  | 
        
        
           | 28 | 
           rodolico | 
           444 | 
              my $mode = (stat($file))[2];
  | 
        
        
           | 13 | 
           rodolico | 
           445 | 
              $mode = sprintf( '%04o', $mode & 07777 );
  | 
        
        
            | 
            | 
           446 | 
              $return .= " - Bad Permission [$mode]" unless $mode =~ m/0.00/;
  | 
        
        
            | 
            | 
           447 | 
              return $return ? $file . $return : '';
  | 
        
        
            | 
            | 
           448 | 
           }
  | 
        
        
            | 
            | 
           449 | 
              | 
        
        
            | 
            | 
           450 | 
           #######################################################
  | 
        
        
            | 
            | 
           451 | 
           #
  | 
        
        
           | 2 | 
           rodolico | 
           452 | 
           # ProcessModules ( $system, $moduleDir )
  | 
        
        
            | 
            | 
           453 | 
           #
  | 
        
        
            | 
            | 
           454 | 
           # Processes all modules in $moduleDir, adding result to $system hash
  | 
        
        
            | 
            | 
           455 | 
           # 
  | 
        
        
            | 
            | 
           456 | 
           # Parameters
  | 
        
        
            | 
            | 
           457 | 
           #     $system - reference (address) of a hash
  | 
        
        
            | 
            | 
           458 | 
           #     $moduleDir - full path to a directory containing executable scripts
  | 
        
        
            | 
            | 
           459 | 
           #  
  | 
        
        
            | 
            | 
           460 | 
           # Each file in the $moduleDir directory that matches the regex in the grep
  | 
        
        
            | 
            | 
           461 | 
           # and is executable is run. It is assumed the script will return 0 on success
  | 
        
        
            | 
            | 
           462 | 
           # or a non-zero on failure
  | 
        
        
            | 
            | 
           463 | 
           # The output of the script is assumed to be a tab delimited, newline separated
  | 
        
        
            | 
            | 
           464 | 
           # list of records that should be added to the hash $system. This is done by calling 
  | 
        
        
            | 
            | 
           465 | 
           # &parseModule above.
  | 
        
        
            | 
            | 
           466 | 
           # on failure, the returned output of the script is assumed to be an error message
  | 
        
        
            | 
            | 
           467 | 
           # and is displayed on STDERR
  | 
        
        
            | 
            | 
           468 | 
           #######################################################
  | 
        
        
            | 
            | 
           469 | 
           sub ProcessModules {
  | 
        
        
            | 
            | 
           470 | 
              my ( $system, $moduleDir ) = @_;
  | 
        
        
            | 
            | 
           471 | 
              # open the module directory
  | 
        
        
           | 47 | 
           rodolico | 
           472 | 
              return unless -d $moduleDir;
  | 
        
        
           | 2 | 
           rodolico | 
           473 | 
              opendir( my $dh, $moduleDir ) || die "Module Directory $moduleDir can not be opened: $!\n";
  | 
        
        
            | 
            | 
           474 | 
              # and get all files which are executable and contain nothing but alpha-numerics and underscores (must begin with alpha-numeric)
  | 
        
        
            | 
            | 
           475 | 
              my @modules = grep { /^[a-zA-Z0-9][a-zA-Z0-9_]+$/ && -x "$moduleDir/$_" } readdir( $dh );
  | 
        
        
            | 
            | 
           476 | 
              closedir $dh;
  | 
        
        
           | 28 | 
           rodolico | 
           477 | 
              foreach my $modFile ( sort @modules ) { # for each valid script
  | 
        
        
           | 14 | 
           rodolico | 
           478 | 
                 if ( my $error = &validatePermission( "$moduleDir$modFile" ) ) {
  | 
        
        
           | 13 | 
           rodolico | 
           479 | 
                    print STDERR "Not Processed: $error\n";
  | 
        
        
            | 
            | 
           480 | 
                    next;
  | 
        
        
            | 
            | 
           481 | 
                 }
  | 
        
        
           | 2 | 
           rodolico | 
           482 | 
                 print "Processing module $moduleDir$modFile\n" if $TESTING > 2;
  | 
        
        
            | 
            | 
           483 | 
                 my $output = qx/$moduleDir$modFile $moduleDir/; # execute it and grab the output
  | 
        
        
            | 
            | 
           484 | 
                 my $exitCode = $? >> 8; # process the exitCode
  | 
        
        
           | 37 | 
           rodolico | 
           485 | 
                 # exitCode 0 - processed normally
  | 
        
        
            | 
            | 
           486 | 
                 # exitCode 1 - not applicable to this machine
  | 
        
        
            | 
            | 
           487 | 
                 if ( $exitCode && $exitCode > 1) { # if non-zero, error, so show an error message
  | 
        
        
           | 2 | 
           rodolico | 
           488 | 
                    warn "Error in $moduleDir$modFile, [$output]\n";
  | 
        
        
            | 
            | 
           489 | 
                 } else { # otherwise, call tabDelimitedToHash to save the data
  | 
        
        
            | 
            | 
           490 | 
                    &tabDelimitedToHash( $system, $output );
  | 
        
        
           | 21 | 
           rodolico | 
           491 | 
                 } # if
  | 
        
        
            | 
            | 
           492 | 
              } # foreach
  | 
        
        
            | 
            | 
           493 | 
              # add sysinfo-client (me) to the software list, since we're obviously installed
  | 
        
        
            | 
            | 
           494 | 
              &tabDelimitedToHash( $system, "software\tsysinfo-client\tversion\t$main::VERSION\n" );
  | 
        
        
           | 2 | 
           rodolico | 
           495 | 
           }
  | 
        
        
            | 
            | 
           496 | 
              | 
        
        
           | 20 | 
           rodolico | 
           497 | 
           sub processParameters {
  | 
        
        
            | 
            | 
           498 | 
              while ( my $parameter = shift ) {
  | 
        
        
            | 
            | 
           499 | 
                 if ( $parameter eq '-v' ) {
  | 
        
        
            | 
            | 
           500 | 
                    print "$main::VERSION\n";
  | 
        
        
            | 
            | 
           501 | 
                    exit;
  | 
        
        
            | 
            | 
           502 | 
                 }
  | 
        
        
            | 
            | 
           503 | 
              } # while
  | 
        
        
            | 
            | 
           504 | 
           }
  | 
        
        
            | 
            | 
           505 | 
              | 
        
        
            | 
            | 
           506 | 
           &processParameters( @ARGV );
  | 
        
        
            | 
            | 
           507 | 
              | 
        
        
           | 14 | 
           rodolico | 
           508 | 
           # load the configuration file
  | 
        
        
           | 13 | 
           rodolico | 
           509 | 
              | 
        
        
           | 14 | 
           rodolico | 
           510 | 
           #die "Searching for $configurationFile in = \n" . join( "\n", @confFileSearchPath ) . "\n";
  | 
        
        
           | 75 | 
           rodolico | 
           511 | 
           eval ( &loadConfigurationFile( $configurationFile, @confFileSearchPath) ) or die "Could not load config: $@\n";
  | 
        
        
           | 61 | 
           rodolico | 
           512 | 
           die Dumper( \%configuration ) . "\n" if $TESTING > 4;
  | 
        
        
            | 
            | 
           513 | 
              | 
        
        
           | 2 | 
           rodolico | 
           514 | 
           # user did not define a serial number, so make something up
  | 
        
        
           | 59 | 
           rodolico | 
           515 | 
           $configuration{'serialNumber'} = '' unless $configuration{'serialNumber'};
  | 
        
        
           | 2 | 
           rodolico | 
           516 | 
           # oops, no client name (required) so tell them and exit
  | 
        
        
           | 61 | 
           rodolico | 
           517 | 
           die "No client name defined in $configurationFile" unless $configuration{'clientName'};
  | 
        
        
           | 2 | 
           rodolico | 
           518 | 
              | 
        
        
           | 61 | 
           rodolico | 
           519 | 
           $TESTING = $configuration{'TESTING'} if defined $configuration{'TESTING'};
  | 
        
        
            | 
            | 
           520 | 
              | 
        
        
           | 76 | 
           rodolico | 
           521 | 
           print "Testing => $TESTING\n" if $TESTING;
  | 
        
        
            | 
            | 
           522 | 
              | 
        
        
            | 
            | 
           523 | 
              | 
        
        
           | 2 | 
           rodolico | 
           524 | 
           my $System; # hash reference that will store all info we are going to send to the server
  | 
        
        
            | 
            | 
           525 | 
           # some defaults.
  | 
        
        
           | 9 | 
           rodolico | 
           526 | 
           $$System{'report'}{'version'} = $DATA_VERSION;
  | 
        
        
           | 2 | 
           rodolico | 
           527 | 
           $$System{'report'}{'date'} = $reportDate;
  | 
        
        
           | 59 | 
           rodolico | 
           528 | 
           $$System{'report'}{'client'} = $configuration{'clientName'};
  | 
        
        
            | 
            | 
           529 | 
           $$System{'system'}{'hostname'} = $configuration{'hostname'};
  | 
        
        
            | 
            | 
           530 | 
           $$System{'system'}{'serial'} = $configuration{'serialNumber'};
  | 
        
        
           | 62 | 
           rodolico | 
           531 | 
           $$System{'system'}{'UUID'} = $configuration{'UUID'};
  | 
        
        
           | 2 | 
           rodolico | 
           532 | 
              | 
        
        
            | 
            | 
           533 | 
           # process any modules in the system
  | 
        
        
           | 59 | 
           rodolico | 
           534 | 
           foreach my $moduleDir ( @{$configuration{'moduleDirs'}} ) {
  | 
        
        
           | 13 | 
           rodolico | 
           535 | 
              &ProcessModules( $System, "$moduleDir/" );
  | 
        
        
            | 
            | 
           536 | 
           }
  | 
        
        
           | 2 | 
           rodolico | 
           537 | 
              | 
        
        
            | 
            | 
           538 | 
           # now, everything ins in $System, so convert it to the proper output format
  | 
        
        
           | 20 | 
           rodolico | 
           539 | 
           my $out =  "#sysinfo: $VERSION YAML\n---\n" . &hashToYAML( $System ) . "...\n";
  | 
        
        
           | 2 | 
           rodolico | 
           540 | 
              | 
        
        
           | 62 | 
           rodolico | 
           541 | 
           #print Data::Dumper->Dump([$System],['System']) if $TESTING>2;
  | 
        
        
           | 2 | 
           rodolico | 
           542 | 
              | 
        
        
           | 19 | 
           rodolico | 
           543 | 
           # load some global values for use in the script, if required
  | 
        
        
            | 
            | 
           544 | 
           my $globals = { 
  | 
        
        
            | 
            | 
           545 | 
                 'data version' => $DATA_VERSION,
  | 
        
        
            | 
            | 
           546 | 
                 'report date'  => $reportDate,
  | 
        
        
           | 59 | 
           rodolico | 
           547 | 
                 'client name'  => $configuration{'clientName'},
  | 
        
        
            | 
            | 
           548 | 
                 'host name'    => $configuration{'hostname'},
  | 
        
        
           | 61 | 
           rodolico | 
           549 | 
                 'serial number'=> $configuration{'serialNumber'},
  | 
        
        
            | 
            | 
           550 | 
                 'UUID'         => $configuration{'UUID'}
  | 
        
        
           | 19 | 
           rodolico | 
           551 | 
                 };
  | 
        
        
           | 62 | 
           rodolico | 
           552 | 
              | 
        
        
           | 2 | 
           rodolico | 
           553 | 
           # and send the results to the server
  | 
        
        
           | 59 | 
           rodolico | 
           554 | 
           if ( my $success = &sendResults( $globals, $configuration{'transports'}, $out, $configuration{'scriptDirs'} ) != 1 ) {
  | 
        
        
            | 
            | 
           555 | 
              print "Error $success while sending report from $configuration{'hostname'}\n";
  | 
        
        
           | 16 | 
           rodolico | 
           556 | 
           }
  | 
        
        
           | 2 | 
           rodolico | 
           557 | 
              | 
        
        
           | 9 | 
           rodolico | 
           558 | 
           1;
  |