inspec 4.3.2 → 4.6.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Gemfile +36 -38
- data/README.md +37 -21
- data/etc/deprecations.json +10 -0
- data/etc/plugin_filters.json +8 -0
- data/inspec.gemspec +38 -39
- data/lib/bundles/inspec-compliance/api.rb +1 -1
- data/lib/bundles/inspec-compliance/configuration.rb +1 -1
- data/lib/bundles/inspec-compliance/http.rb +1 -1
- data/lib/bundles/inspec-compliance/support.rb +1 -1
- data/lib/bundles/inspec-compliance/target.rb +1 -1
- data/lib/bundles/inspec-supermarket.rb +3 -7
- data/lib/bundles/inspec-supermarket/api.rb +10 -13
- data/lib/bundles/inspec-supermarket/cli.rb +12 -15
- data/lib/bundles/inspec-supermarket/target.rb +7 -11
- data/lib/fetchers/git.rb +14 -15
- data/lib/fetchers/local.rb +6 -10
- data/lib/fetchers/mock.rb +3 -5
- data/lib/fetchers/url.rb +42 -44
- data/lib/inspec.rb +23 -24
- data/lib/inspec/archive/tar.rb +2 -6
- data/lib/inspec/archive/zip.rb +3 -7
- data/lib/inspec/backend.rb +8 -9
- data/lib/inspec/base_cli.rb +64 -65
- data/lib/inspec/cached_fetcher.rb +2 -3
- data/lib/inspec/cli.rb +136 -97
- data/lib/inspec/config.rb +71 -61
- data/lib/inspec/control_eval_context.rb +22 -18
- data/lib/inspec/dependencies/cache.rb +2 -3
- data/lib/inspec/dependencies/dependency_set.rb +2 -3
- data/lib/inspec/dependencies/lockfile.rb +8 -9
- data/lib/inspec/dependencies/requirement.rb +7 -8
- data/lib/inspec/dependencies/resolver.rb +5 -7
- data/lib/inspec/describe.rb +2 -6
- data/lib/inspec/dist.rb +20 -0
- data/lib/inspec/dsl.rb +4 -7
- data/lib/inspec/dsl_shared.rb +1 -2
- data/lib/inspec/env_printer.rb +11 -12
- data/lib/inspec/errors.rb +0 -4
- data/lib/inspec/exceptions.rb +0 -1
- data/lib/inspec/expect.rb +5 -8
- data/lib/inspec/fetcher.rb +7 -10
- data/lib/inspec/file_provider.rb +24 -24
- data/lib/inspec/formatters.rb +3 -3
- data/lib/inspec/formatters/base.rb +8 -8
- data/lib/inspec/globals.rb +2 -2
- data/lib/inspec/impact.rb +5 -7
- data/lib/inspec/input_registry.rb +84 -33
- data/lib/inspec/library_eval_context.rb +3 -6
- data/lib/inspec/log.rb +1 -5
- data/lib/inspec/metadata.rb +17 -16
- data/lib/inspec/method_source.rb +5 -9
- data/lib/inspec/objects.rb +10 -12
- data/lib/inspec/objects/control.rb +7 -9
- data/lib/inspec/objects/describe.rb +9 -11
- data/lib/inspec/objects/each_loop.rb +1 -3
- data/lib/inspec/objects/input.rb +24 -26
- data/lib/inspec/objects/list.rb +4 -6
- data/lib/inspec/objects/or_test.rb +2 -4
- data/lib/inspec/objects/ruby_helper.rb +3 -5
- data/lib/inspec/objects/tag.rb +0 -2
- data/lib/inspec/objects/test.rb +9 -11
- data/lib/inspec/objects/value.rb +3 -5
- data/lib/inspec/plugin/v1.rb +2 -2
- data/lib/inspec/plugin/v1/plugin_types/cli.rb +1 -5
- data/lib/inspec/plugin/v1/plugin_types/fetcher.rb +2 -5
- data/lib/inspec/plugin/v1/plugin_types/resource.rb +4 -6
- data/lib/inspec/plugin/v1/plugin_types/secret.rb +1 -5
- data/lib/inspec/plugin/v1/plugin_types/source_reader.rb +1 -5
- data/lib/inspec/plugin/v1/plugins.rb +15 -19
- data/lib/inspec/plugin/v1/registry.rb +0 -4
- data/lib/inspec/plugin/v2.rb +8 -8
- data/lib/inspec/plugin/v2/activator.rb +1 -1
- data/lib/inspec/plugin/v2/config_file.rb +6 -6
- data/lib/inspec/plugin/v2/filter.rb +13 -13
- data/lib/inspec/plugin/v2/installer.rb +36 -24
- data/lib/inspec/plugin/v2/loader.rb +28 -28
- data/lib/inspec/plugin/v2/plugin_base.rb +15 -2
- data/lib/inspec/plugin/v2/plugin_types/cli.rb +5 -5
- data/lib/inspec/plugin/v2/plugin_types/input.rb +34 -0
- data/lib/inspec/plugin/v2/plugin_types/mock.rb +1 -1
- data/lib/inspec/plugin/v2/registry.rb +7 -7
- data/lib/inspec/polyfill.rb +0 -3
- data/lib/inspec/profile.rb +55 -63
- data/lib/inspec/profile_context.rb +27 -30
- data/lib/inspec/profile_vendor.rb +6 -9
- data/lib/inspec/reporters.rb +24 -24
- data/lib/inspec/reporters/automate.rb +17 -19
- data/lib/inspec/reporters/base.rb +1 -1
- data/lib/inspec/reporters/cli.rb +88 -91
- data/lib/inspec/reporters/json.rb +2 -4
- data/lib/inspec/reporters/json_automate.rb +1 -3
- data/lib/inspec/reporters/json_min.rb +1 -3
- data/lib/inspec/reporters/junit.rb +26 -28
- data/lib/inspec/reporters/yaml.rb +1 -3
- data/lib/inspec/require_loader.rb +0 -4
- data/lib/inspec/resource.rb +4 -125
- data/lib/inspec/resources.rb +121 -0
- data/lib/{resources → inspec/resources}/aide_conf.rb +24 -25
- data/lib/{resources → inspec/resources}/apache.rb +13 -14
- data/lib/{resources → inspec/resources}/apache_conf.rb +16 -17
- data/lib/{resources → inspec/resources}/apt.rb +17 -17
- data/lib/{resources → inspec/resources}/audit_policy.rb +7 -6
- data/lib/{resources → inspec/resources}/auditd.rb +62 -64
- data/lib/{resources → inspec/resources}/auditd_conf.rb +7 -8
- data/lib/{resources → inspec/resources}/bash.rb +6 -8
- data/lib/{resources → inspec/resources}/bond.rb +15 -14
- data/lib/{resources → inspec/resources}/bridge.rb +8 -8
- data/lib/{resources → inspec/resources}/chocolatey_package.rb +10 -8
- data/lib/{resources → inspec/resources}/command.rb +11 -10
- data/lib/{resources → inspec/resources}/cpan.rb +12 -12
- data/lib/{resources → inspec/resources}/cran.rb +9 -9
- data/lib/{resources → inspec/resources}/crontab.rb +47 -48
- data/lib/{resources → inspec/resources}/csv.rb +5 -5
- data/lib/{resources → inspec/resources}/dh_params.rb +5 -7
- data/lib/{resources → inspec/resources}/directory.rb +5 -7
- data/lib/{resources → inspec/resources}/docker.rb +63 -63
- data/lib/{resources → inspec/resources}/docker_container.rb +6 -6
- data/lib/{resources → inspec/resources}/docker_image.rb +9 -9
- data/lib/{resources → inspec/resources}/docker_object.rb +8 -13
- data/lib/{resources → inspec/resources}/docker_plugin.rb +6 -6
- data/lib/{resources → inspec/resources}/docker_service.rb +7 -7
- data/lib/{resources → inspec/resources}/elasticsearch.rb +40 -42
- data/lib/{resources → inspec/resources}/etc_fstab.rb +23 -24
- data/lib/{resources → inspec/resources}/etc_group.rb +26 -27
- data/lib/{resources → inspec/resources}/etc_hosts.rb +11 -13
- data/lib/{resources → inspec/resources}/etc_hosts_allow_deny.rb +25 -27
- data/lib/{resources → inspec/resources}/file.rb +80 -79
- data/lib/{resources → inspec/resources}/filesystem.rb +20 -15
- data/lib/{resources → inspec/resources}/firewalld.rb +26 -26
- data/lib/{resources → inspec/resources}/gem.rb +12 -12
- data/lib/{resources → inspec/resources}/groups.rb +28 -27
- data/lib/{resources → inspec/resources}/grub_conf.rb +46 -48
- data/lib/{resources → inspec/resources}/host.rb +31 -29
- data/lib/{resources → inspec/resources}/http.rb +24 -24
- data/lib/{resources → inspec/resources}/iis_app.rb +6 -7
- data/lib/{resources → inspec/resources}/iis_app_pool.rb +21 -19
- data/lib/{resources → inspec/resources}/iis_site.rb +17 -15
- data/lib/{resources → inspec/resources}/inetd_conf.rb +9 -10
- data/lib/{resources → inspec/resources}/ini.rb +7 -8
- data/lib/{resources → inspec/resources}/interface.rb +30 -30
- data/lib/{resources → inspec/resources}/iptables.rb +8 -8
- data/lib/{resources → inspec/resources}/json.rb +8 -10
- data/lib/{resources → inspec/resources}/kernel_module.rb +15 -15
- data/lib/{resources → inspec/resources}/kernel_parameter.rb +8 -8
- data/lib/{resources → inspec/resources}/key_rsa.rb +8 -10
- data/lib/{resources → inspec/resources}/ksh.rb +6 -8
- data/lib/{resources → inspec/resources}/limits_conf.rb +8 -9
- data/lib/{resources/login_def.rb → inspec/resources/login_defs.rb} +9 -10
- data/lib/{resources → inspec/resources}/mount.rb +6 -8
- data/lib/{resources → inspec/resources}/mssql_session.rb +16 -18
- data/lib/inspec/resources/mysql.rb +81 -0
- data/lib/{resources → inspec/resources}/mysql_conf.rb +13 -14
- data/lib/{resources → inspec/resources}/mysql_session.rb +16 -16
- data/lib/{resources → inspec/resources}/nginx.rb +16 -17
- data/lib/{resources → inspec/resources}/nginx_conf.rb +26 -27
- data/lib/{resources → inspec/resources}/npm.rb +9 -10
- data/lib/{resources → inspec/resources}/ntp_conf.rb +9 -10
- data/lib/{resources → inspec/resources}/oneget.rb +8 -8
- data/lib/{resources → inspec/resources}/oracledb_session.rb +33 -34
- data/lib/{resources → inspec/resources}/os.rb +6 -8
- data/lib/{resources → inspec/resources}/os_env.rb +11 -12
- data/lib/{resources → inspec/resources}/package.rb +66 -65
- data/lib/{resources → inspec/resources}/packages.rb +13 -13
- data/lib/{resources → inspec/resources}/parse_config.rb +8 -8
- data/lib/{resources → inspec/resources}/passwd.rb +18 -19
- data/lib/{resources → inspec/resources}/pip.rb +19 -19
- data/lib/{resources → inspec/resources}/platform.rb +9 -11
- data/lib/{resources → inspec/resources}/port.rb +134 -136
- data/lib/{resources → inspec/resources}/postgres.rb +40 -32
- data/lib/{resources → inspec/resources}/postgres_conf.rb +17 -17
- data/lib/{resources → inspec/resources}/postgres_hba_conf.rb +21 -23
- data/lib/{resources → inspec/resources}/postgres_ident_conf.rb +12 -14
- data/lib/{resources → inspec/resources}/postgres_session.rb +8 -9
- data/lib/{resources → inspec/resources}/powershell.rb +17 -13
- data/lib/{resources → inspec/resources}/processes.rb +29 -29
- data/lib/{resources/rabbitmq_conf.rb → inspec/resources/rabbitmq_config.rb} +10 -11
- data/lib/{resources → inspec/resources}/registry_key.rb +14 -14
- data/lib/inspec/resources/script.rb +1 -0
- data/lib/{resources → inspec/resources}/security_identifier.rb +11 -10
- data/lib/{resources → inspec/resources}/security_policy.rb +59 -58
- data/lib/{resources → inspec/resources}/service.rb +74 -75
- data/lib/{resources → inspec/resources}/shadow.rb +44 -45
- data/lib/{resources/ssh_conf.rb → inspec/resources/ssh_config.rb} +16 -17
- data/lib/{resources → inspec/resources}/ssl.rb +28 -29
- data/lib/inspec/resources/sys_info.rb +30 -0
- data/lib/{resources → inspec/resources}/toml.rb +5 -7
- data/lib/{resources → inspec/resources}/users.rb +65 -65
- data/lib/{resources → inspec/resources}/vbscript.rb +8 -9
- data/lib/{resources → inspec/resources}/virtualization.rb +60 -62
- data/lib/{resources → inspec/resources}/windows_feature.rb +9 -9
- data/lib/{resources → inspec/resources}/windows_hotfix.rb +5 -5
- data/lib/{resources → inspec/resources}/windows_task.rb +16 -15
- data/lib/{resources → inspec/resources}/wmi.rb +7 -8
- data/lib/{resources → inspec/resources}/x509_certificate.rb +9 -11
- data/lib/{resources/xinetd.rb → inspec/resources/xinetd_conf.rb} +27 -29
- data/lib/{resources → inspec/resources}/xml.rb +7 -7
- data/lib/{resources → inspec/resources}/yaml.rb +5 -6
- data/lib/{resources → inspec/resources}/yum.rb +10 -10
- data/lib/{resources → inspec/resources}/zfs_dataset.rb +6 -6
- data/lib/{resources → inspec/resources}/zfs_pool.rb +4 -4
- data/lib/inspec/rspec_extensions.rb +24 -8
- data/lib/inspec/rule.rb +14 -15
- data/lib/inspec/runner.rb +28 -28
- data/lib/inspec/runner_mock.rb +1 -5
- data/lib/inspec/runner_rspec.rb +18 -20
- data/lib/inspec/runtime_profile.rb +2 -5
- data/lib/inspec/schema.rb +142 -143
- data/lib/inspec/secrets.rb +3 -7
- data/lib/inspec/secrets/yaml.rb +3 -5
- data/lib/inspec/shell.rb +11 -15
- data/lib/inspec/shell_detector.rb +6 -7
- data/lib/inspec/source_reader.rb +4 -8
- data/lib/inspec/ui.rb +33 -39
- data/lib/inspec/ui_table_helper.rb +12 -0
- data/lib/{utils → inspec/utils}/command_wrapper.rb +4 -8
- data/lib/{utils → inspec/utils}/convert.rb +0 -4
- data/lib/{utils → inspec/utils}/database_helpers.rb +4 -8
- data/lib/inspec/utils/deprecation.rb +6 -0
- data/lib/{utils → inspec/utils}/deprecation/config_file.rb +19 -19
- data/lib/{utils → inspec/utils}/deprecation/deprecator.rb +12 -12
- data/lib/{utils → inspec/utils}/deprecation/errors.rb +1 -1
- data/lib/{utils → inspec/utils}/deprecation/global_method.rb +2 -2
- data/lib/{utils → inspec/utils}/enumerable_delegation.rb +0 -2
- data/lib/{utils → inspec/utils}/erlang_parser.rb +61 -65
- data/lib/{utils → inspec/utils}/file_reader.rb +1 -2
- data/lib/{utils → inspec/utils}/filter.rb +30 -33
- data/lib/{utils → inspec/utils}/filter_array.rb +0 -2
- data/lib/{utils → inspec/utils}/find_files.rb +9 -12
- data/lib/{utils → inspec/utils}/hash.rb +1 -5
- data/lib/inspec/utils/json_log.rb +15 -0
- data/lib/inspec/utils/latest_version.rb +13 -0
- data/lib/{utils → inspec/utils}/modulator.rb +0 -3
- data/lib/{utils → inspec/utils}/nginx_parser.rb +31 -35
- data/lib/{utils → inspec/utils}/object_traversal.rb +0 -3
- data/lib/{utils → inspec/utils}/parser.rb +45 -45
- data/lib/{utils → inspec/utils}/pkey_reader.rb +4 -2
- data/lib/{utils → inspec/utils}/simpleconfig.rb +8 -10
- data/lib/{utils → inspec/utils}/spdx.rb +1 -4
- data/lib/{utils → inspec/utils}/spdx.txt +0 -0
- data/lib/inspec/utils/telemetry.rb +3 -3
- data/lib/inspec/utils/telemetry/collector.rb +30 -9
- data/lib/inspec/utils/telemetry/data_series.rb +3 -1
- data/lib/inspec/utils/telemetry/global_methods.rb +1 -1
- data/lib/inspec/version.rb +1 -1
- data/lib/matchers/matchers.rb +22 -25
- data/lib/plugins/inspec-artifact/lib/inspec-artifact.rb +1 -1
- data/lib/plugins/inspec-artifact/lib/inspec-artifact/base.rb +52 -45
- data/lib/plugins/inspec-artifact/lib/inspec-artifact/cli.rb +18 -16
- data/lib/plugins/inspec-artifact/test/functional/inspec_artifact_test.rb +12 -11
- data/lib/plugins/inspec-compliance/lib/inspec-compliance.rb +1 -1
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/api.rb +73 -73
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/api/login.rb +66 -62
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/cli.rb +59 -57
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/configuration.rb +11 -11
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/http.rb +20 -22
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/support.rb +2 -4
- data/lib/plugins/inspec-compliance/lib/inspec-compliance/target.rb +30 -27
- data/lib/plugins/inspec-compliance/test/functional/inspec_compliance_test.rb +12 -14
- data/lib/plugins/inspec-compliance/test/integration/default/cli.rb +39 -41
- data/lib/plugins/inspec-compliance/test/unit/api/login_test.rb +64 -64
- data/lib/plugins/inspec-compliance/test/unit/api_test.rb +157 -156
- data/lib/plugins/inspec-compliance/test/unit/target_test.rb +85 -85
- data/lib/plugins/inspec-habitat/Berksfile +2 -2
- data/lib/plugins/inspec-habitat/lib/inspec-habitat.rb +1 -1
- data/lib/plugins/inspec-habitat/lib/inspec-habitat/cli.rb +15 -13
- data/lib/plugins/inspec-habitat/lib/inspec-habitat/profile.rb +64 -63
- data/lib/plugins/inspec-habitat/templates/habitat/hooks/run.erb +3 -3
- data/lib/plugins/inspec-habitat/templates/habitat/plan.sh.erb +11 -11
- data/lib/plugins/inspec-habitat/test/cookbooks/inspec_habitat_fixture/Berksfile +1 -1
- data/lib/plugins/inspec-habitat/test/cookbooks/inspec_habitat_fixture/metadata.rb +8 -8
- data/lib/plugins/inspec-habitat/test/cookbooks/inspec_habitat_fixture/recipes/default.rb +17 -17
- data/lib/plugins/inspec-habitat/test/functional/inspec_habitat_test.rb +9 -8
- data/lib/plugins/inspec-habitat/test/integration/default/inspec_habitat/controls/inspec_habitat.rb +14 -14
- data/lib/plugins/inspec-habitat/test/support/example_profile/controls/example.rb +4 -4
- data/lib/plugins/inspec-habitat/test/unit/profile_test.rb +42 -41
- data/lib/plugins/inspec-init/lib/inspec-init.rb +1 -1
- data/lib/plugins/inspec-init/lib/inspec-init/cli.rb +6 -8
- data/lib/plugins/inspec-init/lib/inspec-init/cli_plugin.rb +72 -74
- data/lib/plugins/inspec-init/lib/inspec-init/cli_profile.rb +9 -11
- data/lib/plugins/inspec-init/lib/inspec-init/renderer.rb +4 -4
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/Gemfile +0 -1
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/inspec-plugin-template.gemspec +0 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/lib/inspec-plugin-template.rb +0 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/lib/inspec-plugin-template/cli_command.rb +0 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/lib/inspec-plugin-template/plugin.rb +0 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/lib/inspec-plugin-template/version.rb +0 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/test/functional/inspec_plugin_template_test.rb +5 -5
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/test/helper.rb +1 -3
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/test/unit/cli_args_test.rb +2 -2
- data/lib/plugins/inspec-init/templates/plugins/inspec-plugin-template/test/unit/plugin_def_test.rb +2 -2
- data/lib/plugins/inspec-init/templates/profiles/aws/controls/example.rb +10 -11
- data/lib/plugins/inspec-init/templates/profiles/azure/controls/example.rb +4 -5
- data/lib/plugins/inspec-init/templates/profiles/gcp/controls/example.rb +10 -11
- data/lib/plugins/inspec-init/templates/profiles/os/controls/example.rb +6 -7
- data/lib/plugins/inspec-init/test/functional/inspec_init_plugin_test.rb +51 -50
- data/lib/plugins/inspec-init/test/functional/inspec_init_profile_test.rb +35 -33
- data/lib/plugins/inspec-plugin-manager-cli/lib/inspec-plugin-manager-cli.rb +1 -2
- data/lib/plugins/inspec-plugin-manager-cli/lib/inspec-plugin-manager-cli/cli_command.rb +72 -70
- data/lib/plugins/inspec-plugin-manager-cli/lib/inspec-plugin-manager-cli/plugin.rb +1 -1
- data/lib/plugins/inspec-plugin-manager-cli/test/fixtures/plugins/wrong-name/lib/wrong-name.rb +1 -1
- data/lib/plugins/inspec-plugin-manager-cli/test/functional/inspec-plugin_test.rb +281 -271
- data/lib/plugins/inspec-plugin-manager-cli/test/unit/cli_args_test.rb +41 -41
- data/lib/plugins/inspec-plugin-manager-cli/test/unit/plugin_def_test.rb +25 -6
- data/lib/plugins/shared/core_plugin_test_helper.rb +43 -38
- data/lib/resource_support/aws.rb +67 -67
- data/lib/resource_support/aws/aws_plural_resource_mixin.rb +4 -1
- data/lib/resource_support/aws/aws_resource_mixin.rb +4 -3
- data/lib/resource_support/aws/aws_singular_resource_mixin.rb +4 -1
- data/lib/resources/aws/aws_billing_report.rb +15 -8
- data/lib/resources/aws/aws_billing_reports.rb +10 -7
- data/lib/resources/aws/aws_cloudtrail_trail.rb +9 -5
- data/lib/resources/aws/aws_cloudtrail_trails.rb +9 -5
- data/lib/resources/aws/aws_cloudwatch_alarm.rb +9 -5
- data/lib/resources/aws/aws_cloudwatch_log_metric_filter.rb +12 -8
- data/lib/resources/aws/aws_config_delivery_channel.rb +13 -9
- data/lib/resources/aws/aws_config_recorder.rb +10 -6
- data/lib/resources/aws/aws_ebs_volume.rb +12 -8
- data/lib/resources/aws/aws_ebs_volumes.rb +9 -5
- data/lib/resources/aws/aws_ec2_instance.rb +14 -11
- data/lib/resources/aws/aws_ec2_instances.rb +9 -5
- data/lib/resources/aws/aws_ecs_cluster.rb +11 -7
- data/lib/resources/aws/aws_eks_cluster.rb +13 -9
- data/lib/resources/aws/aws_elb.rb +9 -5
- data/lib/resources/aws/aws_elbs.rb +9 -5
- data/lib/resources/aws/aws_flow_log.rb +17 -13
- data/lib/resources/aws/aws_iam_access_key.rb +15 -11
- data/lib/resources/aws/aws_iam_access_keys.rb +19 -15
- data/lib/resources/aws/aws_iam_group.rb +9 -5
- data/lib/resources/aws/aws_iam_groups.rb +9 -5
- data/lib/resources/aws/aws_iam_password_policy.rb +13 -10
- data/lib/resources/aws/aws_iam_policies.rb +9 -5
- data/lib/resources/aws/aws_iam_policy.rb +16 -12
- data/lib/resources/aws/aws_iam_role.rb +9 -5
- data/lib/resources/aws/aws_iam_root_user.rb +12 -8
- data/lib/resources/aws/aws_iam_user.rb +12 -12
- data/lib/resources/aws/aws_iam_users.rb +10 -10
- data/lib/resources/aws/aws_kms_key.rb +12 -8
- data/lib/resources/aws/aws_kms_keys.rb +9 -5
- data/lib/resources/aws/aws_rds_instance.rb +11 -8
- data/lib/resources/aws/aws_route_table.rb +11 -7
- data/lib/resources/aws/aws_route_tables.rb +10 -6
- data/lib/resources/aws/aws_s3_bucket.rb +14 -11
- data/lib/resources/aws/aws_s3_bucket_object.rb +12 -9
- data/lib/resources/aws/aws_s3_buckets.rb +9 -7
- data/lib/resources/aws/aws_security_group.rb +16 -12
- data/lib/resources/aws/aws_security_groups.rb +12 -8
- data/lib/resources/aws/aws_sns_subscription.rb +15 -11
- data/lib/resources/aws/aws_sns_topic.rb +10 -6
- data/lib/resources/aws/aws_sns_topics.rb +9 -5
- data/lib/resources/aws/aws_sqs_queue.rb +18 -14
- data/lib/resources/aws/aws_subnet.rb +11 -7
- data/lib/resources/aws/aws_subnets.rb +9 -5
- data/lib/resources/aws/aws_vpc.rb +10 -6
- data/lib/resources/aws/aws_vpcs.rb +9 -5
- data/lib/resources/azure/azure_backend.rb +20 -18
- data/lib/resources/azure/azure_generic_resource.rb +13 -15
- data/lib/resources/azure/azure_resource_group.rb +17 -19
- data/lib/resources/azure/azure_virtual_machine.rb +6 -8
- data/lib/resources/azure/azure_virtual_machine_data_disk.rb +6 -8
- data/lib/source_readers/flat.rb +6 -10
- data/lib/source_readers/inspec.rb +8 -12
- metadata +141 -142
- data/lib/resources/mysql.rb +0 -82
- data/lib/resources/sys_info.rb +0 -28
- data/lib/utils/deprecation.rb +0 -6
- data/lib/utils/json_log.rb +0 -18
- data/lib/utils/latest_version.rb +0 -22
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
# encoding: utf-8
|
|
2
1
|
# copyright: 2015, Vulcano Security GmbH
|
|
3
2
|
|
|
4
3
|
# Usage example:
|
|
@@ -10,14 +9,15 @@
|
|
|
10
9
|
# }
|
|
11
10
|
# describe parse_config(audit, options ) do
|
|
12
11
|
|
|
13
|
-
require
|
|
12
|
+
require "inspec/utils/file_reader"
|
|
13
|
+
require "inspec/utils/simpleconfig"
|
|
14
14
|
|
|
15
15
|
module Inspec::Resources
|
|
16
16
|
class PConfig < Inspec.resource(1)
|
|
17
|
-
name
|
|
18
|
-
supports platform:
|
|
19
|
-
supports platform:
|
|
20
|
-
desc
|
|
17
|
+
name "parse_config"
|
|
18
|
+
supports platform: "unix"
|
|
19
|
+
supports platform: "windows"
|
|
20
|
+
desc "Use the parse_config InSpec audit resource to test arbitrary configuration files."
|
|
21
21
|
example <<~EXAMPLE
|
|
22
22
|
output = command('some-command').stdout
|
|
23
23
|
describe parse_config(output, { data_config_option: value } ) do
|
|
@@ -92,8 +92,8 @@ module Inspec::Resources
|
|
|
92
92
|
end
|
|
93
93
|
|
|
94
94
|
class PConfigFile < PConfig
|
|
95
|
-
name
|
|
96
|
-
desc
|
|
95
|
+
name "parse_config_file"
|
|
96
|
+
desc "Use the parse_config_file InSpec resource to test arbitrary configuration files. It works identically to parse_config. Instead of using a command output, this resource works with files."
|
|
97
97
|
example <<~EXAMPLE
|
|
98
98
|
describe parse_config_file('/path/to/file') do
|
|
99
99
|
its('setting') { should eq 1 }
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
# encoding: utf-8
|
|
2
1
|
# copyright: 2015, Vulcano Security GmbH
|
|
3
2
|
|
|
4
3
|
# The file format consists of
|
|
@@ -10,15 +9,15 @@
|
|
|
10
9
|
# - home directory
|
|
11
10
|
# - command
|
|
12
11
|
|
|
13
|
-
require
|
|
14
|
-
require
|
|
15
|
-
require
|
|
12
|
+
require "inspec/utils/parser"
|
|
13
|
+
require "inspec/utils/filter"
|
|
14
|
+
require "inspec/utils/file_reader"
|
|
16
15
|
|
|
17
16
|
module Inspec::Resources
|
|
18
17
|
class Passwd < Inspec.resource(1)
|
|
19
|
-
name
|
|
20
|
-
supports platform:
|
|
21
|
-
desc
|
|
18
|
+
name "passwd"
|
|
19
|
+
supports platform: "unix"
|
|
20
|
+
desc "Use the passwd InSpec audit resource to test the contents of /etc/passwd, which contains the following information for users that may log into the system and/or as users that own running processes."
|
|
22
21
|
example <<~EXAMPLE
|
|
23
22
|
describe passwd do
|
|
24
23
|
its('users') { should_not include 'forbidden_user' }
|
|
@@ -43,32 +42,32 @@ module Inspec::Resources
|
|
|
43
42
|
|
|
44
43
|
def initialize(path = nil, opts = nil)
|
|
45
44
|
opts ||= {}
|
|
46
|
-
@path = path ||
|
|
45
|
+
@path = path || "/etc/passwd"
|
|
47
46
|
@content = opts[:content] || read_file_content(@path, allow_empty: true)
|
|
48
47
|
@lines = @content.to_s.split("\n")
|
|
49
48
|
@params = parse_passwd(@content)
|
|
50
49
|
end
|
|
51
50
|
|
|
52
51
|
filter = FilterTable.create
|
|
53
|
-
filter.register_column(:users, field:
|
|
54
|
-
.register_column(:passwords, field:
|
|
55
|
-
.register_column(:uids, field:
|
|
56
|
-
.register_column(:gids, field:
|
|
57
|
-
.register_column(:descs, field:
|
|
58
|
-
.register_column(:homes, field:
|
|
59
|
-
.register_column(:shells, field:
|
|
52
|
+
filter.register_column(:users, field: "user")
|
|
53
|
+
.register_column(:passwords, field: "password")
|
|
54
|
+
.register_column(:uids, field: "uid")
|
|
55
|
+
.register_column(:gids, field: "gid")
|
|
56
|
+
.register_column(:descs, field: "desc")
|
|
57
|
+
.register_column(:homes, field: "home")
|
|
58
|
+
.register_column(:shells, field: "shell")
|
|
60
59
|
|
|
61
60
|
# rebuild the passwd line from raw content
|
|
62
|
-
filter.register_custom_property(:content)
|
|
61
|
+
filter.register_custom_property(:content) do |t, _|
|
|
63
62
|
t.entries.map do |e|
|
|
64
|
-
[e.user, e.password, e.uid, e.gid, e.desc, e.home, e.shell].join(
|
|
63
|
+
[e.user, e.password, e.uid, e.gid, e.desc, e.home, e.shell].join(":")
|
|
65
64
|
end.join("\n")
|
|
66
|
-
|
|
65
|
+
end
|
|
67
66
|
|
|
68
67
|
filter.install_filter_methods_on_resource(self, :params)
|
|
69
68
|
|
|
70
69
|
def to_s
|
|
71
|
-
|
|
70
|
+
"/etc/passwd"
|
|
72
71
|
end
|
|
73
72
|
end
|
|
74
73
|
end
|
|
@@ -1,17 +1,17 @@
|
|
|
1
|
-
|
|
1
|
+
require "inspec/resources/command"
|
|
2
|
+
require "inspec/utils/simpleconfig"
|
|
2
3
|
|
|
3
4
|
# Usage:
|
|
4
5
|
# describe pip('Jinja2') do
|
|
5
6
|
# it { should be_installed }
|
|
6
7
|
# end
|
|
7
|
-
#
|
|
8
8
|
|
|
9
9
|
module Inspec::Resources
|
|
10
10
|
class PipPackage < Inspec.resource(1)
|
|
11
|
-
name
|
|
12
|
-
supports platform:
|
|
13
|
-
supports platform:
|
|
14
|
-
desc
|
|
11
|
+
name "pip"
|
|
12
|
+
supports platform: "unix"
|
|
13
|
+
supports platform: "windows"
|
|
14
|
+
desc "Use the pip InSpec audit resource to test packages that are installed using the pip installer."
|
|
15
15
|
example <<~EXAMPLE
|
|
16
16
|
describe pip('Jinja2') do
|
|
17
17
|
it { should be_installed }
|
|
@@ -27,23 +27,23 @@ module Inspec::Resources
|
|
|
27
27
|
@package_name = package_name
|
|
28
28
|
@pip_cmd = pip_path || default_pip_path
|
|
29
29
|
|
|
30
|
-
return skip_resource
|
|
30
|
+
return skip_resource "pip not found" if @pip_cmd.nil?
|
|
31
31
|
end
|
|
32
32
|
|
|
33
33
|
def info
|
|
34
34
|
return @info if defined?(@info)
|
|
35
35
|
|
|
36
36
|
@info = {}
|
|
37
|
-
@info[:type] =
|
|
37
|
+
@info[:type] = "pip"
|
|
38
38
|
return @info unless cmd_successful?
|
|
39
39
|
|
|
40
40
|
params = SimpleConfig.new(
|
|
41
41
|
cmd.stdout,
|
|
42
42
|
assignment_regex: /^\s*([^:]*?)\s*:\s*(.*?)\s*$/,
|
|
43
|
-
multiple_values: false
|
|
43
|
+
multiple_values: false
|
|
44
44
|
).params
|
|
45
|
-
@info[:name] = params[
|
|
46
|
-
@info[:version] = params[
|
|
45
|
+
@info[:name] = params["Name"]
|
|
46
|
+
@info[:version] = params["Version"]
|
|
47
47
|
@info[:installed] = true
|
|
48
48
|
@info
|
|
49
49
|
end
|
|
@@ -92,7 +92,7 @@ module Inspec::Resources
|
|
|
92
92
|
'New-Object -Type PSObject |
|
|
93
93
|
Add-Member -MemberType NoteProperty -Name Pip -Value (Invoke-Command -ScriptBlock {where.exe pip}) -PassThru |
|
|
94
94
|
Add-Member -MemberType NoteProperty -Name Python -Value (Invoke-Command -ScriptBlock {where.exe python}) -PassThru |
|
|
95
|
-
ConvertTo-Json'
|
|
95
|
+
ConvertTo-Json'
|
|
96
96
|
)
|
|
97
97
|
|
|
98
98
|
@__windows_paths = JSON.parse(cmd.stdout)
|
|
@@ -102,23 +102,23 @@ module Inspec::Resources
|
|
|
102
102
|
#
|
|
103
103
|
# @return [String] of python pip path
|
|
104
104
|
def default_pip_path
|
|
105
|
-
return
|
|
105
|
+
return "pip" unless inspec.os.windows?
|
|
106
106
|
|
|
107
107
|
# If python is not found, return with skip_resource
|
|
108
|
-
return skip_resource
|
|
108
|
+
return skip_resource "python not found" if windows_paths["Python"].nil?
|
|
109
109
|
|
|
110
110
|
# Pip is not on the default path for Windows, therefore we do some logic
|
|
111
111
|
# to find the binary on Windows
|
|
112
112
|
begin
|
|
113
113
|
# use pip if it on system path
|
|
114
|
-
pipcmd = windows_paths[
|
|
114
|
+
pipcmd = windows_paths["Pip"]
|
|
115
115
|
# calculate path on windows
|
|
116
|
-
if defined?(windows_paths[
|
|
117
|
-
return nil if windows_paths[
|
|
118
|
-
pipdir = windows_paths[
|
|
116
|
+
if defined?(windows_paths["Python"]) && pipcmd.nil?
|
|
117
|
+
return nil if windows_paths["Pip"].nil?
|
|
118
|
+
pipdir = windows_paths["Python"].split('\\')
|
|
119
119
|
# remove python.exe
|
|
120
120
|
pipdir.pop
|
|
121
|
-
pipcmd = pipdir.push(
|
|
121
|
+
pipcmd = pipdir.push("Scripts").push("pip.exe").join("/")
|
|
122
122
|
end
|
|
123
123
|
rescue JSON::ParserError => _e
|
|
124
124
|
return nil
|
|
@@ -1,9 +1,7 @@
|
|
|
1
|
-
# encoding: utf-8
|
|
2
|
-
|
|
3
1
|
module Inspec::Resources
|
|
4
2
|
class PlatformResource < Inspec.resource(1)
|
|
5
|
-
name
|
|
6
|
-
desc
|
|
3
|
+
name "platform"
|
|
4
|
+
desc "Use the platform InSpec resource to test the platform on which the system is running."
|
|
7
5
|
example <<~EXAMPLE
|
|
8
6
|
describe platform do
|
|
9
7
|
its('name') { should eq 'redhat' }
|
|
@@ -58,7 +56,7 @@ module Inspec::Resources
|
|
|
58
56
|
}
|
|
59
57
|
|
|
60
58
|
# Avoid adding Arch for APIs (not applicable)
|
|
61
|
-
unless in_family?(
|
|
59
|
+
unless in_family?("api")
|
|
62
60
|
h[:arch] = arch
|
|
63
61
|
end
|
|
64
62
|
|
|
@@ -71,11 +69,11 @@ module Inspec::Resources
|
|
|
71
69
|
status = true
|
|
72
70
|
supports.each do |s|
|
|
73
71
|
s.each do |k, v|
|
|
74
|
-
if %i
|
|
72
|
+
if %i{os_family os-family platform_family platform-family}.include?(k)
|
|
75
73
|
status = in_family?(v)
|
|
76
|
-
elsif %i
|
|
74
|
+
elsif %i{os platform}.include?(k)
|
|
77
75
|
status = platform?(v)
|
|
78
|
-
elsif %i
|
|
76
|
+
elsif %i{os_name os-name platform_name platform-name}.include?(k)
|
|
79
77
|
status = name == v
|
|
80
78
|
elsif k == :release
|
|
81
79
|
status = check_release(v)
|
|
@@ -91,15 +89,15 @@ module Inspec::Resources
|
|
|
91
89
|
end
|
|
92
90
|
|
|
93
91
|
def to_s
|
|
94
|
-
|
|
92
|
+
"Platform Detection"
|
|
95
93
|
end
|
|
96
94
|
|
|
97
95
|
private
|
|
98
96
|
|
|
99
97
|
def check_release(value)
|
|
100
98
|
# allow wild card matching
|
|
101
|
-
if value.include?(
|
|
102
|
-
cleaned = Regexp.escape(value).gsub('\*',
|
|
99
|
+
if value.include?("*")
|
|
100
|
+
cleaned = Regexp.escape(value).gsub('\*', ".*?")
|
|
103
101
|
!(release =~ /#{cleaned}/).nil?
|
|
104
102
|
else
|
|
105
103
|
release == value
|
|
@@ -1,16 +1,14 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
require
|
|
4
|
-
require 'utils/filter'
|
|
5
|
-
require 'ipaddr'
|
|
1
|
+
require "inspec/utils/parser"
|
|
2
|
+
require "inspec/utils/filter"
|
|
3
|
+
require "ipaddr"
|
|
6
4
|
|
|
7
5
|
# TODO: currently we return local ip only
|
|
8
6
|
# TODO: improve handling of same port on multiple interfaces
|
|
9
7
|
module Inspec::Resources
|
|
10
8
|
class Port < Inspec.resource(1)
|
|
11
|
-
name
|
|
12
|
-
supports platform:
|
|
13
|
-
supports platform:
|
|
9
|
+
name "port"
|
|
10
|
+
supports platform: "unix"
|
|
11
|
+
supports platform: "windows"
|
|
14
12
|
desc "Use the port InSpec audit resource to test basic port properties, such as port, process, if it's listening."
|
|
15
13
|
example <<~EXAMPLE
|
|
16
14
|
describe port(80) do
|
|
@@ -35,15 +33,15 @@ module Inspec::Resources
|
|
|
35
33
|
|
|
36
34
|
@cache = nil
|
|
37
35
|
@port_manager = port_manager_for_os
|
|
38
|
-
return skip_resource
|
|
36
|
+
return skip_resource "The `port` resource is not supported on your OS yet." if @port_manager.nil?
|
|
39
37
|
end
|
|
40
38
|
|
|
41
39
|
filter = FilterTable.create
|
|
42
|
-
filter.register_column(:ports, field:
|
|
43
|
-
.register_column(:addresses, field:
|
|
44
|
-
.register_column(:protocols, field:
|
|
45
|
-
.register_column(:processes, field:
|
|
46
|
-
.register_column(:pids, field:
|
|
40
|
+
filter.register_column(:ports, field: "port", style: :simple)
|
|
41
|
+
.register_column(:addresses, field: "address", style: :simple)
|
|
42
|
+
.register_column(:protocols, field: "protocol", style: :simple)
|
|
43
|
+
.register_column(:processes, field: "process", style: :simple)
|
|
44
|
+
.register_column(:pids, field: "pid", style: :simple)
|
|
47
45
|
.register_custom_matcher(:listening?) { |x| !x.entries.empty? }
|
|
48
46
|
filter.install_filter_methods_on_resource(self, :info)
|
|
49
47
|
|
|
@@ -83,8 +81,8 @@ module Inspec::Resources
|
|
|
83
81
|
return @cache = [] if @port_manager.nil?
|
|
84
82
|
# query ports
|
|
85
83
|
cache = @port_manager.info || []
|
|
86
|
-
cache.select! { |x| x[
|
|
87
|
-
cache.select! { |x| x[
|
|
84
|
+
cache.select! { |x| x["port"] == @port } unless @port.nil?
|
|
85
|
+
cache.select! { |x| x["address"] == @ip } unless @ip.nil?
|
|
88
86
|
@cache = cache
|
|
89
87
|
end
|
|
90
88
|
end
|
|
@@ -121,21 +119,21 @@ module Inspec::Resources
|
|
|
121
119
|
private
|
|
122
120
|
|
|
123
121
|
def powershell_info
|
|
124
|
-
cmd = inspec.command(
|
|
122
|
+
cmd = inspec.command("Get-NetTCPConnection -state Listen | Select-Object -Property State, Caption, Description, LocalAddress, LocalPort, RemoteAddress, RemotePort, DisplayName, Status | ConvertTo-Json")
|
|
125
123
|
return nil if cmd.exit_status != 0
|
|
126
124
|
|
|
127
125
|
entries = JSON.parse(cmd.stdout)
|
|
128
126
|
return nil if entries.nil?
|
|
129
127
|
|
|
130
|
-
entries.map
|
|
128
|
+
entries.map do |x|
|
|
131
129
|
{
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
130
|
+
"port" => x["LocalPort"],
|
|
131
|
+
"address" => x["LocalAddress"],
|
|
132
|
+
"protocol" => "tcp",
|
|
135
133
|
}
|
|
136
|
-
|
|
134
|
+
end
|
|
137
135
|
rescue JSON::ParserError => _e
|
|
138
|
-
|
|
136
|
+
nil
|
|
139
137
|
end
|
|
140
138
|
|
|
141
139
|
def netstat_info
|
|
@@ -146,14 +144,14 @@ module Inspec::Resources
|
|
|
146
144
|
lines = cmd.stdout.scan(/^>\s*(tcp\S*|udp\S*)\s+(\S+):(\d+)\s+(\S+)\s+(\S*)\s+(\d+)\s+(.+)/i)
|
|
147
145
|
lines.map do |line|
|
|
148
146
|
pid = line[5].to_i
|
|
149
|
-
process = line[6].delete(
|
|
150
|
-
process =
|
|
147
|
+
process = line[6].delete("[").delete("]").strip
|
|
148
|
+
process = "System" if process == "Can not obtain ownership information" && pid == 4
|
|
151
149
|
{
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
150
|
+
"port" => line[2].to_i,
|
|
151
|
+
"address" => line[1].delete("[").delete("]"),
|
|
152
|
+
"protocol" => line[0].downcase,
|
|
153
|
+
"pid" => pid,
|
|
154
|
+
"process" => process,
|
|
157
155
|
}
|
|
158
156
|
end
|
|
159
157
|
end
|
|
@@ -164,7 +162,7 @@ module Inspec::Resources
|
|
|
164
162
|
attr_reader :lsof
|
|
165
163
|
|
|
166
164
|
def initialize(inspec, lsofpath = nil)
|
|
167
|
-
@lsof = lsofpath ||
|
|
165
|
+
@lsof = lsofpath || "lsof"
|
|
168
166
|
super(inspec)
|
|
169
167
|
end
|
|
170
168
|
|
|
@@ -172,7 +170,7 @@ module Inspec::Resources
|
|
|
172
170
|
ports = []
|
|
173
171
|
|
|
174
172
|
# check that lsof is available, otherwise fail
|
|
175
|
-
raise
|
|
173
|
+
raise "Please ensure `lsof` is available on the machine." if !inspec.command(@lsof.to_s).exist?
|
|
176
174
|
|
|
177
175
|
# -F p=pid, c=command, P=protocol name, t=type, n=internet addresses
|
|
178
176
|
# see 'OUTPUT FOR OTHER PROGRAMS' in LSOF(8)
|
|
@@ -181,15 +179,15 @@ module Inspec::Resources
|
|
|
181
179
|
|
|
182
180
|
# map to desired return struct
|
|
183
181
|
lsof_parser(lsof_cmd).each do |process, port_ids|
|
|
184
|
-
pid, cmd = process.split(
|
|
182
|
+
pid, cmd = process.split(":")
|
|
185
183
|
port_ids.each do |port_str|
|
|
186
184
|
# should not break on ipv6 addresses
|
|
187
|
-
ipv, proto, port, host = port_str.split(
|
|
188
|
-
ports.push({
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
185
|
+
ipv, proto, port, host = port_str.split(":", 4)
|
|
186
|
+
ports.push({ "port" => port.to_i,
|
|
187
|
+
"address" => host,
|
|
188
|
+
"protocol" => ipv == "ipv6" ? proto + "6" : proto,
|
|
189
|
+
"process" => cmd,
|
|
190
|
+
"pid" => pid.to_i })
|
|
193
191
|
end
|
|
194
192
|
end
|
|
195
193
|
|
|
@@ -218,17 +216,17 @@ module Inspec::Resources
|
|
|
218
216
|
line.chomp!
|
|
219
217
|
key = line.slice!(0)
|
|
220
218
|
case key
|
|
221
|
-
when
|
|
219
|
+
when "p"
|
|
222
220
|
proc_id = line
|
|
223
221
|
port_id = nil
|
|
224
|
-
when
|
|
225
|
-
proc_id +=
|
|
226
|
-
when
|
|
222
|
+
when "c"
|
|
223
|
+
proc_id += ":" + line
|
|
224
|
+
when "t"
|
|
227
225
|
port_id = line.downcase
|
|
228
|
-
when
|
|
229
|
-
port_id +=
|
|
230
|
-
when
|
|
231
|
-
src, dst = line.split(
|
|
226
|
+
when "P"
|
|
227
|
+
port_id += ":" + line.downcase
|
|
228
|
+
when "n"
|
|
229
|
+
src, dst = line.split("->")
|
|
232
230
|
|
|
233
231
|
# skip active comm streams
|
|
234
232
|
next if dst
|
|
@@ -236,13 +234,13 @@ module Inspec::Resources
|
|
|
236
234
|
host, port = /^(\S+):(\d+|\*)$/.match(src)[1, 2]
|
|
237
235
|
|
|
238
236
|
# skip channels from port 0 - what does this mean?
|
|
239
|
-
next if port ==
|
|
237
|
+
next if port == "*"
|
|
240
238
|
|
|
241
239
|
# create new array stub if !exist?
|
|
242
240
|
procs[proc_id] = [] unless procs.key?(proc_id)
|
|
243
241
|
|
|
244
242
|
# change address '*' to zero
|
|
245
|
-
host = port_id =~ /^ipv6:/ ?
|
|
243
|
+
host = port_id =~ /^ipv6:/ ? "[::]" : "0.0.0.0" if host == "*"
|
|
246
244
|
# entrust URI to scrub the host and port
|
|
247
245
|
begin
|
|
248
246
|
uri = URI("addr://#{host}:#{port}")
|
|
@@ -254,7 +252,7 @@ module Inspec::Resources
|
|
|
254
252
|
|
|
255
253
|
# e.g. 'ipv4:tcp:22:127.0.0.1'
|
|
256
254
|
# strip ipv6 squares for inspec
|
|
257
|
-
port_id +=
|
|
255
|
+
port_id += ":" + port + ":" + host.gsub(/^\[|\]$/, "")
|
|
258
256
|
|
|
259
257
|
# lsof will give us another port unless it's done
|
|
260
258
|
procs[proc_id] << port_id
|
|
@@ -271,15 +269,15 @@ module Inspec::Resources
|
|
|
271
269
|
end
|
|
272
270
|
|
|
273
271
|
def ports_via_lsof
|
|
274
|
-
return nil unless inspec.command(
|
|
272
|
+
return nil unless inspec.command("lsof").exist?
|
|
275
273
|
LsofPorts.new(inspec).info
|
|
276
274
|
end
|
|
277
275
|
|
|
278
276
|
def ports_via_netstat
|
|
279
|
-
return nil unless inspec.command(
|
|
277
|
+
return nil unless inspec.command("netstat").exist?
|
|
280
278
|
|
|
281
|
-
cmd = inspec.command(
|
|
282
|
-
return nil unless cmd.exit_status.to_i
|
|
279
|
+
cmd = inspec.command("netstat -Aan | grep LISTEN")
|
|
280
|
+
return nil unless cmd.exit_status.to_i == 0
|
|
283
281
|
|
|
284
282
|
ports = []
|
|
285
283
|
# parse all lines
|
|
@@ -287,7 +285,7 @@ module Inspec::Resources
|
|
|
287
285
|
port_info = parse_netstat_line(line)
|
|
288
286
|
|
|
289
287
|
# only push protocols we are interested in
|
|
290
|
-
next unless %w{tcp tcp6 udp udp6}.include?(port_info[
|
|
288
|
+
next unless %w{tcp tcp6 udp udp6}.include?(port_info["protocol"])
|
|
291
289
|
ports.push(port_info)
|
|
292
290
|
end
|
|
293
291
|
|
|
@@ -304,7 +302,7 @@ module Inspec::Resources
|
|
|
304
302
|
protocol = parsed[2].downcase
|
|
305
303
|
|
|
306
304
|
# detect protocol if not provided
|
|
307
|
-
protocol +=
|
|
305
|
+
protocol += "6" if parsed[5].count(":") > 1 && %w{tcp udp}.include?(protocol)
|
|
308
306
|
protocol.chop! if %w{tcp4 upd4}.include?(protocol)
|
|
309
307
|
|
|
310
308
|
# extract host and port information
|
|
@@ -320,29 +318,29 @@ module Inspec::Resources
|
|
|
320
318
|
pid = pid.to_i if pid =~ /^\d+$/
|
|
321
319
|
|
|
322
320
|
{
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
321
|
+
"port" => port,
|
|
322
|
+
"address" => host,
|
|
323
|
+
"protocol" => protocol,
|
|
324
|
+
"process" => process,
|
|
325
|
+
"pid" => pid,
|
|
328
326
|
}
|
|
329
327
|
end
|
|
330
328
|
|
|
331
329
|
def parse_net_address(net_addr, protocol)
|
|
332
330
|
# local/foreign addresses on AIX use a '.' to separate the addresss
|
|
333
331
|
# from the port
|
|
334
|
-
address, _sep, port = net_addr.rpartition(
|
|
335
|
-
if protocol.eql?(
|
|
332
|
+
address, _sep, port = net_addr.rpartition(".")
|
|
333
|
+
if protocol.eql?("tcp6") || protocol.eql?("udp6")
|
|
336
334
|
ip6addr = address
|
|
337
335
|
# AIX uses the wildcard character for ipv6 addresses listening on
|
|
338
336
|
# all interfaces.
|
|
339
|
-
ip6addr =
|
|
337
|
+
ip6addr = "::" if ip6addr =~ /^\*$/
|
|
340
338
|
|
|
341
339
|
# v6 addresses need to end in a double-colon when using
|
|
342
340
|
# shorthand notation. netstat ends with a single colon.
|
|
343
341
|
# IPAddr will fail to properly parse an address unless it
|
|
344
342
|
# uses a double-colon for short-hand notation.
|
|
345
|
-
ip6addr +=
|
|
343
|
+
ip6addr += ":" if ip6addr =~ /\w:$/
|
|
346
344
|
|
|
347
345
|
begin
|
|
348
346
|
ip_parser = IPAddr.new(ip6addr)
|
|
@@ -366,12 +364,12 @@ module Inspec::Resources
|
|
|
366
364
|
host = ip_addr.host
|
|
367
365
|
else
|
|
368
366
|
ip_addr = URI("addr://[#{ip6addr}]:#{port}")
|
|
369
|
-
host = ip_addr.host[1..ip_addr.host.size-2]
|
|
367
|
+
host = ip_addr.host[1..ip_addr.host.size - 2]
|
|
370
368
|
end
|
|
371
369
|
else
|
|
372
370
|
ip4addr = address
|
|
373
371
|
# In AIX the wildcard character is used to match all interfaces
|
|
374
|
-
ip4addr =
|
|
372
|
+
ip4addr = "0.0.0.0" if ip4addr =~ /^\*$/
|
|
375
373
|
ip_addr = URI("addr://#{ip4addr}:#{port}")
|
|
376
374
|
host = ip_addr.host
|
|
377
375
|
end
|
|
@@ -389,10 +387,10 @@ module Inspec::Resources
|
|
|
389
387
|
end
|
|
390
388
|
|
|
391
389
|
def ports_via_ss
|
|
392
|
-
return nil unless inspec.command(
|
|
390
|
+
return nil unless inspec.command("ss").exist?
|
|
393
391
|
|
|
394
|
-
cmd = inspec.command(
|
|
395
|
-
return nil unless cmd.exit_status.to_i
|
|
392
|
+
cmd = inspec.command("ss -tulpen")
|
|
393
|
+
return nil unless cmd.exit_status.to_i == 0
|
|
396
394
|
|
|
397
395
|
ports = []
|
|
398
396
|
|
|
@@ -405,10 +403,10 @@ module Inspec::Resources
|
|
|
405
403
|
end
|
|
406
404
|
|
|
407
405
|
def ports_via_netstat
|
|
408
|
-
return nil unless inspec.command(
|
|
406
|
+
return nil unless inspec.command("netstat").exist?
|
|
409
407
|
|
|
410
|
-
cmd = inspec.command(
|
|
411
|
-
return nil unless cmd.exit_status.to_i
|
|
408
|
+
cmd = inspec.command("netstat -tulpen")
|
|
409
|
+
return nil unless cmd.exit_status.to_i == 0
|
|
412
410
|
|
|
413
411
|
ports = []
|
|
414
412
|
# parse all lines
|
|
@@ -416,24 +414,24 @@ module Inspec::Resources
|
|
|
416
414
|
port_info = parse_netstat_line(line)
|
|
417
415
|
|
|
418
416
|
# only push protocols we are interested in
|
|
419
|
-
next unless %w{tcp tcp6 udp udp6}.include?(port_info[
|
|
417
|
+
next unless %w{tcp tcp6 udp udp6}.include?(port_info["protocol"])
|
|
420
418
|
ports.push(port_info)
|
|
421
419
|
end
|
|
422
420
|
ports
|
|
423
421
|
end
|
|
424
422
|
|
|
425
423
|
def parse_net_address(net_addr, protocol)
|
|
426
|
-
if protocol.eql?(
|
|
424
|
+
if protocol.eql?("tcp6") || protocol.eql?("udp6")
|
|
427
425
|
# prep for URI parsing, parse ip6 port
|
|
428
426
|
ip6 = /^(\S+):(\d+)$/.match(net_addr)
|
|
429
427
|
ip6addr = ip6[1]
|
|
430
|
-
ip6addr =
|
|
428
|
+
ip6addr = "::" if ip6addr =~ /^:::$/
|
|
431
429
|
|
|
432
430
|
# v6 addresses need to end in a double-colon when using
|
|
433
431
|
# shorthand notation. netstat ends with a single colon.
|
|
434
432
|
# IPAddr will fail to properly parse an address unless it
|
|
435
433
|
# uses a double-colon for short-hand notation.
|
|
436
|
-
ip6addr +=
|
|
434
|
+
ip6addr += ":" if ip6addr =~ /\w:$/
|
|
437
435
|
|
|
438
436
|
begin
|
|
439
437
|
ip_parser = IPAddr.new(ip6addr)
|
|
@@ -458,10 +456,10 @@ module Inspec::Resources
|
|
|
458
456
|
else
|
|
459
457
|
ip_addr = URI("addr://[#{ip6addr}]:#{ip6[2]}")
|
|
460
458
|
# strip []
|
|
461
|
-
host = ip_addr.host[1..ip_addr.host.size-2]
|
|
459
|
+
host = ip_addr.host[1..ip_addr.host.size - 2]
|
|
462
460
|
end
|
|
463
461
|
else
|
|
464
|
-
ip_addr = URI(
|
|
462
|
+
ip_addr = URI("addr://" + net_addr)
|
|
465
463
|
host = ip_addr.host
|
|
466
464
|
end
|
|
467
465
|
|
|
@@ -487,24 +485,24 @@ module Inspec::Resources
|
|
|
487
485
|
protocol = parsed[:proto].downcase
|
|
488
486
|
|
|
489
487
|
# detect protocol if not provided
|
|
490
|
-
protocol +=
|
|
488
|
+
protocol += "6" if parsed[:local_addr].count(":") > 1 && %w{tcp udp}.include?(protocol)
|
|
491
489
|
|
|
492
490
|
# extract host and port information
|
|
493
491
|
host, port = parse_net_address(parsed[:local_addr], protocol)
|
|
494
492
|
return {} if host.nil?
|
|
495
493
|
|
|
496
494
|
# extract PID
|
|
497
|
-
process = parsed[:pid_prog].split(
|
|
495
|
+
process = parsed[:pid_prog].split("/")
|
|
498
496
|
pid = process[0]
|
|
499
497
|
pid = pid.to_i if pid =~ /^\d+$/
|
|
500
498
|
process = process[1]
|
|
501
499
|
|
|
502
500
|
{
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
501
|
+
"port" => port,
|
|
502
|
+
"address" => host,
|
|
503
|
+
"protocol" => protocol,
|
|
504
|
+
"process" => process,
|
|
505
|
+
"pid" => pid,
|
|
508
506
|
}
|
|
509
507
|
end
|
|
510
508
|
|
|
@@ -544,7 +542,7 @@ module Inspec::Resources
|
|
|
544
542
|
# entry.
|
|
545
543
|
process_info = parsed[:process_info]
|
|
546
544
|
protocol = parsed[:netid]
|
|
547
|
-
protocol +=
|
|
545
|
+
protocol += "6" if process_info.include?("v6only:1")
|
|
548
546
|
return nil unless ALLOWED_PROTOCOLS.include?(protocol)
|
|
549
547
|
|
|
550
548
|
# parse the Local Address:Port
|
|
@@ -567,20 +565,20 @@ module Inspec::Resources
|
|
|
567
565
|
# for those "v4-but-listed-in-v6" entries, strip off the
|
|
568
566
|
# leading IPv6 value at the beginning
|
|
569
567
|
# example: ::ffff:10.0.2.15:9200
|
|
570
|
-
host.delete!(
|
|
568
|
+
host.delete!("::ffff:") if host.start_with?("::ffff:")
|
|
571
569
|
|
|
572
570
|
# To remove brackets that might surround the IPv6 address
|
|
573
571
|
# example: [::] and [fe80::dc11:b9b6:514b:134]%eth0:123
|
|
574
|
-
host = host.tr(
|
|
572
|
+
host = host.tr("[]", "")
|
|
575
573
|
|
|
576
574
|
# if there's an interface name in the local address, which is common for
|
|
577
575
|
# IPv6 listeners, strip that out too.
|
|
578
576
|
# example: fe80::a00:27ff:fe32:ed09%enp0s3
|
|
579
|
-
host = host.split(
|
|
577
|
+
host = host.split("%").first
|
|
580
578
|
|
|
581
579
|
# if host is "*", replace with "0.0.0.0" to maintain backward compatibility with
|
|
582
580
|
# the netstat-provided data
|
|
583
|
-
host =
|
|
581
|
+
host = "0.0.0.0" if host == "*"
|
|
584
582
|
|
|
585
583
|
# in case process list parsing is not successfull
|
|
586
584
|
process = nil
|
|
@@ -596,7 +594,7 @@ module Inspec::Resources
|
|
|
596
594
|
# list entires are seperated by "," the braces can also be removed
|
|
597
595
|
# input: \"nginx\",pid=583,fd=8),(\"nginx\",pid=582,fd=8),(\"nginx\",pid=580,fd=8),(\"nginx\",pid=579,fd=8
|
|
598
596
|
# res: ["\"nginx\",pid=583,fd=8", "\"nginx\",pid=582,fd=8", "\"nginx\",pid=580,fd=8", "\"nginx\",pid=579,fd=8"]
|
|
599
|
-
process_list = process_list_match[1].split(
|
|
597
|
+
process_list = process_list_match[1].split("),(")
|
|
600
598
|
# To stay backwards compatible with netstat we need to select
|
|
601
599
|
# the last element in the resulting array.
|
|
602
600
|
# res: "\"nginx\",pid=579,fd=8"
|
|
@@ -611,11 +609,11 @@ module Inspec::Resources
|
|
|
611
609
|
end
|
|
612
610
|
|
|
613
611
|
{
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
612
|
+
"port" => port,
|
|
613
|
+
"address" => host,
|
|
614
|
+
"protocol" => protocol,
|
|
615
|
+
"process" => process,
|
|
616
|
+
"pid" => pid,
|
|
619
617
|
}
|
|
620
618
|
end
|
|
621
619
|
end
|
|
@@ -623,7 +621,7 @@ module Inspec::Resources
|
|
|
623
621
|
# extracts information from sockstat
|
|
624
622
|
class FreeBsdPorts < PortsInfo
|
|
625
623
|
def info
|
|
626
|
-
cmd = inspec.command(
|
|
624
|
+
cmd = inspec.command("sockstat -46l")
|
|
627
625
|
return nil if cmd.exit_status.to_i != 0
|
|
628
626
|
|
|
629
627
|
ports = []
|
|
@@ -632,7 +630,7 @@ module Inspec::Resources
|
|
|
632
630
|
port_info = parse_sockstat_line(line)
|
|
633
631
|
|
|
634
632
|
# push data, if not headerfile
|
|
635
|
-
next unless %w{tcp tcp6 udp udp6}.include?(port_info[
|
|
633
|
+
next unless %w{tcp tcp6 udp udp6}.include?(port_info["protocol"])
|
|
636
634
|
ports.push(port_info)
|
|
637
635
|
end
|
|
638
636
|
ports
|
|
@@ -640,22 +638,22 @@ module Inspec::Resources
|
|
|
640
638
|
|
|
641
639
|
def parse_net_address(net_addr, protocol)
|
|
642
640
|
case protocol
|
|
643
|
-
when
|
|
641
|
+
when "tcp4", "udp4", "tcp", "udp"
|
|
644
642
|
# replace * with 0.0.0.0
|
|
645
|
-
net_addr = net_addr.gsub(/^\*:/,
|
|
646
|
-
ip_addr = URI(
|
|
643
|
+
net_addr = net_addr.gsub(/^\*:/, "0.0.0.0:") if net_addr =~ /^*:(\d+)$/
|
|
644
|
+
ip_addr = URI("addr://" + net_addr)
|
|
647
645
|
host = ip_addr.host
|
|
648
646
|
port = ip_addr.port
|
|
649
|
-
when
|
|
650
|
-
return [] if net_addr ==
|
|
647
|
+
when "tcp6", "udp6"
|
|
648
|
+
return [] if net_addr == "*:*" # abort for now
|
|
651
649
|
# replace * with 0:0:0:0:0:0:0:0
|
|
652
|
-
net_addr = net_addr.gsub(/^\*:/,
|
|
650
|
+
net_addr = net_addr.gsub(/^\*:/, "0:0:0:0:0:0:0:0:") if net_addr =~ /^*:(\d+)$/
|
|
653
651
|
# extract port
|
|
654
652
|
ip6 = /^(\S+):(\d+)$/.match(net_addr)
|
|
655
653
|
ip6addr = ip6[1]
|
|
656
654
|
ip_addr = URI("addr://[#{ip6addr}]:#{ip6[2]}")
|
|
657
655
|
# replace []
|
|
658
|
-
host = ip_addr.host[1..ip_addr.host.size-2]
|
|
656
|
+
host = ip_addr.host[1..ip_addr.host.size - 2]
|
|
659
657
|
port = ip_addr.port
|
|
660
658
|
end
|
|
661
659
|
[host, port]
|
|
@@ -672,7 +670,7 @@ module Inspec::Resources
|
|
|
672
670
|
# extract ip information
|
|
673
671
|
protocol = parsed[5].downcase
|
|
674
672
|
host, port = parse_net_address(parsed[6], protocol)
|
|
675
|
-
return {} if host.nil?
|
|
673
|
+
return {} if host.nil? || port.nil?
|
|
676
674
|
|
|
677
675
|
# extract process
|
|
678
676
|
process = parsed[2]
|
|
@@ -682,15 +680,15 @@ module Inspec::Resources
|
|
|
682
680
|
pid = pid.to_i if pid =~ /^\d+$/
|
|
683
681
|
|
|
684
682
|
# map tcp4 and udp4
|
|
685
|
-
protocol =
|
|
686
|
-
protocol =
|
|
683
|
+
protocol = "tcp" if protocol.eql?("tcp4")
|
|
684
|
+
protocol = "udp" if protocol.eql?("udp4")
|
|
687
685
|
|
|
688
686
|
{
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
687
|
+
"port" => port,
|
|
688
|
+
"address" => host,
|
|
689
|
+
"protocol" => protocol,
|
|
690
|
+
"process" => process,
|
|
691
|
+
"pid" => pid,
|
|
694
692
|
}
|
|
695
693
|
end
|
|
696
694
|
end
|
|
@@ -700,36 +698,36 @@ module Inspec::Resources
|
|
|
700
698
|
|
|
701
699
|
def info
|
|
702
700
|
# extract all port info
|
|
703
|
-
cmd = inspec.command(
|
|
701
|
+
cmd = inspec.command("netstat -an -f inet -f inet6")
|
|
704
702
|
return nil if cmd.exit_status.to_i != 0
|
|
705
703
|
|
|
706
704
|
# parse the content
|
|
707
705
|
netstat_ports = parse_netstat(cmd.stdout)
|
|
708
706
|
|
|
709
707
|
# filter all ports, where we `listen`
|
|
710
|
-
listen = netstat_ports.select
|
|
711
|
-
!val[
|
|
712
|
-
|
|
708
|
+
listen = netstat_ports.select do |val|
|
|
709
|
+
!val["state"].nil? && "listen".casecmp(val["state"]) == 0
|
|
710
|
+
end
|
|
713
711
|
|
|
714
712
|
# map the data
|
|
715
|
-
ports = listen.map
|
|
716
|
-
protocol = val[
|
|
717
|
-
local_addr = val[
|
|
713
|
+
ports = listen.map do |val|
|
|
714
|
+
protocol = val["protocol"]
|
|
715
|
+
local_addr = val["local-address"]
|
|
718
716
|
|
|
719
717
|
# solaris uses 127.0.0.1.57455 instead 127.0.0.1:57455, lets convert the
|
|
720
718
|
# the last . to :
|
|
721
|
-
local_addr[local_addr.rindex(
|
|
719
|
+
local_addr[local_addr.rindex(".")] = ":"
|
|
722
720
|
host, port = parse_net_address(local_addr, protocol)
|
|
723
721
|
if host.nil?
|
|
724
722
|
nil
|
|
725
723
|
else
|
|
726
724
|
{
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
725
|
+
"port" => port,
|
|
726
|
+
"address" => host,
|
|
727
|
+
"protocol" => protocol,
|
|
730
728
|
}
|
|
731
729
|
end
|
|
732
|
-
|
|
730
|
+
end
|
|
733
731
|
ports.compact
|
|
734
732
|
end
|
|
735
733
|
end
|
|
@@ -738,20 +736,20 @@ module Inspec::Resources
|
|
|
738
736
|
class HpuxPorts < FreeBsdPorts
|
|
739
737
|
def info
|
|
740
738
|
## Can't use 'netstat -an -f inet -f inet6' as the latter -f option overrides the former one and return only inet ports
|
|
741
|
-
cmd1 = inspec.command(
|
|
739
|
+
cmd1 = inspec.command("netstat -an -f inet")
|
|
742
740
|
return nil if cmd1.exit_status.to_i != 0
|
|
743
|
-
cmd2 = inspec.command(
|
|
741
|
+
cmd2 = inspec.command("netstat -an -f inet6")
|
|
744
742
|
return nil if cmd2.exit_status.to_i != 0
|
|
745
743
|
cmd = cmd1.stdout + cmd2.stdout
|
|
746
744
|
ports = []
|
|
747
745
|
# parse all lines
|
|
748
746
|
cmd.each_line do |line|
|
|
749
747
|
port_info = parse_netstat_line(line)
|
|
750
|
-
next unless %w{tcp tcp6 udp udp6}.include?(port_info[
|
|
748
|
+
next unless %w{tcp tcp6 udp udp6}.include?(port_info["protocol"])
|
|
751
749
|
ports.push(port_info)
|
|
752
750
|
end
|
|
753
751
|
# select all ports, where we `listen`
|
|
754
|
-
ports.select { |val| val if
|
|
752
|
+
ports.select { |val| val if "listen".casecmp(val["state"]) == 0 }
|
|
755
753
|
end
|
|
756
754
|
|
|
757
755
|
def parse_netstat_line(line)
|
|
@@ -761,18 +759,18 @@ module Inspec::Resources
|
|
|
761
759
|
|
|
762
760
|
return {} if parsed.nil? || line.match(/^proto/i) || line.match(/^active/i)
|
|
763
761
|
protocol = parsed[1].downcase
|
|
764
|
-
state = parsed[6].nil
|
|
762
|
+
state = parsed[6].nil? ? " " : parsed[6].downcase
|
|
765
763
|
local_addr = parsed[4]
|
|
766
|
-
local_addr[local_addr.rindex(
|
|
764
|
+
local_addr[local_addr.rindex(".")] = ":"
|
|
767
765
|
# extract host and port information
|
|
768
766
|
host, port = parse_net_address(local_addr, protocol)
|
|
769
767
|
return {} if host.nil?
|
|
770
768
|
# map data
|
|
771
769
|
{
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
770
|
+
"port" => port,
|
|
771
|
+
"address" => host,
|
|
772
|
+
"protocol" => protocol,
|
|
773
|
+
"state" => state,
|
|
776
774
|
}
|
|
777
775
|
end
|
|
778
776
|
end
|