merge(3p/abseil_cpp): Merge upstream at 'ccdbb5941'
Change-Id: I6e85fc7b5f76bba1f1eef15e600a8acb64e97ef5
This commit is contained in:
commit
543379ce45
97 changed files with 3546 additions and 2316 deletions
179
third_party/abseil_cpp/absl/flags/BUILD.bazel
vendored
179
third_party/abseil_cpp/absl/flags/BUILD.bazel
vendored
|
|
@ -27,28 +27,18 @@ package(default_visibility = ["//visibility:public"])
|
|||
licenses(["notice"]) # Apache 2.0
|
||||
|
||||
cc_library(
|
||||
name = "flag_internal",
|
||||
srcs = [
|
||||
"internal/flag.cc",
|
||||
],
|
||||
name = "path_util",
|
||||
hdrs = [
|
||||
"internal/flag.h",
|
||||
"internal/path_util.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = ["//absl/base:__subpackages__"],
|
||||
visibility = [
|
||||
"//absl/flags:__pkg__",
|
||||
],
|
||||
deps = [
|
||||
":config",
|
||||
":handle",
|
||||
":marshalling",
|
||||
":registry",
|
||||
"//absl/base",
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/memory",
|
||||
"//absl/meta:type_traits",
|
||||
"//absl/strings",
|
||||
"//absl/synchronization",
|
||||
],
|
||||
)
|
||||
|
||||
|
|
@ -74,22 +64,6 @@ cc_library(
|
|||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "path_util",
|
||||
hdrs = [
|
||||
"internal/path_util.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = [
|
||||
"//absl/flags:__pkg__",
|
||||
],
|
||||
deps = [
|
||||
"//absl/base:config",
|
||||
"//absl/strings",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "config",
|
||||
srcs = [
|
||||
|
|
@ -131,21 +105,32 @@ cc_library(
|
|||
)
|
||||
|
||||
cc_library(
|
||||
name = "handle",
|
||||
srcs = [
|
||||
"internal/commandlineflag.cc",
|
||||
],
|
||||
name = "commandlineflag_internal",
|
||||
hdrs = [
|
||||
"internal/commandlineflag.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = [
|
||||
"//absl/flags:__pkg__",
|
||||
],
|
||||
visibility = ["//visibility:private"],
|
||||
deps = [
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/base:fast_type_id",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "commandlineflag",
|
||||
srcs = [
|
||||
"commandlineflag.cc",
|
||||
],
|
||||
hdrs = [
|
||||
"commandlineflag.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":commandlineflag_internal",
|
||||
"//absl/base:config",
|
||||
"//absl/base:fast_type_id",
|
||||
"//absl/strings",
|
||||
"//absl/types:optional",
|
||||
|
|
@ -165,36 +150,65 @@ cc_library(
|
|||
visibility = [
|
||||
"//absl/flags:__pkg__",
|
||||
],
|
||||
deps = [":handle"],
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":commandlineflag_internal",
|
||||
"//absl/base:config",
|
||||
"//absl/strings",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "registry",
|
||||
name = "reflection",
|
||||
srcs = [
|
||||
"internal/registry.cc",
|
||||
"internal/type_erased.cc",
|
||||
"reflection.cc",
|
||||
],
|
||||
hdrs = [
|
||||
"internal/registry.h",
|
||||
"internal/type_erased.h",
|
||||
"reflection.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = [
|
||||
"//absl/flags:__pkg__",
|
||||
],
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":commandlineflag_internal",
|
||||
":config",
|
||||
":handle",
|
||||
":private_handle_accessor",
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/base:raw_logging_internal",
|
||||
"//absl/strings",
|
||||
"//absl/synchronization",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "flag_internal",
|
||||
srcs = [
|
||||
"internal/flag.cc",
|
||||
],
|
||||
hdrs = [
|
||||
"internal/flag.h",
|
||||
],
|
||||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
visibility = ["//absl/base:__subpackages__"],
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":commandlineflag_internal",
|
||||
":config",
|
||||
":marshalling",
|
||||
":reflection",
|
||||
"//absl/base",
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/memory",
|
||||
"//absl/meta:type_traits",
|
||||
"//absl/strings",
|
||||
"//absl/synchronization",
|
||||
"//absl/utility",
|
||||
],
|
||||
)
|
||||
|
||||
cc_library(
|
||||
name = "flag",
|
||||
srcs = [
|
||||
|
|
@ -209,9 +223,7 @@ cc_library(
|
|||
deps = [
|
||||
":config",
|
||||
":flag_internal",
|
||||
":handle",
|
||||
":marshalling",
|
||||
":registry",
|
||||
":reflection",
|
||||
"//absl/base",
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
|
|
@ -233,14 +245,14 @@ cc_library(
|
|||
"//absl/flags:__pkg__",
|
||||
],
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":config",
|
||||
":flag",
|
||||
":flag_internal",
|
||||
":handle",
|
||||
":path_util",
|
||||
":private_handle_accessor",
|
||||
":program_name",
|
||||
":registry",
|
||||
":reflection",
|
||||
"//absl/base:config",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/strings",
|
||||
|
|
@ -276,13 +288,14 @@ cc_library(
|
|||
copts = ABSL_DEFAULT_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":commandlineflag_internal",
|
||||
":config",
|
||||
":flag",
|
||||
":flag_internal",
|
||||
":handle",
|
||||
":private_handle_accessor",
|
||||
":program_name",
|
||||
":registry",
|
||||
":reflection",
|
||||
":usage",
|
||||
":usage_internal",
|
||||
"//absl/base:config",
|
||||
|
|
@ -299,16 +312,17 @@ cc_test(
|
|||
name = "commandlineflag_test",
|
||||
size = "small",
|
||||
srcs = [
|
||||
"internal/commandlineflag_test.cc",
|
||||
"commandlineflag_test.cc",
|
||||
],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":commandlineflag",
|
||||
":commandlineflag_internal",
|
||||
":config",
|
||||
":flag",
|
||||
":handle",
|
||||
":private_handle_accessor",
|
||||
":registry",
|
||||
":reflection",
|
||||
"//absl/memory",
|
||||
"//absl/strings",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
|
|
@ -342,8 +356,8 @@ cc_test(
|
|||
":config",
|
||||
":flag",
|
||||
":flag_internal",
|
||||
":handle",
|
||||
":registry",
|
||||
":marshalling",
|
||||
":reflection",
|
||||
"//absl/base:core_headers",
|
||||
"//absl/base:malloc_internal",
|
||||
"//absl/strings",
|
||||
|
|
@ -363,6 +377,8 @@ cc_binary(
|
|||
visibility = ["//visibility:private"],
|
||||
deps = [
|
||||
":flag",
|
||||
":marshalling",
|
||||
"//absl/strings",
|
||||
"//absl/time",
|
||||
"//absl/types:optional",
|
||||
"@com_github_google_benchmark//:benchmark_main",
|
||||
|
|
@ -383,20 +399,6 @@ cc_test(
|
|||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "path_util_test",
|
||||
size = "small",
|
||||
srcs = [
|
||||
"internal/path_util_test.cc",
|
||||
],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":path_util",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "parse_test",
|
||||
size = "small",
|
||||
|
|
@ -408,7 +410,7 @@ cc_test(
|
|||
deps = [
|
||||
":flag",
|
||||
":parse",
|
||||
":registry",
|
||||
":reflection",
|
||||
"//absl/base:raw_logging_internal",
|
||||
"//absl/base:scoped_set_env",
|
||||
"//absl/strings",
|
||||
|
|
@ -417,6 +419,20 @@ cc_test(
|
|||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "path_util_test",
|
||||
size = "small",
|
||||
srcs = [
|
||||
"internal/path_util_test.cc",
|
||||
],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":path_util",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
|
||||
cc_test(
|
||||
name = "program_name_test",
|
||||
size = "small",
|
||||
|
|
@ -433,18 +449,18 @@ cc_test(
|
|||
)
|
||||
|
||||
cc_test(
|
||||
name = "type_erased_test",
|
||||
name = "reflection_test",
|
||||
size = "small",
|
||||
srcs = [
|
||||
"internal/type_erased_test.cc",
|
||||
"reflection_test.cc",
|
||||
],
|
||||
copts = ABSL_TEST_COPTS,
|
||||
linkopts = ABSL_DEFAULT_LINKOPTS,
|
||||
deps = [
|
||||
":commandlineflag_internal",
|
||||
":flag",
|
||||
":handle",
|
||||
":marshalling",
|
||||
":registry",
|
||||
":reflection",
|
||||
"//absl/memory",
|
||||
"@com_google_googletest//:gtest_main",
|
||||
],
|
||||
|
|
@ -481,10 +497,9 @@ cc_test(
|
|||
":parse",
|
||||
":path_util",
|
||||
":program_name",
|
||||
":registry",
|
||||
":reflection",
|
||||
":usage",
|
||||
":usage_internal",
|
||||
"//absl/memory",
|
||||
"//absl/strings",
|
||||
"@com_google_googletest//:gtest",
|
||||
],
|
||||
|
|
|
|||
140
third_party/abseil_cpp/absl/flags/CMakeLists.txt
vendored
140
third_party/abseil_cpp/absl/flags/CMakeLists.txt
vendored
|
|
@ -17,24 +17,16 @@
|
|||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_internal
|
||||
SRCS
|
||||
"internal/flag.cc"
|
||||
flags_path_util
|
||||
HDRS
|
||||
"internal/flag.h"
|
||||
"internal/path_util.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::base
|
||||
absl::config
|
||||
absl::flags_config
|
||||
absl::flags_handle
|
||||
absl::flags_marshalling
|
||||
absl::flags_registry
|
||||
absl::synchronization
|
||||
absl::meta
|
||||
absl::strings
|
||||
PUBLIC
|
||||
)
|
||||
|
||||
|
|
@ -59,22 +51,6 @@ absl_cc_library(
|
|||
PUBLIC
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_path_util
|
||||
HDRS
|
||||
"internal/path_util.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
absl::strings
|
||||
PUBLIC
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_config
|
||||
|
|
@ -118,9 +94,7 @@ absl_cc_library(
|
|||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_handle
|
||||
SRCS
|
||||
"internal/commandlineflag.cc"
|
||||
flags_commandlineflag_internal
|
||||
HDRS
|
||||
"internal/commandlineflag.h"
|
||||
COPTS
|
||||
|
|
@ -130,11 +104,25 @@ absl_cc_library(
|
|||
DEPS
|
||||
absl::config
|
||||
absl::fast_type_id
|
||||
absl::core_headers
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_commandlineflag
|
||||
SRCS
|
||||
"commandlineflag.cc"
|
||||
HDRS
|
||||
"commandlineflag.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
absl::fast_type_id
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::optional
|
||||
absl::raw_logging_internal
|
||||
absl::strings
|
||||
absl::synchronization
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
|
|
@ -150,34 +138,57 @@ absl_cc_library(
|
|||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::flags_handle
|
||||
absl::config
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::strings
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_registry
|
||||
flags_reflection
|
||||
SRCS
|
||||
"internal/registry.cc"
|
||||
"internal/type_erased.cc"
|
||||
"reflection.cc"
|
||||
HDRS
|
||||
"reflection.h"
|
||||
"internal/registry.h"
|
||||
"internal/type_erased.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
absl::flags_config
|
||||
absl::flags_handle
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_private_handle_accessor
|
||||
absl::core_headers
|
||||
absl::raw_logging_internal
|
||||
absl::flags_config
|
||||
absl::strings
|
||||
absl::synchronization
|
||||
)
|
||||
|
||||
# Internal-only target, do not depend on directly.
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags_internal
|
||||
SRCS
|
||||
"internal/flag.cc"
|
||||
HDRS
|
||||
"internal/flag.h"
|
||||
COPTS
|
||||
${ABSL_DEFAULT_COPTS}
|
||||
LINKOPTS
|
||||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::base
|
||||
absl::config
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::flags_config
|
||||
absl::flags_marshalling
|
||||
absl::synchronization
|
||||
absl::meta
|
||||
absl::utility
|
||||
PUBLIC
|
||||
)
|
||||
|
||||
absl_cc_library(
|
||||
NAME
|
||||
flags
|
||||
|
|
@ -192,11 +203,10 @@ absl_cc_library(
|
|||
${ABSL_DEFAULT_LINKOPTS}
|
||||
DEPS
|
||||
absl::config
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_config
|
||||
absl::flags_handle
|
||||
absl::flags_internal
|
||||
absl::flags_marshalling
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::base
|
||||
absl::core_headers
|
||||
absl::strings
|
||||
|
|
@ -218,12 +228,12 @@ absl_cc_library(
|
|||
absl::config
|
||||
absl::flags_config
|
||||
absl::flags
|
||||
absl::flags_handle
|
||||
absl::flags_private_handle_accessor
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_internal
|
||||
absl::flags_path_util
|
||||
absl::flags_private_handle_accessor
|
||||
absl::flags_program_name
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::strings
|
||||
absl::synchronization
|
||||
)
|
||||
|
|
@ -264,11 +274,12 @@ absl_cc_library(
|
|||
absl::core_headers
|
||||
absl::flags_config
|
||||
absl::flags
|
||||
absl::flags_handle
|
||||
absl::flags_private_handle_accessor
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::flags_internal
|
||||
absl::flags_private_handle_accessor
|
||||
absl::flags_program_name
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::flags_usage
|
||||
absl::strings
|
||||
absl::synchronization
|
||||
|
|
@ -281,15 +292,16 @@ absl_cc_test(
|
|||
NAME
|
||||
flags_commandlineflag_test
|
||||
SRCS
|
||||
"internal/commandlineflag_test.cc"
|
||||
"commandlineflag_test.cc"
|
||||
COPTS
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::flags
|
||||
absl::flags_commandlineflag
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::flags_config
|
||||
absl::flags_handle
|
||||
absl::flags_private_handle_accessor
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::memory
|
||||
absl::strings
|
||||
gtest_main
|
||||
|
|
@ -319,9 +331,9 @@ absl_cc_test(
|
|||
absl::core_headers
|
||||
absl::flags
|
||||
absl::flags_config
|
||||
absl::flags_handle
|
||||
absl::flags_internal
|
||||
absl::flags_registry
|
||||
absl::flags_marshalling
|
||||
absl::flags_reflection
|
||||
absl::strings
|
||||
absl::time
|
||||
gtest_main
|
||||
|
|
@ -349,7 +361,7 @@ absl_cc_test(
|
|||
DEPS
|
||||
absl::flags
|
||||
absl::flags_parse
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::raw_logging_internal
|
||||
absl::scoped_set_env
|
||||
absl::span
|
||||
|
|
@ -384,16 +396,15 @@ absl_cc_test(
|
|||
|
||||
absl_cc_test(
|
||||
NAME
|
||||
flags_type_erased_test
|
||||
flags_reflection_test
|
||||
SRCS
|
||||
"internal/type_erased_test.cc"
|
||||
"reflection_test.cc"
|
||||
COPTS
|
||||
${ABSL_TEST_COPTS}
|
||||
DEPS
|
||||
absl::flags_commandlineflag_internal
|
||||
absl::flags
|
||||
absl::flags_handle
|
||||
absl::flags_marshalling
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::memory
|
||||
absl::strings
|
||||
gtest_main
|
||||
|
|
@ -427,9 +438,8 @@ absl_cc_test(
|
|||
absl::flags_path_util
|
||||
absl::flags_program_name
|
||||
absl::flags_parse
|
||||
absl::flags_registry
|
||||
absl::flags_reflection
|
||||
absl::flags_usage
|
||||
absl::memory
|
||||
absl::strings
|
||||
gtest
|
||||
)
|
||||
|
|
|
|||
|
|
@ -13,21 +13,25 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
||||
FlagStateInterface::~FlagStateInterface() {}
|
||||
|
||||
bool CommandLineFlag::IsRetired() const { return false; }
|
||||
|
||||
bool CommandLineFlag::ParseFrom(absl::string_view value, std::string* error) {
|
||||
return ParseFrom(value, flags_internal::SET_FLAGS_VALUE,
|
||||
flags_internal::kProgrammaticChange, error);
|
||||
flags_internal::kProgrammaticChange, *error);
|
||||
}
|
||||
|
||||
namespace flags_internal {
|
||||
FlagStateInterface::~FlagStateInterface() {}
|
||||
} // namespace flags_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
196
third_party/abseil_cpp/absl/flags/commandlineflag.h
vendored
Normal file
196
third_party/abseil_cpp/absl/flags/commandlineflag.h
vendored
Normal file
|
|
@ -0,0 +1,196 @@
|
|||
//
|
||||
// Copyright 2020 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
// File: commandlineflag.h
|
||||
// -----------------------------------------------------------------------------
|
||||
//
|
||||
// This header file defines the `CommandLineFlag`, which acts as a type-erased
|
||||
// handle for accessing metadata about the Abseil Flag in question.
|
||||
//
|
||||
// Because an actual Abseil flag is of an unspecified type, you should not
|
||||
// manipulate or interact directly with objects of that type. Instead, use the
|
||||
// CommandLineFlag type as an intermediary.
|
||||
#ifndef ABSL_FLAGS_COMMANDLINEFLAG_H_
|
||||
#define ABSL_FLAGS_COMMANDLINEFLAG_H_
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/fast_type_id.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/types/optional.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
class PrivateHandleAccessor;
|
||||
} // namespace flags_internal
|
||||
|
||||
// CommandLineFlag
|
||||
//
|
||||
// This type acts as a type-erased handle for an instance of an Abseil Flag and
|
||||
// holds reflection information pertaining to that flag. Use CommandLineFlag to
|
||||
// access a flag's name, location, help string etc.
|
||||
//
|
||||
// To obtain an absl::CommandLineFlag, invoke `absl::FindCommandLineFlag()`
|
||||
// passing it the flag name string.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
// // Obtain reflection handle for a flag named "flagname".
|
||||
// const absl::CommandLineFlag* my_flag_data =
|
||||
// absl::FindCommandLineFlag("flagname");
|
||||
//
|
||||
// // Now you can get flag info from that reflection handle.
|
||||
// std::string flag_location = my_flag_data->Filename();
|
||||
// ...
|
||||
class CommandLineFlag {
|
||||
public:
|
||||
constexpr CommandLineFlag() = default;
|
||||
|
||||
// Not copyable/assignable.
|
||||
CommandLineFlag(const CommandLineFlag&) = delete;
|
||||
CommandLineFlag& operator=(const CommandLineFlag&) = delete;
|
||||
|
||||
// absl::CommandLineFlag::IsOfType()
|
||||
//
|
||||
// Return true iff flag has type T.
|
||||
template <typename T>
|
||||
inline bool IsOfType() const {
|
||||
return TypeId() == base_internal::FastTypeId<T>();
|
||||
}
|
||||
|
||||
// absl::CommandLineFlag::TryGet()
|
||||
//
|
||||
// Attempts to retrieve the flag value. Returns value on success,
|
||||
// absl::nullopt otherwise.
|
||||
template <typename T>
|
||||
absl::optional<T> TryGet() const {
|
||||
if (IsRetired() || !IsOfType<T>()) {
|
||||
return absl::nullopt;
|
||||
}
|
||||
|
||||
// Implementation notes:
|
||||
//
|
||||
// We are wrapping a union around the value of `T` to serve three purposes:
|
||||
//
|
||||
// 1. `U.value` has correct size and alignment for a value of type `T`
|
||||
// 2. The `U.value` constructor is not invoked since U's constructor does
|
||||
// not do it explicitly.
|
||||
// 3. The `U.value` destructor is invoked since U's destructor does it
|
||||
// explicitly. This makes `U` a kind of RAII wrapper around non default
|
||||
// constructible value of T, which is destructed when we leave the
|
||||
// scope. We do need to destroy U.value, which is constructed by
|
||||
// CommandLineFlag::Read even though we left it in a moved-from state
|
||||
// after std::move.
|
||||
//
|
||||
// All of this serves to avoid requiring `T` being default constructible.
|
||||
union U {
|
||||
T value;
|
||||
U() {}
|
||||
~U() { value.~T(); }
|
||||
};
|
||||
U u;
|
||||
|
||||
Read(&u.value);
|
||||
return std::move(u.value);
|
||||
}
|
||||
|
||||
// absl::CommandLineFlag::Name()
|
||||
//
|
||||
// Returns name of this flag.
|
||||
virtual absl::string_view Name() const = 0;
|
||||
|
||||
// absl::CommandLineFlag::Filename()
|
||||
//
|
||||
// Returns name of the file where this flag is defined.
|
||||
virtual std::string Filename() const = 0;
|
||||
|
||||
// absl::CommandLineFlag::Help()
|
||||
//
|
||||
// Returns help message associated with this flag.
|
||||
virtual std::string Help() const = 0;
|
||||
|
||||
// absl::CommandLineFlag::IsRetired()
|
||||
//
|
||||
// Returns true iff this object corresponds to retired flag.
|
||||
virtual bool IsRetired() const;
|
||||
|
||||
// absl::CommandLineFlag::DefaultValue()
|
||||
//
|
||||
// Returns the default value for this flag.
|
||||
virtual std::string DefaultValue() const = 0;
|
||||
|
||||
// absl::CommandLineFlag::CurrentValue()
|
||||
//
|
||||
// Returns the current value for this flag.
|
||||
virtual std::string CurrentValue() const = 0;
|
||||
|
||||
// absl::CommandLineFlag::ParseFrom()
|
||||
//
|
||||
// Sets the value of the flag based on specified string `value`. If the flag
|
||||
// was successfully set to new value, it returns true. Otherwise, sets `error`
|
||||
// to indicate the error, leaves the flag unchanged, and returns false.
|
||||
bool ParseFrom(absl::string_view value, std::string* error);
|
||||
|
||||
protected:
|
||||
~CommandLineFlag() = default;
|
||||
|
||||
private:
|
||||
friend class flags_internal::PrivateHandleAccessor;
|
||||
|
||||
// Sets the value of the flag based on specified string `value`. If the flag
|
||||
// was successfully set to new value, it returns true. Otherwise, sets `error`
|
||||
// to indicate the error, leaves the flag unchanged, and returns false. There
|
||||
// are three ways to set the flag's value:
|
||||
// * Update the current flag value
|
||||
// * Update the flag's default value
|
||||
// * Update the current flag value if it was never set before
|
||||
// The mode is selected based on `set_mode` parameter.
|
||||
virtual bool ParseFrom(absl::string_view value,
|
||||
flags_internal::FlagSettingMode set_mode,
|
||||
flags_internal::ValueSource source,
|
||||
std::string& error) = 0;
|
||||
|
||||
// Returns id of the flag's value type.
|
||||
virtual flags_internal::FlagFastTypeId TypeId() const = 0;
|
||||
|
||||
// Interface to save flag to some persistent state. Returns current flag state
|
||||
// or nullptr if flag does not support saving and restoring a state.
|
||||
virtual std::unique_ptr<flags_internal::FlagStateInterface> SaveState() = 0;
|
||||
|
||||
// Copy-construct a new value of the flag's type in a memory referenced by
|
||||
// the dst based on the current flag's value.
|
||||
virtual void Read(void* dst) const = 0;
|
||||
|
||||
// To be deleted. Used to return true if flag's current value originated from
|
||||
// command line.
|
||||
virtual bool IsSpecifiedOnCommandLine() const = 0;
|
||||
|
||||
// Validates supplied value usign validator or parseflag routine
|
||||
virtual bool ValidateInputValue(absl::string_view value) const = 0;
|
||||
|
||||
// Checks that flags default value can be converted to string and back to the
|
||||
// flag's value type.
|
||||
virtual void CheckDefaultValueParsingRoundtrip() const = 0;
|
||||
};
|
||||
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#endif // ABSL_FLAGS_COMMANDLINEFLAG_H_
|
||||
|
|
@ -13,15 +13,16 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/memory/memory.h"
|
||||
#include "absl/strings/match.h"
|
||||
|
|
@ -33,6 +34,10 @@ ABSL_FLAG(std::string, string_flag, "dflt",
|
|||
absl::StrCat("string_flag", " help"));
|
||||
ABSL_RETIRED_FLAG(bool, bool_retired_flag, false, "bool_retired_flag help");
|
||||
|
||||
// These are only used to test default values.
|
||||
ABSL_FLAG(int, int_flag2, 201, "");
|
||||
ABSL_FLAG(std::string, string_flag2, "dflt", "");
|
||||
|
||||
namespace {
|
||||
|
||||
namespace flags = absl::flags_internal;
|
||||
|
|
@ -46,7 +51,7 @@ class CommandLineFlagTest : public testing::Test {
|
|||
absl::SetFlagsUsageConfig(default_config);
|
||||
}
|
||||
|
||||
void SetUp() override { flag_saver_ = absl::make_unique<flags::FlagSaver>(); }
|
||||
void SetUp() override { flag_saver_ = absl::make_unique<absl::FlagSaver>(); }
|
||||
void TearDown() override { flag_saver_.reset(); }
|
||||
|
||||
private:
|
||||
|
|
@ -59,56 +64,49 @@ class CommandLineFlagTest : public testing::Test {
|
|||
return std::string(fname);
|
||||
}
|
||||
|
||||
std::unique_ptr<flags::FlagSaver> flag_saver_;
|
||||
std::unique_ptr<absl::FlagSaver> flag_saver_;
|
||||
};
|
||||
|
||||
TEST_F(CommandLineFlagTest, TestAttributesAccessMethods) {
|
||||
auto* flag_01 = flags::FindCommandLineFlag("int_flag");
|
||||
auto* flag_01 = absl::FindCommandLineFlag("int_flag");
|
||||
|
||||
ASSERT_TRUE(flag_01);
|
||||
EXPECT_EQ(flag_01->Name(), "int_flag");
|
||||
EXPECT_EQ(flag_01->Help(), "int_flag help");
|
||||
EXPECT_TRUE(!flag_01->IsRetired());
|
||||
EXPECT_TRUE(flag_01->IsOfType<int>());
|
||||
EXPECT_TRUE(
|
||||
absl::EndsWith(flag_01->Filename(),
|
||||
"absl/flags/internal/commandlineflag_test.cc"))
|
||||
EXPECT_TRUE(!flag_01->IsOfType<bool>());
|
||||
EXPECT_TRUE(!flag_01->IsOfType<std::string>());
|
||||
EXPECT_TRUE(absl::EndsWith(flag_01->Filename(),
|
||||
"absl/flags/commandlineflag_test.cc"))
|
||||
<< flag_01->Filename();
|
||||
|
||||
auto* flag_02 = flags::FindCommandLineFlag("string_flag");
|
||||
auto* flag_02 = absl::FindCommandLineFlag("string_flag");
|
||||
|
||||
ASSERT_TRUE(flag_02);
|
||||
EXPECT_EQ(flag_02->Name(), "string_flag");
|
||||
EXPECT_EQ(flag_02->Help(), "string_flag help");
|
||||
EXPECT_TRUE(!flag_02->IsRetired());
|
||||
EXPECT_TRUE(flag_02->IsOfType<std::string>());
|
||||
EXPECT_TRUE(
|
||||
absl::EndsWith(flag_02->Filename(),
|
||||
"absl/flags/internal/commandlineflag_test.cc"))
|
||||
EXPECT_TRUE(!flag_02->IsOfType<bool>());
|
||||
EXPECT_TRUE(!flag_02->IsOfType<int>());
|
||||
EXPECT_TRUE(absl::EndsWith(flag_02->Filename(),
|
||||
"absl/flags/commandlineflag_test.cc"))
|
||||
<< flag_02->Filename();
|
||||
|
||||
auto* flag_03 = flags::FindRetiredFlag("bool_retired_flag");
|
||||
|
||||
ASSERT_TRUE(flag_03);
|
||||
EXPECT_EQ(flag_03->Name(), "bool_retired_flag");
|
||||
EXPECT_EQ(flag_03->Help(), "");
|
||||
EXPECT_TRUE(flag_03->IsRetired());
|
||||
EXPECT_TRUE(flag_03->IsOfType<bool>());
|
||||
EXPECT_EQ(flag_03->Filename(), "RETIRED");
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(CommandLineFlagTest, TestValueAccessMethods) {
|
||||
absl::SetFlag(&FLAGS_int_flag, 301);
|
||||
auto* flag_01 = flags::FindCommandLineFlag("int_flag");
|
||||
absl::SetFlag(&FLAGS_int_flag2, 301);
|
||||
auto* flag_01 = absl::FindCommandLineFlag("int_flag2");
|
||||
|
||||
ASSERT_TRUE(flag_01);
|
||||
EXPECT_EQ(flag_01->CurrentValue(), "301");
|
||||
EXPECT_EQ(flag_01->DefaultValue(), "201");
|
||||
|
||||
absl::SetFlag(&FLAGS_string_flag, "new_str_value");
|
||||
auto* flag_02 = flags::FindCommandLineFlag("string_flag");
|
||||
absl::SetFlag(&FLAGS_string_flag2, "new_str_value");
|
||||
auto* flag_02 = absl::FindCommandLineFlag("string_flag2");
|
||||
|
||||
ASSERT_TRUE(flag_02);
|
||||
EXPECT_EQ(flag_02->CurrentValue(), "new_str_value");
|
||||
|
|
@ -120,62 +118,62 @@ TEST_F(CommandLineFlagTest, TestValueAccessMethods) {
|
|||
TEST_F(CommandLineFlagTest, TestParseFromCurrentValue) {
|
||||
std::string err;
|
||||
|
||||
auto* flag_01 = flags::FindCommandLineFlag("int_flag");
|
||||
auto* flag_01 = absl::FindCommandLineFlag("int_flag");
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "11", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, &err));
|
||||
*flag_01, "11", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 11);
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "-123", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "-123", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), -123);
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(!flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "xyz", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "xyz", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), -123);
|
||||
EXPECT_EQ(err, "Illegal value 'xyz' specified for flag 'int_flag'");
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(!flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "A1", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, &err));
|
||||
*flag_01, "A1", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), -123);
|
||||
EXPECT_EQ(err, "Illegal value 'A1' specified for flag 'int_flag'");
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "0x10", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "0x10", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 16);
|
||||
EXPECT_FALSE(
|
||||
flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "011", flags::SET_FLAGS_VALUE, flags::kCommandLine, &err));
|
||||
*flag_01, "011", flags::SET_FLAGS_VALUE, flags::kCommandLine, err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 11);
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::IsSpecifiedOnCommandLine(*flag_01));
|
||||
|
||||
EXPECT_TRUE(!flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, &err));
|
||||
*flag_01, "", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, err));
|
||||
EXPECT_EQ(err, "Illegal value '' specified for flag 'int_flag'");
|
||||
|
||||
auto* flag_02 = flags::FindCommandLineFlag("string_flag");
|
||||
auto* flag_02 = absl::FindCommandLineFlag("string_flag");
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_02, "xyz", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_02, "xyz", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "xyz");
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_02, "", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, &err));
|
||||
*flag_02, "", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange, err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "");
|
||||
}
|
||||
|
||||
|
|
@ -184,18 +182,18 @@ TEST_F(CommandLineFlagTest, TestParseFromCurrentValue) {
|
|||
TEST_F(CommandLineFlagTest, TestParseFromDefaultValue) {
|
||||
std::string err;
|
||||
|
||||
auto* flag_01 = flags::FindCommandLineFlag("int_flag");
|
||||
auto* flag_01 = absl::FindCommandLineFlag("int_flag");
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "111", flags::SET_FLAGS_DEFAULT, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "111", flags::SET_FLAGS_DEFAULT, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(flag_01->DefaultValue(), "111");
|
||||
|
||||
auto* flag_02 = flags::FindCommandLineFlag("string_flag");
|
||||
auto* flag_02 = absl::FindCommandLineFlag("string_flag");
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_02, "abc", flags::SET_FLAGS_DEFAULT, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_02, "abc", flags::SET_FLAGS_DEFAULT, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(flag_02->DefaultValue(), "abc");
|
||||
}
|
||||
|
||||
|
|
@ -204,28 +202,28 @@ TEST_F(CommandLineFlagTest, TestParseFromDefaultValue) {
|
|||
TEST_F(CommandLineFlagTest, TestParseFromIfDefault) {
|
||||
std::string err;
|
||||
|
||||
auto* flag_01 = flags::FindCommandLineFlag("int_flag");
|
||||
auto* flag_01 = absl::FindCommandLineFlag("int_flag");
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "22", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
&err))
|
||||
*flag_01, "22", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
err))
|
||||
<< err;
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 22);
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "33", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "33", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 22);
|
||||
// EXPECT_EQ(err, "ERROR: int_flag is already set to 22");
|
||||
|
||||
// Reset back to default value
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "201", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "201", flags::SET_FLAGS_VALUE, flags::kProgrammaticChange,
|
||||
err));
|
||||
|
||||
EXPECT_TRUE(flags::PrivateHandleAccessor::ParseFrom(
|
||||
flag_01, "33", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
&err));
|
||||
*flag_01, "33", flags::SET_FLAG_IF_DEFAULT, flags::kProgrammaticChange,
|
||||
err));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 201);
|
||||
// EXPECT_EQ(err, "ERROR: int_flag is already set to 201");
|
||||
}
|
||||
1
third_party/abseil_cpp/absl/flags/declare.h
vendored
1
third_party/abseil_cpp/absl/flags/declare.h
vendored
|
|
@ -26,7 +26,6 @@
|
|||
#define ABSL_FLAGS_DECLARE_H_
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
|
|
|||
2
third_party/abseil_cpp/absl/flags/flag.cc
vendored
2
third_party/abseil_cpp/absl/flags/flag.cc
vendored
|
|
@ -16,8 +16,6 @@
|
|||
#include "absl/flags/flag.h"
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/flag.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
|
|
|||
142
third_party/abseil_cpp/absl/flags/flag.h
vendored
142
third_party/abseil_cpp/absl/flags/flag.h
vendored
|
|
@ -33,14 +33,11 @@
|
|||
#include <type_traits>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/casts.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/optimization.h"
|
||||
#include "absl/flags/config.h"
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/flag.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
|
|
@ -111,12 +108,12 @@ class Flag {
|
|||
impl_(nullptr) {}
|
||||
#endif
|
||||
|
||||
flags_internal::Flag<T>* GetImpl() const {
|
||||
flags_internal::Flag<T>& GetImpl() const {
|
||||
if (!inited_.load(std::memory_order_acquire)) {
|
||||
absl::MutexLock l(flags_internal::GetGlobalConstructionGuard());
|
||||
|
||||
if (inited_.load(std::memory_order_acquire)) {
|
||||
return impl_;
|
||||
return *impl_;
|
||||
}
|
||||
|
||||
impl_ = new flags_internal::Flag<T>(
|
||||
|
|
@ -128,28 +125,30 @@ class Flag {
|
|||
inited_.store(true, std::memory_order_release);
|
||||
}
|
||||
|
||||
return impl_;
|
||||
return *impl_;
|
||||
}
|
||||
|
||||
// Public methods of `absl::Flag<T>` are NOT part of the Abseil Flags API.
|
||||
// See https://abseil.io/docs/cpp/guides/flags
|
||||
bool IsRetired() const { return GetImpl()->IsRetired(); }
|
||||
absl::string_view Name() const { return GetImpl()->Name(); }
|
||||
std::string Help() const { return GetImpl()->Help(); }
|
||||
bool IsModified() const { return GetImpl()->IsModified(); }
|
||||
bool IsRetired() const { return GetImpl().IsRetired(); }
|
||||
absl::string_view Name() const { return GetImpl().Name(); }
|
||||
std::string Help() const { return GetImpl().Help(); }
|
||||
bool IsModified() const { return GetImpl().IsModified(); }
|
||||
bool IsSpecifiedOnCommandLine() const {
|
||||
return GetImpl()->IsSpecifiedOnCommandLine();
|
||||
return GetImpl().IsSpecifiedOnCommandLine();
|
||||
}
|
||||
std::string Filename() const { return GetImpl()->Filename(); }
|
||||
std::string DefaultValue() const { return GetImpl()->DefaultValue(); }
|
||||
std::string CurrentValue() const { return GetImpl()->CurrentValue(); }
|
||||
std::string Filename() const { return GetImpl().Filename(); }
|
||||
std::string DefaultValue() const { return GetImpl().DefaultValue(); }
|
||||
std::string CurrentValue() const { return GetImpl().CurrentValue(); }
|
||||
template <typename U>
|
||||
inline bool IsOfType() const {
|
||||
return GetImpl()->template IsOfType<U>();
|
||||
return GetImpl().template IsOfType<U>();
|
||||
}
|
||||
T Get() const { return GetImpl()->Get(); }
|
||||
void Set(const T& v) { GetImpl()->Set(v); }
|
||||
void InvokeCallback() { GetImpl()->InvokeCallback(); }
|
||||
T Get() const { return GetImpl().Get(); }
|
||||
void Set(const T& v) { GetImpl().Set(v); }
|
||||
void InvokeCallback() { GetImpl().InvokeCallback(); }
|
||||
|
||||
const CommandLineFlag& Reflect() const { return GetImpl().Reflect(); }
|
||||
|
||||
// The data members are logically private, but they need to be public for
|
||||
// this to be an aggregate type.
|
||||
|
|
@ -205,6 +204,21 @@ void SetFlag(absl::Flag<T>* flag, const V& v) {
|
|||
flag->Set(value);
|
||||
}
|
||||
|
||||
// GetFlagReflectionHandle()
|
||||
//
|
||||
// Returns the reflection handle corresponding to specified Abseil Flag
|
||||
// instance. Use this handle to access flag's reflection information, like name,
|
||||
// location, default value etc.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
// std::string = absl::GetFlagReflectionHandle(FLAGS_count).DefaultValue();
|
||||
|
||||
template <typename T>
|
||||
const CommandLineFlag& GetFlagReflectionHandle(const absl::Flag<T>& f) {
|
||||
return f.Reflect();
|
||||
}
|
||||
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
|
|
@ -265,27 +279,29 @@ ABSL_NAMESPACE_END
|
|||
// -----------------------------------------------------------------------------
|
||||
|
||||
// ABSL_FLAG_IMPL macro definition conditional on ABSL_FLAGS_STRIP_NAMES
|
||||
#if !defined(_MSC_VER) || defined(__clang__)
|
||||
#define ABSL_FLAG_IMPL_FLAG_PTR(flag) flag
|
||||
#define ABSL_FLAG_IMPL_HELP_ARG(name) \
|
||||
absl::flags_internal::HelpArg<AbslFlagHelpGenFor##name>( \
|
||||
FLAGS_help_storage_##name)
|
||||
#define ABSL_FLAG_IMPL_DEFAULT_ARG(Type, name) \
|
||||
absl::flags_internal::DefaultArg<Type, AbslFlagDefaultGenFor##name>(0)
|
||||
#else
|
||||
#define ABSL_FLAG_IMPL_FLAG_PTR(flag) flag.GetImpl()
|
||||
#define ABSL_FLAG_IMPL_HELP_ARG(name) &AbslFlagHelpGenFor##name::NonConst
|
||||
#define ABSL_FLAG_IMPL_DEFAULT_ARG(Type, name) &AbslFlagDefaultGenFor##name::Gen
|
||||
#endif
|
||||
|
||||
#if ABSL_FLAGS_STRIP_NAMES
|
||||
#define ABSL_FLAG_IMPL_FLAGNAME(txt) ""
|
||||
#define ABSL_FLAG_IMPL_FILENAME() ""
|
||||
#if !defined(_MSC_VER) || defined(__clang__)
|
||||
#define ABSL_FLAG_IMPL_REGISTRAR(T, flag) \
|
||||
absl::flags_internal::FlagRegistrar<T, false>(&flag)
|
||||
#else
|
||||
#define ABSL_FLAG_IMPL_REGISTRAR(T, flag) \
|
||||
absl::flags_internal::FlagRegistrar<T, false>(flag.GetImpl())
|
||||
#endif
|
||||
absl::flags_internal::FlagRegistrar<T, false>(ABSL_FLAG_IMPL_FLAG_PTR(flag))
|
||||
#else
|
||||
#define ABSL_FLAG_IMPL_FLAGNAME(txt) txt
|
||||
#define ABSL_FLAG_IMPL_FILENAME() __FILE__
|
||||
#if !defined(_MSC_VER) || defined(__clang__)
|
||||
#define ABSL_FLAG_IMPL_REGISTRAR(T, flag) \
|
||||
absl::flags_internal::FlagRegistrar<T, true>(&flag)
|
||||
#else
|
||||
#define ABSL_FLAG_IMPL_REGISTRAR(T, flag) \
|
||||
absl::flags_internal::FlagRegistrar<T, true>(flag.GetImpl())
|
||||
#endif
|
||||
absl::flags_internal::FlagRegistrar<T, true>(ABSL_FLAG_IMPL_FLAG_PTR(flag))
|
||||
#endif
|
||||
|
||||
// ABSL_FLAG_IMPL macro definition conditional on ABSL_FLAGS_STRIP_HELP
|
||||
|
|
@ -301,15 +317,24 @@ ABSL_NAMESPACE_END
|
|||
// between the two via the call to HelpArg in absl::Flag instantiation below.
|
||||
// If help message expression is constexpr evaluable compiler will optimize
|
||||
// away this whole struct.
|
||||
#define ABSL_FLAG_IMPL_DECLARE_HELP_WRAPPER(name, txt) \
|
||||
struct AbslFlagHelpGenFor##name { \
|
||||
template <typename T = void> \
|
||||
static constexpr const char* Const() { \
|
||||
return absl::flags_internal::HelpConstexprWrap( \
|
||||
ABSL_FLAG_IMPL_FLAGHELP(txt)); \
|
||||
} \
|
||||
static std::string NonConst() { return ABSL_FLAG_IMPL_FLAGHELP(txt); } \
|
||||
}
|
||||
// TODO(rogeeff): place these generated structs into local namespace and apply
|
||||
// ABSL_INTERNAL_UNIQUE_SHORT_NAME.
|
||||
// TODO(rogeeff): Apply __attribute__((nodebug)) to FLAGS_help_storage_##name
|
||||
#define ABSL_FLAG_IMPL_DECLARE_HELP_WRAPPER(name, txt) \
|
||||
struct AbslFlagHelpGenFor##name { \
|
||||
/* The expression is run in the caller as part of the */ \
|
||||
/* default value argument. That keeps temporaries alive */ \
|
||||
/* long enough for NonConst to work correctly. */ \
|
||||
static constexpr absl::string_view Value( \
|
||||
absl::string_view v = ABSL_FLAG_IMPL_FLAGHELP(txt)) { \
|
||||
return v; \
|
||||
} \
|
||||
static std::string NonConst() { return std::string(Value()); } \
|
||||
}; \
|
||||
constexpr auto FLAGS_help_storage_##name ABSL_INTERNAL_UNIQUE_SMALL_NAME() \
|
||||
ABSL_ATTRIBUTE_SECTION_VARIABLE(flags_help_cold) = \
|
||||
absl::flags_internal::HelpStringAsArray<AbslFlagHelpGenFor##name>( \
|
||||
0);
|
||||
|
||||
#define ABSL_FLAG_IMPL_DECLARE_DEF_VAL_WRAPPER(name, Type, default_value) \
|
||||
struct AbslFlagDefaultGenFor##name { \
|
||||
|
|
@ -317,40 +342,23 @@ ABSL_NAMESPACE_END
|
|||
static void Gen(void* p) { \
|
||||
new (p) Type(AbslFlagDefaultGenFor##name{}.value); \
|
||||
} \
|
||||
}
|
||||
};
|
||||
|
||||
// ABSL_FLAG_IMPL
|
||||
//
|
||||
// Note: Name of registrar object is not arbitrary. It is used to "grab"
|
||||
// global name for FLAGS_no<flag_name> symbol, thus preventing the possibility
|
||||
// of defining two flags with names foo and nofoo.
|
||||
#if !defined(_MSC_VER) || defined(__clang__)
|
||||
|
||||
#define ABSL_FLAG_IMPL(Type, name, default_value, help) \
|
||||
namespace absl /* block flags in namespaces */ {} \
|
||||
ABSL_FLAG_IMPL_DECLARE_DEF_VAL_WRAPPER(name, Type, default_value); \
|
||||
ABSL_FLAG_IMPL_DECLARE_HELP_WRAPPER(name, help); \
|
||||
ABSL_CONST_INIT absl::Flag<Type> FLAGS_##name{ \
|
||||
ABSL_FLAG_IMPL_FLAGNAME(#name), ABSL_FLAG_IMPL_FILENAME(), \
|
||||
absl::flags_internal::HelpArg<AbslFlagHelpGenFor##name>(0), \
|
||||
absl::flags_internal::DefaultArg<Type, AbslFlagDefaultGenFor##name>(0)}; \
|
||||
extern absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name; \
|
||||
absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name = \
|
||||
#define ABSL_FLAG_IMPL(Type, name, default_value, help) \
|
||||
namespace absl /* block flags in namespaces */ {} \
|
||||
ABSL_FLAG_IMPL_DECLARE_DEF_VAL_WRAPPER(name, Type, default_value) \
|
||||
ABSL_FLAG_IMPL_DECLARE_HELP_WRAPPER(name, help) \
|
||||
ABSL_CONST_INIT absl::Flag<Type> FLAGS_##name{ \
|
||||
ABSL_FLAG_IMPL_FLAGNAME(#name), ABSL_FLAG_IMPL_FILENAME(), \
|
||||
ABSL_FLAG_IMPL_HELP_ARG(name), ABSL_FLAG_IMPL_DEFAULT_ARG(Type, name)}; \
|
||||
extern absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name; \
|
||||
absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name = \
|
||||
ABSL_FLAG_IMPL_REGISTRAR(Type, FLAGS_##name)
|
||||
#else
|
||||
// MSVC version uses aggregate initialization. We also do not try to
|
||||
// optimize away help wrapper.
|
||||
#define ABSL_FLAG_IMPL(Type, name, default_value, help) \
|
||||
namespace absl /* block flags in namespaces */ {} \
|
||||
ABSL_FLAG_IMPL_DECLARE_DEF_VAL_WRAPPER(name, Type, default_value); \
|
||||
ABSL_FLAG_IMPL_DECLARE_HELP_WRAPPER(name, help); \
|
||||
ABSL_CONST_INIT absl::Flag<Type> FLAGS_##name{ \
|
||||
ABSL_FLAG_IMPL_FLAGNAME(#name), ABSL_FLAG_IMPL_FILENAME(), \
|
||||
&AbslFlagHelpGenFor##name::NonConst, &AbslFlagDefaultGenFor##name::Gen}; \
|
||||
extern absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name; \
|
||||
absl::flags_internal::FlagRegistrarEmpty FLAGS_no##name = \
|
||||
ABSL_FLAG_IMPL_REGISTRAR(Type, FLAGS_##name)
|
||||
#endif
|
||||
|
||||
// ABSL_RETIRED_FLAG
|
||||
//
|
||||
|
|
|
|||
|
|
@ -13,7 +13,14 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/time/time.h"
|
||||
#include "absl/types/optional.h"
|
||||
#include "benchmark/benchmark.h"
|
||||
|
|
|
|||
378
third_party/abseil_cpp/absl/flags/flag_test.cc
vendored
378
third_party/abseil_cpp/absl/flags/flag_test.cc
vendored
|
|
@ -15,9 +15,11 @@
|
|||
|
||||
#include "absl/flags/flag.h"
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include <cmath>
|
||||
#include <new>
|
||||
#include <string>
|
||||
#include <thread> // NOLINT
|
||||
#include <vector>
|
||||
|
|
@ -26,9 +28,9 @@
|
|||
#include "absl/base/attributes.h"
|
||||
#include "absl/flags/config.h"
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/flag.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/strings/match.h"
|
||||
#include "absl/strings/numbers.h"
|
||||
|
|
@ -45,6 +47,9 @@ namespace {
|
|||
namespace flags = absl::flags_internal;
|
||||
|
||||
std::string TestHelpMsg() { return "dynamic help"; }
|
||||
#if defined(_MSC_VER) && !defined(__clang__)
|
||||
std::string TestLiteralHelpMsg() { return "literal help"; }
|
||||
#endif
|
||||
template <typename T>
|
||||
void TestMakeDflt(void* dst) {
|
||||
new (dst) T{};
|
||||
|
|
@ -76,7 +81,7 @@ class FlagTest : public testing::Test {
|
|||
#endif
|
||||
return std::string(fname);
|
||||
}
|
||||
flags::FlagSaver flag_saver_;
|
||||
absl::FlagSaver flag_saver_;
|
||||
};
|
||||
|
||||
struct S1 {
|
||||
|
|
@ -128,15 +133,29 @@ constexpr flags::FlagHelpArg help_arg{flags::FlagHelpMsg("literal help"),
|
|||
|
||||
using String = std::string;
|
||||
|
||||
#define DEFINE_CONSTRUCTED_FLAG(T, dflt, dflt_kind) \
|
||||
constexpr flags::FlagDefaultArg f1default##T{ \
|
||||
flags::FlagDefaultSrc{dflt}, flags::FlagDefaultKind::dflt_kind}; \
|
||||
constexpr flags::Flag<T> f1##T("f1", "file", help_arg, f1default##T); \
|
||||
ABSL_CONST_INIT flags::Flag<T> f2##T( \
|
||||
"f2", "file", \
|
||||
{flags::FlagHelpMsg(&TestHelpMsg), flags::FlagHelpKind::kGenFunc}, \
|
||||
flags::FlagDefaultArg{flags::FlagDefaultSrc(&TestMakeDflt<T>), \
|
||||
flags::FlagDefaultKind::kGenFunc})
|
||||
#if !defined(_MSC_VER) || defined(__clang__)
|
||||
#define DEFINE_CONSTRUCTED_FLAG(T, dflt, dflt_kind) \
|
||||
constexpr flags::FlagDefaultArg f1default##T{ \
|
||||
flags::FlagDefaultSrc{dflt}, flags::FlagDefaultKind::dflt_kind}; \
|
||||
constexpr absl::Flag<T> f1##T{"f1", "file", help_arg, f1default##T}; \
|
||||
ABSL_CONST_INIT absl::Flag<T> f2##T { \
|
||||
"f2", "file", \
|
||||
{flags::FlagHelpMsg(&TestHelpMsg), flags::FlagHelpKind::kGenFunc}, \
|
||||
flags::FlagDefaultArg { \
|
||||
flags::FlagDefaultSrc(&TestMakeDflt<T>), \
|
||||
flags::FlagDefaultKind::kGenFunc \
|
||||
} \
|
||||
}
|
||||
#else
|
||||
#define DEFINE_CONSTRUCTED_FLAG(T, dflt, dflt_kind) \
|
||||
constexpr flags::FlagDefaultArg f1default##T{ \
|
||||
flags::FlagDefaultSrc{dflt}, flags::FlagDefaultKind::dflt_kind}; \
|
||||
constexpr absl::Flag<T> f1##T{"f1", "file", &TestLiteralHelpMsg, \
|
||||
&TestMakeDflt<T>}; \
|
||||
ABSL_CONST_INIT absl::Flag<T> f2##T { \
|
||||
"f2", "file", &TestHelpMsg, &TestMakeDflt<T> \
|
||||
}
|
||||
#endif
|
||||
|
||||
DEFINE_CONSTRUCTED_FLAG(bool, true, kOneWord);
|
||||
DEFINE_CONSTRUCTED_FLAG(int16_t, 1, kOneWord);
|
||||
|
|
@ -151,21 +170,22 @@ DEFINE_CONSTRUCTED_FLAG(String, &TestMakeDflt<String>, kGenFunc);
|
|||
DEFINE_CONSTRUCTED_FLAG(UDT, &TestMakeDflt<UDT>, kGenFunc);
|
||||
|
||||
template <typename T>
|
||||
bool TestConstructionFor(const flags::Flag<T>& f1, flags::Flag<T>* f2) {
|
||||
EXPECT_EQ(f1.Name(), "f1");
|
||||
EXPECT_EQ(f1.Help(), "literal help");
|
||||
EXPECT_EQ(f1.Filename(), "file");
|
||||
bool TestConstructionFor(const absl::Flag<T>& f1, absl::Flag<T>& f2) {
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f1).Name(), "f1");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f1).Help(), "literal help");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f1).Filename(), "file");
|
||||
|
||||
flags::FlagRegistrar<T, false>(f2).OnUpdate(TestCallback);
|
||||
flags::FlagRegistrar<T, false>(ABSL_FLAG_IMPL_FLAG_PTR(f2))
|
||||
.OnUpdate(TestCallback);
|
||||
|
||||
EXPECT_EQ(f2->Name(), "f2");
|
||||
EXPECT_EQ(f2->Help(), "dynamic help");
|
||||
EXPECT_EQ(f2->Filename(), "file");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f2).Name(), "f2");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f2).Help(), "dynamic help");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(f2).Filename(), "file");
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
#define TEST_CONSTRUCTED_FLAG(T) TestConstructionFor(f1##T, &f2##T);
|
||||
#define TEST_CONSTRUCTED_FLAG(T) TestConstructionFor(f1##T, f2##T);
|
||||
|
||||
TEST_F(FlagTest, TestConstruction) {
|
||||
TEST_CONSTRUCTED_FLAG(bool);
|
||||
|
|
@ -204,18 +224,30 @@ namespace {
|
|||
|
||||
TEST_F(FlagTest, TestFlagDeclaration) {
|
||||
// test that we can access flag objects.
|
||||
EXPECT_EQ(FLAGS_test_flag_01.Name(), "test_flag_01");
|
||||
EXPECT_EQ(FLAGS_test_flag_02.Name(), "test_flag_02");
|
||||
EXPECT_EQ(FLAGS_test_flag_03.Name(), "test_flag_03");
|
||||
EXPECT_EQ(FLAGS_test_flag_04.Name(), "test_flag_04");
|
||||
EXPECT_EQ(FLAGS_test_flag_05.Name(), "test_flag_05");
|
||||
EXPECT_EQ(FLAGS_test_flag_06.Name(), "test_flag_06");
|
||||
EXPECT_EQ(FLAGS_test_flag_07.Name(), "test_flag_07");
|
||||
EXPECT_EQ(FLAGS_test_flag_08.Name(), "test_flag_08");
|
||||
EXPECT_EQ(FLAGS_test_flag_09.Name(), "test_flag_09");
|
||||
EXPECT_EQ(FLAGS_test_flag_10.Name(), "test_flag_10");
|
||||
EXPECT_EQ(FLAGS_test_flag_11.Name(), "test_flag_11");
|
||||
EXPECT_EQ(FLAGS_test_flag_12.Name(), "test_flag_12");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_01).Name(),
|
||||
"test_flag_01");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_02).Name(),
|
||||
"test_flag_02");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_03).Name(),
|
||||
"test_flag_03");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_04).Name(),
|
||||
"test_flag_04");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_05).Name(),
|
||||
"test_flag_05");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_06).Name(),
|
||||
"test_flag_06");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_07).Name(),
|
||||
"test_flag_07");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_08).Name(),
|
||||
"test_flag_08");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_09).Name(),
|
||||
"test_flag_09");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_10).Name(),
|
||||
"test_flag_10");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_11).Name(),
|
||||
"test_flag_11");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_12).Name(),
|
||||
"test_flag_12");
|
||||
}
|
||||
#endif // !ABSL_FLAGS_STRIP_NAMES
|
||||
|
||||
|
|
@ -242,96 +274,168 @@ namespace {
|
|||
TEST_F(FlagTest, TestFlagDefinition) {
|
||||
absl::string_view expected_file_name = "absl/flags/flag_test.cc";
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_01.Name(), "test_flag_01");
|
||||
EXPECT_EQ(FLAGS_test_flag_01.Help(), "test flag 01");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_01.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_01.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_01).Name(),
|
||||
"test_flag_01");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_01).Help(),
|
||||
"test flag 01");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_01).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_01).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_02.Name(), "test_flag_02");
|
||||
EXPECT_EQ(FLAGS_test_flag_02.Help(), "test flag 02");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_02.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_02.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_02).Name(),
|
||||
"test_flag_02");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_02).Help(),
|
||||
"test flag 02");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_02).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_02).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_03.Name(), "test_flag_03");
|
||||
EXPECT_EQ(FLAGS_test_flag_03.Help(), "test flag 03");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_03.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_03.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_03).Name(),
|
||||
"test_flag_03");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_03).Help(),
|
||||
"test flag 03");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_03).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_03).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_04.Name(), "test_flag_04");
|
||||
EXPECT_EQ(FLAGS_test_flag_04.Help(), "test flag 04");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_04.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_04.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_04).Name(),
|
||||
"test_flag_04");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_04).Help(),
|
||||
"test flag 04");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_04).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_04).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_05.Name(), "test_flag_05");
|
||||
EXPECT_EQ(FLAGS_test_flag_05.Help(), "test flag 05");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_05.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_05.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_05).Name(),
|
||||
"test_flag_05");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_05).Help(),
|
||||
"test flag 05");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_05).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_05).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_06.Name(), "test_flag_06");
|
||||
EXPECT_EQ(FLAGS_test_flag_06.Help(), "test flag 06");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_06.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_06.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_06).Name(),
|
||||
"test_flag_06");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_06).Help(),
|
||||
"test flag 06");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_06).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_06).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_07.Name(), "test_flag_07");
|
||||
EXPECT_EQ(FLAGS_test_flag_07.Help(), "test flag 07");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_07.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_07.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_07).Name(),
|
||||
"test_flag_07");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_07).Help(),
|
||||
"test flag 07");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_07).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_07).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_08.Name(), "test_flag_08");
|
||||
EXPECT_EQ(FLAGS_test_flag_08.Help(), "test flag 08");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_08.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_08.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_08).Name(),
|
||||
"test_flag_08");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_08).Help(),
|
||||
"test flag 08");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_08).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_08).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_09.Name(), "test_flag_09");
|
||||
EXPECT_EQ(FLAGS_test_flag_09.Help(), "test flag 09");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_09.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_09.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_09).Name(),
|
||||
"test_flag_09");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_09).Help(),
|
||||
"test flag 09");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_09).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_09).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_10.Name(), "test_flag_10");
|
||||
EXPECT_EQ(FLAGS_test_flag_10.Help(), "test flag 10");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_10.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_10.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_10).Name(),
|
||||
"test_flag_10");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_10).Help(),
|
||||
"test flag 10");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_10).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_10).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_11.Name(), "test_flag_11");
|
||||
EXPECT_EQ(FLAGS_test_flag_11.Help(), "test flag 11");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_11.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_11.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_11).Name(),
|
||||
"test_flag_11");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_11).Help(),
|
||||
"test flag 11");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_11).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_11).Filename();
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_12.Name(), "test_flag_12");
|
||||
EXPECT_EQ(FLAGS_test_flag_12.Help(), "test flag 12");
|
||||
EXPECT_TRUE(absl::EndsWith(FLAGS_test_flag_12.Filename(), expected_file_name))
|
||||
<< FLAGS_test_flag_12.Filename();
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_12).Name(),
|
||||
"test_flag_12");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_12).Help(),
|
||||
"test flag 12");
|
||||
EXPECT_TRUE(absl::EndsWith(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_12).Filename(),
|
||||
expected_file_name))
|
||||
<< absl::GetFlagReflectionHandle(FLAGS_test_flag_12).Filename();
|
||||
}
|
||||
#endif // !ABSL_FLAGS_STRIP_NAMES
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(FlagTest, TestDefault) {
|
||||
EXPECT_EQ(FLAGS_test_flag_01.DefaultValue(), "true");
|
||||
EXPECT_EQ(FLAGS_test_flag_02.DefaultValue(), "1234");
|
||||
EXPECT_EQ(FLAGS_test_flag_03.DefaultValue(), "-34");
|
||||
EXPECT_EQ(FLAGS_test_flag_04.DefaultValue(), "189");
|
||||
EXPECT_EQ(FLAGS_test_flag_05.DefaultValue(), "10765");
|
||||
EXPECT_EQ(FLAGS_test_flag_06.DefaultValue(), "40000");
|
||||
EXPECT_EQ(FLAGS_test_flag_07.DefaultValue(), "-1234567");
|
||||
EXPECT_EQ(FLAGS_test_flag_08.DefaultValue(), "9876543");
|
||||
EXPECT_EQ(FLAGS_test_flag_09.DefaultValue(), "-9.876e-50");
|
||||
EXPECT_EQ(FLAGS_test_flag_10.DefaultValue(), "1.234e+12");
|
||||
EXPECT_EQ(FLAGS_test_flag_11.DefaultValue(), "");
|
||||
EXPECT_EQ(FLAGS_test_flag_12.DefaultValue(), "10m");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_01).DefaultValue(),
|
||||
"true");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_02).DefaultValue(),
|
||||
"1234");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_03).DefaultValue(),
|
||||
"-34");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_04).DefaultValue(),
|
||||
"189");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_05).DefaultValue(),
|
||||
"10765");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_06).DefaultValue(),
|
||||
"40000");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_07).DefaultValue(),
|
||||
"-1234567");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_08).DefaultValue(),
|
||||
"9876543");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_09).DefaultValue(),
|
||||
"-9.876e-50");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_10).DefaultValue(),
|
||||
"1.234e+12");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_11).DefaultValue(),
|
||||
"");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_12).DefaultValue(),
|
||||
"10m");
|
||||
|
||||
EXPECT_EQ(FLAGS_test_flag_01.CurrentValue(), "true");
|
||||
EXPECT_EQ(FLAGS_test_flag_02.CurrentValue(), "1234");
|
||||
EXPECT_EQ(FLAGS_test_flag_03.CurrentValue(), "-34");
|
||||
EXPECT_EQ(FLAGS_test_flag_04.CurrentValue(), "189");
|
||||
EXPECT_EQ(FLAGS_test_flag_05.CurrentValue(), "10765");
|
||||
EXPECT_EQ(FLAGS_test_flag_06.CurrentValue(), "40000");
|
||||
EXPECT_EQ(FLAGS_test_flag_07.CurrentValue(), "-1234567");
|
||||
EXPECT_EQ(FLAGS_test_flag_08.CurrentValue(), "9876543");
|
||||
EXPECT_EQ(FLAGS_test_flag_09.CurrentValue(), "-9.876e-50");
|
||||
EXPECT_EQ(FLAGS_test_flag_10.CurrentValue(), "1.234e+12");
|
||||
EXPECT_EQ(FLAGS_test_flag_11.CurrentValue(), "");
|
||||
EXPECT_EQ(FLAGS_test_flag_12.CurrentValue(), "10m");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_01).CurrentValue(),
|
||||
"true");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_02).CurrentValue(),
|
||||
"1234");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_03).CurrentValue(),
|
||||
"-34");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_04).CurrentValue(),
|
||||
"189");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_05).CurrentValue(),
|
||||
"10765");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_06).CurrentValue(),
|
||||
"40000");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_07).CurrentValue(),
|
||||
"-1234567");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_08).CurrentValue(),
|
||||
"9876543");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_09).CurrentValue(),
|
||||
"-9.876e-50");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_10).CurrentValue(),
|
||||
"1.234e+12");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_11).CurrentValue(),
|
||||
"");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_12).CurrentValue(),
|
||||
"10m");
|
||||
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_test_flag_01), true);
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_test_flag_02), 1234);
|
||||
|
|
@ -386,12 +490,18 @@ ABSL_FLAG(NonTriviallyCopyableAggregate, test_flag_eb_06, {}, "");
|
|||
namespace {
|
||||
|
||||
TEST_F(FlagTest, TestEmptyBracesDefault) {
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_01.DefaultValue(), "false");
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_02.DefaultValue(), "0");
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_03.DefaultValue(), "0");
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_04.DefaultValue(), "0");
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_05.DefaultValue(), "");
|
||||
EXPECT_EQ(FLAGS_test_flag_eb_06.DefaultValue(), "0");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_01).DefaultValue(),
|
||||
"false");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_02).DefaultValue(),
|
||||
"0");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_03).DefaultValue(),
|
||||
"0");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_04).DefaultValue(),
|
||||
"0");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_05).DefaultValue(),
|
||||
"");
|
||||
EXPECT_EQ(absl::GetFlagReflectionHandle(FLAGS_test_flag_eb_06).DefaultValue(),
|
||||
"0");
|
||||
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_test_flag_eb_01), false);
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_test_flag_eb_02), 0);
|
||||
|
|
@ -445,29 +555,29 @@ TEST_F(FlagTest, TestGetSet) {
|
|||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(FlagTest, TestGetViaReflection) {
|
||||
auto* handle = flags::FindCommandLineFlag("test_flag_01");
|
||||
auto* handle = absl::FindCommandLineFlag("test_flag_01");
|
||||
EXPECT_EQ(*handle->TryGet<bool>(), true);
|
||||
handle = flags::FindCommandLineFlag("test_flag_02");
|
||||
handle = absl::FindCommandLineFlag("test_flag_02");
|
||||
EXPECT_EQ(*handle->TryGet<int>(), 1234);
|
||||
handle = flags::FindCommandLineFlag("test_flag_03");
|
||||
handle = absl::FindCommandLineFlag("test_flag_03");
|
||||
EXPECT_EQ(*handle->TryGet<int16_t>(), -34);
|
||||
handle = flags::FindCommandLineFlag("test_flag_04");
|
||||
handle = absl::FindCommandLineFlag("test_flag_04");
|
||||
EXPECT_EQ(*handle->TryGet<uint16_t>(), 189);
|
||||
handle = flags::FindCommandLineFlag("test_flag_05");
|
||||
handle = absl::FindCommandLineFlag("test_flag_05");
|
||||
EXPECT_EQ(*handle->TryGet<int32_t>(), 10765);
|
||||
handle = flags::FindCommandLineFlag("test_flag_06");
|
||||
handle = absl::FindCommandLineFlag("test_flag_06");
|
||||
EXPECT_EQ(*handle->TryGet<uint32_t>(), 40000);
|
||||
handle = flags::FindCommandLineFlag("test_flag_07");
|
||||
handle = absl::FindCommandLineFlag("test_flag_07");
|
||||
EXPECT_EQ(*handle->TryGet<int64_t>(), -1234567);
|
||||
handle = flags::FindCommandLineFlag("test_flag_08");
|
||||
handle = absl::FindCommandLineFlag("test_flag_08");
|
||||
EXPECT_EQ(*handle->TryGet<uint64_t>(), 9876543);
|
||||
handle = flags::FindCommandLineFlag("test_flag_09");
|
||||
handle = absl::FindCommandLineFlag("test_flag_09");
|
||||
EXPECT_NEAR(*handle->TryGet<double>(), -9.876e-50, 1e-55);
|
||||
handle = flags::FindCommandLineFlag("test_flag_10");
|
||||
handle = absl::FindCommandLineFlag("test_flag_10");
|
||||
EXPECT_NEAR(*handle->TryGet<float>(), 1.234e12f, 1e5f);
|
||||
handle = flags::FindCommandLineFlag("test_flag_11");
|
||||
handle = absl::FindCommandLineFlag("test_flag_11");
|
||||
EXPECT_EQ(*handle->TryGet<std::string>(), "");
|
||||
handle = flags::FindCommandLineFlag("test_flag_12");
|
||||
handle = absl::FindCommandLineFlag("test_flag_12");
|
||||
EXPECT_EQ(*handle->TryGet<absl::Duration>(), absl::Minutes(10));
|
||||
}
|
||||
|
||||
|
|
@ -501,8 +611,9 @@ namespace {
|
|||
|
||||
#if !ABSL_FLAGS_STRIP_HELP
|
||||
TEST_F(FlagTest, TestNonConstexprHelp) {
|
||||
EXPECT_EQ(FLAGS_test_flag_with_non_const_help.Help(),
|
||||
"test flag non const help");
|
||||
EXPECT_EQ(
|
||||
absl::GetFlagReflectionHandle(FLAGS_test_flag_with_non_const_help).Help(),
|
||||
"test flag non const help");
|
||||
}
|
||||
#endif //! ABSL_FLAGS_STRIP_HELP
|
||||
|
||||
|
|
@ -704,14 +815,15 @@ ABSL_RETIRED_FLAG(std::string, old_str_flag, "", absl::StrCat("old ", "descr"));
|
|||
namespace {
|
||||
|
||||
TEST_F(FlagTest, TestRetiredFlagRegistration) {
|
||||
bool is_bool = false;
|
||||
EXPECT_TRUE(flags::IsRetiredFlag("old_bool_flag", &is_bool));
|
||||
EXPECT_TRUE(is_bool);
|
||||
EXPECT_TRUE(flags::IsRetiredFlag("old_int_flag", &is_bool));
|
||||
EXPECT_FALSE(is_bool);
|
||||
EXPECT_TRUE(flags::IsRetiredFlag("old_str_flag", &is_bool));
|
||||
EXPECT_FALSE(is_bool);
|
||||
EXPECT_FALSE(flags::IsRetiredFlag("some_other_flag", &is_bool));
|
||||
auto* handle = absl::FindCommandLineFlag("old_bool_flag");
|
||||
EXPECT_TRUE(handle->IsOfType<bool>());
|
||||
EXPECT_TRUE(handle->IsRetired());
|
||||
handle = absl::FindCommandLineFlag("old_int_flag");
|
||||
EXPECT_TRUE(handle->IsOfType<int>());
|
||||
EXPECT_TRUE(handle->IsRetired());
|
||||
handle = absl::FindCommandLineFlag("old_str_flag");
|
||||
EXPECT_TRUE(handle->IsOfType<std::string>());
|
||||
EXPECT_TRUE(handle->IsRetired());
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
|
|
|||
|
|
@ -16,14 +16,8 @@
|
|||
#ifndef ABSL_FLAGS_INTERNAL_COMMANDLINEFLAG_H_
|
||||
#define ABSL_FLAGS_INTERNAL_COMMANDLINEFLAG_H_
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/fast_type_id.h"
|
||||
#include "absl/base/macros.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/types/optional.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
|
@ -34,7 +28,7 @@ namespace flags_internal {
|
|||
// cases this id is enough to uniquely identify the flag's value type. In a few
|
||||
// cases we'll have to resort to using actual RTTI implementation if it is
|
||||
// available.
|
||||
using FlagFastTypeId = base_internal::FastTypeIdType;
|
||||
using FlagFastTypeId = absl::base_internal::FastTypeIdType;
|
||||
|
||||
// Options that control SetCommandLineOptionWithMode.
|
||||
enum FlagSettingMode {
|
||||
|
|
@ -67,117 +61,6 @@ class FlagStateInterface {
|
|||
virtual void Restore() const = 0;
|
||||
};
|
||||
|
||||
// Holds all information for a flag.
|
||||
class CommandLineFlag {
|
||||
public:
|
||||
constexpr CommandLineFlag() = default;
|
||||
|
||||
// Not copyable/assignable.
|
||||
CommandLineFlag(const CommandLineFlag&) = delete;
|
||||
CommandLineFlag& operator=(const CommandLineFlag&) = delete;
|
||||
|
||||
// Non-polymorphic access methods.
|
||||
|
||||
// Return true iff flag has type T.
|
||||
template <typename T>
|
||||
inline bool IsOfType() const {
|
||||
return TypeId() == base_internal::FastTypeId<T>();
|
||||
}
|
||||
|
||||
// Attempts to retrieve the flag value. Returns value on success,
|
||||
// absl::nullopt otherwise.
|
||||
template <typename T>
|
||||
absl::optional<T> TryGet() const {
|
||||
if (IsRetired() || !IsOfType<T>()) {
|
||||
return absl::nullopt;
|
||||
}
|
||||
|
||||
// Implementation notes:
|
||||
//
|
||||
// We are wrapping a union around the value of `T` to serve three purposes:
|
||||
//
|
||||
// 1. `U.value` has correct size and alignment for a value of type `T`
|
||||
// 2. The `U.value` constructor is not invoked since U's constructor does
|
||||
// not do it explicitly.
|
||||
// 3. The `U.value` destructor is invoked since U's destructor does it
|
||||
// explicitly. This makes `U` a kind of RAII wrapper around non default
|
||||
// constructible value of T, which is destructed when we leave the
|
||||
// scope. We do need to destroy U.value, which is constructed by
|
||||
// CommandLineFlag::Read even though we left it in a moved-from state
|
||||
// after std::move.
|
||||
//
|
||||
// All of this serves to avoid requiring `T` being default constructible.
|
||||
union U {
|
||||
T value;
|
||||
U() {}
|
||||
~U() { value.~T(); }
|
||||
};
|
||||
U u;
|
||||
|
||||
Read(&u.value);
|
||||
return std::move(u.value);
|
||||
}
|
||||
|
||||
// Polymorphic access methods
|
||||
|
||||
// Returns name of this flag.
|
||||
virtual absl::string_view Name() const = 0;
|
||||
// Returns name of the file where this flag is defined.
|
||||
virtual std::string Filename() const = 0;
|
||||
// Returns help message associated with this flag.
|
||||
virtual std::string Help() const = 0;
|
||||
// Returns true iff this object corresponds to retired flag.
|
||||
virtual bool IsRetired() const;
|
||||
virtual std::string DefaultValue() const = 0;
|
||||
virtual std::string CurrentValue() const = 0;
|
||||
|
||||
// Sets the value of the flag based on specified string `value`. If the flag
|
||||
// was successfully set to new value, it returns true. Otherwise, sets `error`
|
||||
// to indicate the error, leaves the flag unchanged, and returns false.
|
||||
bool ParseFrom(absl::string_view value, std::string* error);
|
||||
|
||||
protected:
|
||||
~CommandLineFlag() = default;
|
||||
|
||||
private:
|
||||
friend class PrivateHandleAccessor;
|
||||
|
||||
// Sets the value of the flag based on specified string `value`. If the flag
|
||||
// was successfully set to new value, it returns true. Otherwise, sets `error`
|
||||
// to indicate the error, leaves the flag unchanged, and returns false. There
|
||||
// are three ways to set the flag's value:
|
||||
// * Update the current flag value
|
||||
// * Update the flag's default value
|
||||
// * Update the current flag value if it was never set before
|
||||
// The mode is selected based on `set_mode` parameter.
|
||||
virtual bool ParseFrom(absl::string_view value,
|
||||
flags_internal::FlagSettingMode set_mode,
|
||||
flags_internal::ValueSource source,
|
||||
std::string* error) = 0;
|
||||
|
||||
// Returns id of the flag's value type.
|
||||
virtual FlagFastTypeId TypeId() const = 0;
|
||||
|
||||
// Interface to save flag to some persistent state. Returns current flag state
|
||||
// or nullptr if flag does not support saving and restoring a state.
|
||||
virtual std::unique_ptr<FlagStateInterface> SaveState() = 0;
|
||||
|
||||
// Copy-construct a new value of the flag's type in a memory referenced by
|
||||
// the dst based on the current flag's value.
|
||||
virtual void Read(void* dst) const = 0;
|
||||
|
||||
// To be deleted. Used to return true if flag's current value originated from
|
||||
// command line.
|
||||
virtual bool IsSpecifiedOnCommandLine() const = 0;
|
||||
|
||||
// Validates supplied value usign validator or parseflag routine
|
||||
virtual bool ValidateInputValue(absl::string_view value) const = 0;
|
||||
|
||||
// Checks that flags default value can be converted to string and back to the
|
||||
// flag's value type.
|
||||
virtual void CheckDefaultValueParsingRoundtrip() const = 0;
|
||||
};
|
||||
|
||||
} // namespace flags_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
|
|
|||
|
|
@ -15,22 +15,26 @@
|
|||
|
||||
#include "absl/flags/internal/flag.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <array>
|
||||
#include <atomic>
|
||||
#include <memory>
|
||||
#include <new>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <typeinfo>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/call_once.h"
|
||||
#include "absl/base/casts.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/const_init.h"
|
||||
#include "absl/base/optimization.h"
|
||||
#include "absl/flags/config.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/memory/memory.h"
|
||||
#include "absl/strings/str_cat.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/synchronization/mutex.h"
|
||||
|
|
@ -63,14 +67,14 @@ bool ShouldValidateFlagValue(FlagFastTypeId flag_type_id) {
|
|||
// need to acquire these locks themselves.
|
||||
class MutexRelock {
|
||||
public:
|
||||
explicit MutexRelock(absl::Mutex* mu) : mu_(mu) { mu_->Unlock(); }
|
||||
~MutexRelock() { mu_->Lock(); }
|
||||
explicit MutexRelock(absl::Mutex& mu) : mu_(mu) { mu_.Unlock(); }
|
||||
~MutexRelock() { mu_.Lock(); }
|
||||
|
||||
MutexRelock(const MutexRelock&) = delete;
|
||||
MutexRelock& operator=(const MutexRelock&) = delete;
|
||||
|
||||
private:
|
||||
absl::Mutex* mu_;
|
||||
absl::Mutex& mu_;
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
|
@ -83,7 +87,7 @@ class FlagImpl;
|
|||
class FlagState : public flags_internal::FlagStateInterface {
|
||||
public:
|
||||
template <typename V>
|
||||
FlagState(FlagImpl* flag_impl, const V& v, bool modified,
|
||||
FlagState(FlagImpl& flag_impl, const V& v, bool modified,
|
||||
bool on_command_line, int64_t counter)
|
||||
: flag_impl_(flag_impl),
|
||||
value_(v),
|
||||
|
|
@ -92,9 +96,9 @@ class FlagState : public flags_internal::FlagStateInterface {
|
|||
counter_(counter) {}
|
||||
|
||||
~FlagState() override {
|
||||
if (flag_impl_->ValueStorageKind() != FlagValueStorageKind::kAlignedBuffer)
|
||||
if (flag_impl_.ValueStorageKind() != FlagValueStorageKind::kAlignedBuffer)
|
||||
return;
|
||||
flags_internal::Delete(flag_impl_->op_, value_.heap_allocated);
|
||||
flags_internal::Delete(flag_impl_.op_, value_.heap_allocated);
|
||||
}
|
||||
|
||||
private:
|
||||
|
|
@ -102,15 +106,15 @@ class FlagState : public flags_internal::FlagStateInterface {
|
|||
|
||||
// Restores the flag to the saved state.
|
||||
void Restore() const override {
|
||||
if (!flag_impl_->RestoreState(*this)) return;
|
||||
if (!flag_impl_.RestoreState(*this)) return;
|
||||
|
||||
ABSL_INTERNAL_LOG(
|
||||
INFO, absl::StrCat("Restore saved value of ", flag_impl_->Name(),
|
||||
" to: ", flag_impl_->CurrentValue()));
|
||||
ABSL_INTERNAL_LOG(INFO,
|
||||
absl::StrCat("Restore saved value of ", flag_impl_.Name(),
|
||||
" to: ", flag_impl_.CurrentValue()));
|
||||
}
|
||||
|
||||
// Flag and saved flag data.
|
||||
FlagImpl* flag_impl_;
|
||||
FlagImpl& flag_impl_;
|
||||
union SavedValue {
|
||||
explicit SavedValue(void* v) : heap_allocated(v) {}
|
||||
explicit SavedValue(int64_t v) : one_word(v) {}
|
||||
|
|
@ -327,7 +331,7 @@ void FlagImpl::InvokeCallback() const {
|
|||
// and it also can be different by the time the callback invocation is
|
||||
// completed. Requires that *primary_lock be held in exclusive mode; it may be
|
||||
// released and reacquired by the implementation.
|
||||
MutexRelock relock(DataGuard());
|
||||
MutexRelock relock(*DataGuard());
|
||||
absl::MutexLock lock(&callback_->guard);
|
||||
cb();
|
||||
}
|
||||
|
|
@ -340,17 +344,17 @@ std::unique_ptr<FlagStateInterface> FlagImpl::SaveState() {
|
|||
switch (ValueStorageKind()) {
|
||||
case FlagValueStorageKind::kAlignedBuffer: {
|
||||
return absl::make_unique<FlagState>(
|
||||
this, flags_internal::Clone(op_, AlignedBufferValue()), modified,
|
||||
*this, flags_internal::Clone(op_, AlignedBufferValue()), modified,
|
||||
on_command_line, counter_);
|
||||
}
|
||||
case FlagValueStorageKind::kOneWordAtomic: {
|
||||
return absl::make_unique<FlagState>(
|
||||
this, OneWordValue().load(std::memory_order_acquire), modified,
|
||||
*this, OneWordValue().load(std::memory_order_acquire), modified,
|
||||
on_command_line, counter_);
|
||||
}
|
||||
case FlagValueStorageKind::kTwoWordsAtomic: {
|
||||
return absl::make_unique<FlagState>(
|
||||
this, TwoWordsValue().load(std::memory_order_acquire), modified,
|
||||
*this, TwoWordsValue().load(std::memory_order_acquire), modified,
|
||||
on_command_line, counter_);
|
||||
}
|
||||
}
|
||||
|
|
@ -411,14 +415,14 @@ std::atomic<AlignedTwoWords>& FlagImpl::TwoWordsValue() const {
|
|||
// parsed value. In case if any error is encountered in either step, the error
|
||||
// message is stored in 'err'
|
||||
std::unique_ptr<void, DynValueDeleter> FlagImpl::TryParse(
|
||||
absl::string_view value, std::string* err) const {
|
||||
absl::string_view value, std::string& err) const {
|
||||
std::unique_ptr<void, DynValueDeleter> tentative_value = MakeInitValue();
|
||||
|
||||
std::string parse_err;
|
||||
if (!flags_internal::Parse(op_, value, tentative_value.get(), &parse_err)) {
|
||||
absl::string_view err_sep = parse_err.empty() ? "" : "; ";
|
||||
*err = absl::StrCat("Illegal value '", value, "' specified for flag '",
|
||||
Name(), "'", err_sep, parse_err);
|
||||
err = absl::StrCat("Illegal value '", value, "' specified for flag '",
|
||||
Name(), "'", err_sep, parse_err);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
|
@ -474,7 +478,7 @@ void FlagImpl::Write(const void* src) {
|
|||
// * Update the current flag value if it was never set before
|
||||
// The mode is selected based on 'set_mode' parameter.
|
||||
bool FlagImpl::ParseFrom(absl::string_view value, FlagSettingMode set_mode,
|
||||
ValueSource source, std::string* err) {
|
||||
ValueSource source, std::string& err) {
|
||||
absl::MutexLock l(DataGuard());
|
||||
|
||||
switch (set_mode) {
|
||||
|
|
|
|||
105
third_party/abseil_cpp/absl/flags/internal/flag.h
vendored
105
third_party/abseil_cpp/absl/flags/internal/flag.h
vendored
|
|
@ -16,31 +16,36 @@
|
|||
#ifndef ABSL_FLAGS_INTERNAL_FLAG_H_
|
||||
#define ABSL_FLAGS_INTERNAL_FLAG_H_
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include <atomic>
|
||||
#include <cstring>
|
||||
#include <memory>
|
||||
#include <new>
|
||||
#include <string>
|
||||
#include <type_traits>
|
||||
#include <typeinfo>
|
||||
|
||||
#include "absl/base/attributes.h"
|
||||
#include "absl/base/call_once.h"
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/optimization.h"
|
||||
#include "absl/base/thread_annotations.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/config.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/memory/memory.h"
|
||||
#include "absl/meta/type_traits.h"
|
||||
#include "absl/strings/str_cat.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/synchronization/mutex.h"
|
||||
#include "absl/utility/utility.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Forward declaration of absl::Flag<T> public API.
|
||||
namespace flags_internal {
|
||||
template <typename T>
|
||||
|
|
@ -64,12 +69,15 @@ void SetFlag(absl::Flag<T>* flag, const T& v);
|
|||
template <typename T, typename V>
|
||||
void SetFlag(absl::Flag<T>* flag, const V& v);
|
||||
|
||||
namespace flags_internal {
|
||||
template <typename U>
|
||||
const CommandLineFlag& GetFlagReflectionHandle(const absl::Flag<U>& f);
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// Flag value type operations, eg., parsing, copying, etc. are provided
|
||||
// by function specific to that type with a signature matching FlagOpFn.
|
||||
|
||||
namespace flags_internal {
|
||||
|
||||
enum class FlagOp {
|
||||
kAlloc,
|
||||
kDelete,
|
||||
|
|
@ -168,6 +176,28 @@ inline const std::type_info* GenRuntimeTypeId() {
|
|||
// cases.
|
||||
using HelpGenFunc = std::string (*)();
|
||||
|
||||
template <size_t N>
|
||||
struct FixedCharArray {
|
||||
char value[N];
|
||||
|
||||
template <size_t... I>
|
||||
static constexpr FixedCharArray<N> FromLiteralString(
|
||||
absl::string_view str, absl::index_sequence<I...>) {
|
||||
return (void)str, FixedCharArray<N>({{str[I]..., '\0'}});
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Gen, size_t N = Gen::Value().size()>
|
||||
constexpr FixedCharArray<N + 1> HelpStringAsArray(int) {
|
||||
return FixedCharArray<N + 1>::FromLiteralString(
|
||||
Gen::Value(), absl::make_index_sequence<N>{});
|
||||
}
|
||||
|
||||
template <typename Gen>
|
||||
constexpr std::false_type HelpStringAsArray(char) {
|
||||
return std::false_type{};
|
||||
}
|
||||
|
||||
union FlagHelpMsg {
|
||||
constexpr explicit FlagHelpMsg(const char* help_msg) : literal(help_msg) {}
|
||||
constexpr explicit FlagHelpMsg(HelpGenFunc help_gen) : gen_func(help_gen) {}
|
||||
|
|
@ -185,40 +215,28 @@ struct FlagHelpArg {
|
|||
|
||||
extern const char kStrippedFlagHelp[];
|
||||
|
||||
// HelpConstexprWrap is used by struct AbslFlagHelpGenFor##name generated by
|
||||
// ABSL_FLAG macro. It is only used to silence the compiler in the case where
|
||||
// help message expression is not constexpr and does not have type const char*.
|
||||
// If help message expression is indeed constexpr const char* HelpConstexprWrap
|
||||
// is just a trivial identity function.
|
||||
template <typename T>
|
||||
const char* HelpConstexprWrap(const T&) {
|
||||
return nullptr;
|
||||
}
|
||||
constexpr const char* HelpConstexprWrap(const char* p) { return p; }
|
||||
constexpr const char* HelpConstexprWrap(char* p) { return p; }
|
||||
|
||||
// These two HelpArg overloads allows us to select at compile time one of two
|
||||
// way to pass Help argument to absl::Flag. We'll be passing
|
||||
// AbslFlagHelpGenFor##name as T and integer 0 as a single argument to prefer
|
||||
// first overload if possible. If T::Const is evaluatable on constexpr
|
||||
// context (see non template int parameter below) we'll choose first overload.
|
||||
// In this case the help message expression is immediately evaluated and is used
|
||||
// to construct the absl::Flag. No additionl code is generated by ABSL_FLAG.
|
||||
// Otherwise SFINAE kicks in and first overload is dropped from the
|
||||
// AbslFlagHelpGenFor##name as Gen and integer 0 as a single argument to prefer
|
||||
// first overload if possible. If help message is evaluatable on constexpr
|
||||
// context We'll be able to make FixedCharArray out of it and we'll choose first
|
||||
// overload. In this case the help message expression is immediately evaluated
|
||||
// and is used to construct the absl::Flag. No additionl code is generated by
|
||||
// ABSL_FLAG Otherwise SFINAE kicks in and first overload is dropped from the
|
||||
// consideration, in which case the second overload will be used. The second
|
||||
// overload does not attempt to evaluate the help message expression
|
||||
// immediately and instead delays the evaluation by returing the function
|
||||
// pointer (&T::NonConst) genering the help message when necessary. This is
|
||||
// evaluatable in constexpr context, but the cost is an extra function being
|
||||
// generated in the ABSL_FLAG code.
|
||||
template <typename T, int = (T::Const(), 1)>
|
||||
constexpr FlagHelpArg HelpArg(int) {
|
||||
return {FlagHelpMsg(T::Const()), FlagHelpKind::kLiteral};
|
||||
template <typename Gen, size_t N>
|
||||
constexpr FlagHelpArg HelpArg(const FixedCharArray<N>& value) {
|
||||
return {FlagHelpMsg(value.value), FlagHelpKind::kLiteral};
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
constexpr FlagHelpArg HelpArg(char) {
|
||||
return {FlagHelpMsg(&T::NonConst), FlagHelpKind::kGenFunc};
|
||||
template <typename Gen>
|
||||
constexpr FlagHelpArg HelpArg(std::false_type) {
|
||||
return {FlagHelpMsg(&Gen::NonConst), FlagHelpKind::kGenFunc};
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -364,31 +382,31 @@ struct FlagValue;
|
|||
|
||||
template <typename T>
|
||||
struct FlagValue<T, FlagValueStorageKind::kAlignedBuffer> {
|
||||
bool Get(T*) const { return false; }
|
||||
bool Get(T&) const { return false; }
|
||||
|
||||
alignas(T) char value[sizeof(T)];
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct FlagValue<T, FlagValueStorageKind::kOneWordAtomic> : FlagOneWordValue {
|
||||
bool Get(T* dst) const {
|
||||
bool Get(T& dst) const {
|
||||
int64_t one_word_val = value.load(std::memory_order_acquire);
|
||||
if (ABSL_PREDICT_FALSE(one_word_val == UninitializedFlagValue())) {
|
||||
return false;
|
||||
}
|
||||
std::memcpy(dst, static_cast<const void*>(&one_word_val), sizeof(T));
|
||||
std::memcpy(&dst, static_cast<const void*>(&one_word_val), sizeof(T));
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct FlagValue<T, FlagValueStorageKind::kTwoWordsAtomic> : FlagTwoWordsValue {
|
||||
bool Get(T* dst) const {
|
||||
bool Get(T& dst) const {
|
||||
AlignedTwoWords two_words_val = value.load(std::memory_order_acquire);
|
||||
if (ABSL_PREDICT_FALSE(!two_words_val.IsInitialized())) {
|
||||
return false;
|
||||
}
|
||||
std::memcpy(dst, static_cast<const void*>(&two_words_val), sizeof(T));
|
||||
std::memcpy(&dst, static_cast<const void*>(&two_words_val), sizeof(T));
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
|
@ -419,7 +437,7 @@ struct DynValueDeleter {
|
|||
|
||||
class FlagState;
|
||||
|
||||
class FlagImpl final : public flags_internal::CommandLineFlag {
|
||||
class FlagImpl final : public CommandLineFlag {
|
||||
public:
|
||||
constexpr FlagImpl(const char* name, const char* filename, FlagOpFn op,
|
||||
FlagHelpArg help, FlagValueStorageKind value_kind,
|
||||
|
|
@ -492,7 +510,7 @@ class FlagImpl final : public flags_internal::CommandLineFlag {
|
|||
// Attempts to parse supplied `value` string. If parsing is successful,
|
||||
// returns new value. Otherwise returns nullptr.
|
||||
std::unique_ptr<void, DynValueDeleter> TryParse(absl::string_view value,
|
||||
std::string* err) const
|
||||
std::string& err) const
|
||||
ABSL_EXCLUSIVE_LOCKS_REQUIRED(*DataGuard());
|
||||
// Stores the flag value based on the pointer to the source.
|
||||
void StoreValue(const void* src) ABSL_EXCLUSIVE_LOCKS_REQUIRED(*DataGuard());
|
||||
|
|
@ -534,7 +552,7 @@ class FlagImpl final : public flags_internal::CommandLineFlag {
|
|||
ABSL_LOCKS_EXCLUDED(*DataGuard());
|
||||
|
||||
bool ParseFrom(absl::string_view value, FlagSettingMode set_mode,
|
||||
ValueSource source, std::string* error) override
|
||||
ValueSource source, std::string& error) override
|
||||
ABSL_LOCKS_EXCLUDED(*DataGuard());
|
||||
|
||||
// Immutable flag's state.
|
||||
|
|
@ -641,7 +659,7 @@ class Flag {
|
|||
impl_.AssertValidType(base_internal::FastTypeId<T>(), &GenRuntimeTypeId<T>);
|
||||
#endif
|
||||
|
||||
if (!value_.Get(&u.value)) impl_.Read(&u.value);
|
||||
if (!value_.Get(u.value)) impl_.Read(&u.value);
|
||||
return std::move(u.value);
|
||||
}
|
||||
void Set(const T& v) {
|
||||
|
|
@ -649,6 +667,13 @@ class Flag {
|
|||
impl_.Write(&v);
|
||||
}
|
||||
|
||||
template <typename U>
|
||||
friend const CommandLineFlag& absl::GetFlagReflectionHandle(
|
||||
const absl::Flag<U>& f);
|
||||
|
||||
// Access to the reflection.
|
||||
const CommandLineFlag& Reflect() const { return impl_; }
|
||||
|
||||
// Flag's data
|
||||
// The implementation depends on value_ field to be placed exactly after the
|
||||
// impl_ field, so that impl_ can figure out the offset to the value and
|
||||
|
|
@ -720,12 +745,12 @@ struct FlagRegistrarEmpty {};
|
|||
template <typename T, bool do_register>
|
||||
class FlagRegistrar {
|
||||
public:
|
||||
explicit FlagRegistrar(Flag<T>* flag) : flag_(flag) {
|
||||
if (do_register) flags_internal::RegisterCommandLineFlag(&flag_->impl_);
|
||||
explicit FlagRegistrar(Flag<T>& flag) : flag_(flag) {
|
||||
if (do_register) flags_internal::RegisterCommandLineFlag(flag_.impl_);
|
||||
}
|
||||
|
||||
FlagRegistrar OnUpdate(FlagCallbackFunc cb) && {
|
||||
flag_->impl_.SetCallback(cb);
|
||||
flag_.impl_.SetCallback(cb);
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
|
@ -735,7 +760,7 @@ class FlagRegistrar {
|
|||
operator FlagRegistrarEmpty() const { return {}; } // NOLINT
|
||||
|
||||
private:
|
||||
Flag<T>* flag_; // Flag being registered (not owned).
|
||||
Flag<T>& flag_; // Flag being registered (not owned).
|
||||
};
|
||||
|
||||
} // namespace flags_internal
|
||||
|
|
|
|||
|
|
@ -21,6 +21,7 @@
|
|||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
ABSL_DECLARE_FLAG(std::vector<std::string>, flagfile);
|
||||
ABSL_DECLARE_FLAG(std::vector<std::string>, fromenv);
|
||||
|
|
|
|||
|
|
@ -17,7 +17,6 @@
|
|||
#define ABSL_FLAGS_INTERNAL_PATH_UTIL_H_
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/strings/match.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
|
|
|
|||
|
|
@ -15,6 +15,14 @@
|
|||
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
|
@ -24,8 +32,8 @@ FlagFastTypeId PrivateHandleAccessor::TypeId(const CommandLineFlag& flag) {
|
|||
}
|
||||
|
||||
std::unique_ptr<FlagStateInterface> PrivateHandleAccessor::SaveState(
|
||||
CommandLineFlag* flag) {
|
||||
return flag->SaveState();
|
||||
CommandLineFlag& flag) {
|
||||
return flag.SaveState();
|
||||
}
|
||||
|
||||
bool PrivateHandleAccessor::IsSpecifiedOnCommandLine(
|
||||
|
|
@ -43,12 +51,12 @@ void PrivateHandleAccessor::CheckDefaultValueParsingRoundtrip(
|
|||
flag.CheckDefaultValueParsingRoundtrip();
|
||||
}
|
||||
|
||||
bool PrivateHandleAccessor::ParseFrom(CommandLineFlag* flag,
|
||||
bool PrivateHandleAccessor::ParseFrom(CommandLineFlag& flag,
|
||||
absl::string_view value,
|
||||
flags_internal::FlagSettingMode set_mode,
|
||||
flags_internal::ValueSource source,
|
||||
std::string* error) {
|
||||
return flag->ParseFrom(value, set_mode, source, error);
|
||||
std::string& error) {
|
||||
return flag.ParseFrom(value, set_mode, source, error);
|
||||
}
|
||||
|
||||
} // namespace flags_internal
|
||||
|
|
|
|||
|
|
@ -16,7 +16,13 @@
|
|||
#ifndef ABSL_FLAGS_INTERNAL_PRIVATE_HANDLE_ACCESSOR_H_
|
||||
#define ABSL_FLAGS_INTERNAL_PRIVATE_HANDLE_ACCESSOR_H_
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
|
|
@ -31,7 +37,7 @@ class PrivateHandleAccessor {
|
|||
static FlagFastTypeId TypeId(const CommandLineFlag& flag);
|
||||
|
||||
// Access to CommandLineFlag::SaveState.
|
||||
static std::unique_ptr<FlagStateInterface> SaveState(CommandLineFlag* flag);
|
||||
static std::unique_ptr<FlagStateInterface> SaveState(CommandLineFlag& flag);
|
||||
|
||||
// Access to CommandLineFlag::IsSpecifiedOnCommandLine.
|
||||
static bool IsSpecifiedOnCommandLine(const CommandLineFlag& flag);
|
||||
|
|
@ -43,9 +49,9 @@ class PrivateHandleAccessor {
|
|||
// Access to CommandLineFlag::CheckDefaultValueParsingRoundtrip.
|
||||
static void CheckDefaultValueParsingRoundtrip(const CommandLineFlag& flag);
|
||||
|
||||
static bool ParseFrom(CommandLineFlag* flag, absl::string_view value,
|
||||
static bool ParseFrom(CommandLineFlag& flag, absl::string_view value,
|
||||
flags_internal::FlagSettingMode set_mode,
|
||||
flags_internal::ValueSource source, std::string* error);
|
||||
flags_internal::ValueSource source, std::string& error);
|
||||
};
|
||||
|
||||
} // namespace flags_internal
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ namespace {
|
|||
|
||||
namespace flags = absl::flags_internal;
|
||||
|
||||
TEST(FlagsPathUtilTest, TestInitialProgamName) {
|
||||
TEST(FlagsPathUtilTest, TestProgamNameInterfaces) {
|
||||
flags::SetProgramInvocationName("absl/flags/program_name_test");
|
||||
std::string program_name = flags::ProgramInvocationName();
|
||||
for (char& c : program_name)
|
||||
|
|
@ -43,9 +43,7 @@ TEST(FlagsPathUtilTest, TestInitialProgamName) {
|
|||
|
||||
EXPECT_TRUE(absl::EndsWith(program_name, expect_name)) << program_name;
|
||||
EXPECT_EQ(flags::ShortProgramInvocationName(), expect_basename);
|
||||
}
|
||||
|
||||
TEST(FlagsPathUtilTest, TestProgamNameInterfaces) {
|
||||
flags::SetProgramInvocationName("a/my_test");
|
||||
|
||||
EXPECT_EQ(flags::ProgramInvocationName(), "a/my_test");
|
||||
|
|
|
|||
|
|
@ -17,11 +17,9 @@
|
|||
#define ABSL_FLAGS_INTERNAL_REGISTRY_H_
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/macros.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
|
|
@ -32,19 +30,16 @@ namespace absl {
|
|||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
||||
CommandLineFlag* FindCommandLineFlag(absl::string_view name);
|
||||
CommandLineFlag* FindRetiredFlag(absl::string_view name);
|
||||
|
||||
// Executes specified visitor for each non-retired flag in the registry.
|
||||
// Requires the caller hold the registry lock.
|
||||
void ForEachFlagUnlocked(std::function<void(CommandLineFlag*)> visitor);
|
||||
void ForEachFlagUnlocked(std::function<void(CommandLineFlag&)> visitor);
|
||||
// Executes specified visitor for each non-retired flag in the registry. While
|
||||
// callback are executed, the registry is locked and can't be changed.
|
||||
void ForEachFlag(std::function<void(CommandLineFlag*)> visitor);
|
||||
void ForEachFlag(std::function<void(CommandLineFlag&)> visitor);
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
bool RegisterCommandLineFlag(CommandLineFlag*);
|
||||
bool RegisterCommandLineFlag(CommandLineFlag&);
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Retired registrations:
|
||||
|
|
@ -87,36 +82,6 @@ inline bool RetiredFlag(const char* flag_name) {
|
|||
return flags_internal::Retire(flag_name, base_internal::FastTypeId<T>());
|
||||
}
|
||||
|
||||
// If the flag is retired, returns true and indicates in |*type_is_bool|
|
||||
// whether the type of the retired flag is a bool.
|
||||
// Only to be called by code that needs to explicitly ignore retired flags.
|
||||
bool IsRetiredFlag(absl::string_view name, bool* type_is_bool);
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Saves the states (value, default value, whether the user has set
|
||||
// the flag, registered validators, etc) of all flags, and restores
|
||||
// them when the FlagSaver is destroyed.
|
||||
//
|
||||
// This class is thread-safe. However, its destructor writes to
|
||||
// exactly the set of flags that have changed value during its
|
||||
// lifetime, so concurrent _direct_ access to those flags
|
||||
// (i.e. FLAGS_foo instead of {Get,Set}CommandLineOption()) is unsafe.
|
||||
|
||||
class FlagSaver {
|
||||
public:
|
||||
FlagSaver();
|
||||
~FlagSaver();
|
||||
|
||||
FlagSaver(const FlagSaver&) = delete;
|
||||
void operator=(const FlagSaver&) = delete;
|
||||
|
||||
// Prevents saver from restoring the saved state of flags.
|
||||
void Ignore();
|
||||
|
||||
private:
|
||||
class FlagSaverImpl* impl_; // we use pimpl here to keep API steady
|
||||
};
|
||||
|
||||
} // namespace flags_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
|
|
|||
|
|
@ -1,86 +0,0 @@
|
|||
//
|
||||
// Copyright 2019 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/internal/type_erased.h"
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/raw_logging.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
||||
bool GetCommandLineOption(absl::string_view name, std::string* value) {
|
||||
if (name.empty()) return false;
|
||||
assert(value);
|
||||
|
||||
CommandLineFlag* flag = flags_internal::FindCommandLineFlag(name);
|
||||
if (flag == nullptr || flag->IsRetired()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
*value = flag->CurrentValue();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SetCommandLineOption(absl::string_view name, absl::string_view value) {
|
||||
return SetCommandLineOptionWithMode(name, value,
|
||||
flags_internal::SET_FLAGS_VALUE);
|
||||
}
|
||||
|
||||
bool SetCommandLineOptionWithMode(absl::string_view name,
|
||||
absl::string_view value,
|
||||
FlagSettingMode set_mode) {
|
||||
CommandLineFlag* flag = flags_internal::FindCommandLineFlag(name);
|
||||
|
||||
if (!flag || flag->IsRetired()) return false;
|
||||
|
||||
std::string error;
|
||||
if (!flags_internal::PrivateHandleAccessor::ParseFrom(
|
||||
flag, value, set_mode, kProgrammaticChange, &error)) {
|
||||
// Errors here are all of the form: the provided name was a recognized
|
||||
// flag, but the value was invalid (bad type, or validation failed).
|
||||
flags_internal::ReportUsageError(error, false);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
bool IsValidFlagValue(absl::string_view name, absl::string_view value) {
|
||||
CommandLineFlag* flag = flags_internal::FindCommandLineFlag(name);
|
||||
|
||||
return flag != nullptr &&
|
||||
(flag->IsRetired() ||
|
||||
flags_internal::PrivateHandleAccessor::ValidateInputValue(*flag,
|
||||
value));
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
} // namespace flags_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
|
@ -1,79 +0,0 @@
|
|||
//
|
||||
// Copyright 2019 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#ifndef ABSL_FLAGS_INTERNAL_TYPE_ERASED_H_
|
||||
#define ABSL_FLAGS_INTERNAL_TYPE_ERASED_H_
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
// Registry interfaces operating on type erased handles.
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
||||
// If a flag named "name" exists, store its current value in *OUTPUT
|
||||
// and return true. Else return false without changing *OUTPUT.
|
||||
// Thread-safe.
|
||||
bool GetCommandLineOption(absl::string_view name, std::string* value);
|
||||
|
||||
// Set the value of the flag named "name" to value. If successful,
|
||||
// returns true. If not successful (e.g., the flag was not found or
|
||||
// the value is not a valid value), returns false.
|
||||
// Thread-safe.
|
||||
bool SetCommandLineOption(absl::string_view name, absl::string_view value);
|
||||
|
||||
bool SetCommandLineOptionWithMode(absl::string_view name,
|
||||
absl::string_view value,
|
||||
FlagSettingMode set_mode);
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
// Returns true iff all of the following conditions are true:
|
||||
// (a) "name" names a registered flag
|
||||
// (b) "value" can be parsed succesfully according to the type of the flag
|
||||
// (c) parsed value passes any validator associated with the flag
|
||||
bool IsValidFlagValue(absl::string_view name, absl::string_view value);
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
// If a flag with specified "name" exists and has type T, store
|
||||
// its current value in *dst and return true. Else return false
|
||||
// without touching *dst. T must obey all of the requirements for
|
||||
// types passed to DEFINE_FLAG.
|
||||
template <typename T>
|
||||
inline bool GetByName(absl::string_view name, T* dst) {
|
||||
CommandLineFlag* flag = flags_internal::FindCommandLineFlag(name);
|
||||
if (!flag) return false;
|
||||
|
||||
if (auto val = flag->TryGet<T>()) {
|
||||
*dst = *val;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
} // namespace flags_internal
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#endif // ABSL_FLAGS_INTERNAL_TYPE_ERASED_H_
|
||||
|
|
@ -1,157 +0,0 @@
|
|||
//
|
||||
// Copyright 2019 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/internal/type_erased.h"
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/memory/memory.h"
|
||||
|
||||
ABSL_FLAG(int, int_flag, 1, "int_flag help");
|
||||
ABSL_FLAG(std::string, string_flag, "dflt", "string_flag help");
|
||||
ABSL_RETIRED_FLAG(bool, bool_retired_flag, false, "bool_retired_flag help");
|
||||
|
||||
namespace {
|
||||
|
||||
namespace flags = absl::flags_internal;
|
||||
|
||||
class TypeErasedTest : public testing::Test {
|
||||
protected:
|
||||
void SetUp() override { flag_saver_ = absl::make_unique<flags::FlagSaver>(); }
|
||||
void TearDown() override { flag_saver_.reset(); }
|
||||
|
||||
private:
|
||||
std::unique_ptr<flags::FlagSaver> flag_saver_;
|
||||
};
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestGetCommandLineOption) {
|
||||
std::string value;
|
||||
EXPECT_TRUE(flags::GetCommandLineOption("int_flag", &value));
|
||||
EXPECT_EQ(value, "1");
|
||||
|
||||
EXPECT_TRUE(flags::GetCommandLineOption("string_flag", &value));
|
||||
EXPECT_EQ(value, "dflt");
|
||||
|
||||
EXPECT_FALSE(flags::GetCommandLineOption("bool_retired_flag", &value));
|
||||
|
||||
EXPECT_FALSE(flags::GetCommandLineOption("unknown_flag", &value));
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestSetCommandLineOption) {
|
||||
EXPECT_TRUE(flags::SetCommandLineOption("int_flag", "101"));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 101);
|
||||
|
||||
EXPECT_TRUE(flags::SetCommandLineOption("string_flag", "asdfgh"));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "asdfgh");
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOption("bool_retired_flag", "true"));
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOption("unknown_flag", "true"));
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestSetCommandLineOptionWithMode_SET_FLAGS_VALUE) {
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "101",
|
||||
flags::SET_FLAGS_VALUE));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 101);
|
||||
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("string_flag", "asdfgh",
|
||||
flags::SET_FLAGS_VALUE));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "asdfgh");
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("bool_retired_flag", "true",
|
||||
flags::SET_FLAGS_VALUE));
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("unknown_flag", "true",
|
||||
flags::SET_FLAGS_VALUE));
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestSetCommandLineOptionWithMode_SET_FLAG_IF_DEFAULT) {
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "101",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 101);
|
||||
|
||||
// This semantic is broken. We return true instead of false. Value is not
|
||||
// updated.
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "202",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 101);
|
||||
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("string_flag", "asdfgh",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "asdfgh");
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("bool_retired_flag", "true",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("unknown_flag", "true",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestSetCommandLineOptionWithMode_SET_FLAGS_DEFAULT) {
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "101",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
|
||||
// Set it again to ensure that resetting logic is covered.
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "102",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "103",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("string_flag", "asdfgh",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_string_flag), "asdfgh");
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("bool_retired_flag", "true",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
|
||||
EXPECT_FALSE(flags::SetCommandLineOptionWithMode("unknown_flag", "true",
|
||||
flags::SET_FLAGS_DEFAULT));
|
||||
|
||||
// This should be successfull, since flag is still is not set
|
||||
EXPECT_TRUE(flags::SetCommandLineOptionWithMode("int_flag", "202",
|
||||
flags::SET_FLAG_IF_DEFAULT));
|
||||
EXPECT_EQ(absl::GetFlag(FLAGS_int_flag), 202);
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(TypeErasedTest, TestIsValidFlagValue) {
|
||||
EXPECT_TRUE(flags::IsValidFlagValue("int_flag", "57"));
|
||||
EXPECT_TRUE(flags::IsValidFlagValue("int_flag", "-101"));
|
||||
EXPECT_FALSE(flags::IsValidFlagValue("int_flag", "1.1"));
|
||||
|
||||
EXPECT_TRUE(flags::IsValidFlagValue("string_flag", "#%^#%^$%DGHDG$W%adsf"));
|
||||
|
||||
EXPECT_TRUE(flags::IsValidFlagValue("bool_retired_flag", "true"));
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
|
@ -15,6 +15,8 @@
|
|||
|
||||
#include "absl/flags/internal/usage.h"
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <ostream>
|
||||
|
|
@ -23,8 +25,8 @@
|
|||
#include <vector>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/internal/flag.h"
|
||||
#include "absl/flags/internal/path_util.h"
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
|
|
@ -107,8 +109,8 @@ class FlagHelpPrettyPrinter {
|
|||
public:
|
||||
// Pretty printer holds on to the std::ostream& reference to direct an output
|
||||
// to that stream.
|
||||
FlagHelpPrettyPrinter(int max_line_len, std::ostream* out)
|
||||
: out_(*out),
|
||||
FlagHelpPrettyPrinter(int max_line_len, std::ostream& out)
|
||||
: out_(out),
|
||||
max_line_len_(max_line_len),
|
||||
line_len_(0),
|
||||
first_line_(true) {}
|
||||
|
|
@ -182,8 +184,7 @@ class FlagHelpPrettyPrinter {
|
|||
bool first_line_;
|
||||
};
|
||||
|
||||
void FlagHelpHumanReadable(const flags_internal::CommandLineFlag& flag,
|
||||
std::ostream* out) {
|
||||
void FlagHelpHumanReadable(const CommandLineFlag& flag, std::ostream& out) {
|
||||
FlagHelpPrettyPrinter printer(80, out); // Max line length is 80.
|
||||
|
||||
// Flag name.
|
||||
|
|
@ -245,30 +246,28 @@ void FlagsHelpImpl(std::ostream& out, flags_internal::FlagKindFilter filter_cb,
|
|||
// This map is used to output matching flags grouped by package and file
|
||||
// name.
|
||||
std::map<std::string,
|
||||
std::map<std::string,
|
||||
std::vector<const flags_internal::CommandLineFlag*>>>
|
||||
std::map<std::string, std::vector<const absl::CommandLineFlag*>>>
|
||||
matching_flags;
|
||||
|
||||
flags_internal::ForEachFlag([&](flags_internal::CommandLineFlag* flag) {
|
||||
std::string flag_filename = flag->Filename();
|
||||
flags_internal::ForEachFlag([&](absl::CommandLineFlag& flag) {
|
||||
std::string flag_filename = flag.Filename();
|
||||
|
||||
// Ignore retired flags.
|
||||
if (flag->IsRetired()) return;
|
||||
if (flag.IsRetired()) return;
|
||||
|
||||
// If the flag has been stripped, pretend that it doesn't exist.
|
||||
if (flag->Help() == flags_internal::kStrippedFlagHelp) return;
|
||||
if (flag.Help() == flags_internal::kStrippedFlagHelp) return;
|
||||
|
||||
// Make sure flag satisfies the filter
|
||||
if (!filter_cb || !filter_cb(flag_filename)) return;
|
||||
|
||||
matching_flags[std::string(flags_internal::Package(flag_filename))]
|
||||
[flag_filename]
|
||||
.push_back(flag);
|
||||
.push_back(&flag);
|
||||
});
|
||||
|
||||
absl::string_view
|
||||
package_separator; // controls blank lines between packages.
|
||||
absl::string_view file_separator; // controls blank lines between files.
|
||||
absl::string_view package_separator; // controls blank lines between packages
|
||||
absl::string_view file_separator; // controls blank lines between files
|
||||
for (const auto& package : matching_flags) {
|
||||
if (format == HelpFormat::kHumanReadable) {
|
||||
out << package_separator;
|
||||
|
|
@ -303,10 +302,10 @@ void FlagsHelpImpl(std::ostream& out, flags_internal::FlagKindFilter filter_cb,
|
|||
|
||||
// --------------------------------------------------------------------
|
||||
// Produces the help message describing specific flag.
|
||||
void FlagHelp(std::ostream& out, const flags_internal::CommandLineFlag& flag,
|
||||
void FlagHelp(std::ostream& out, const CommandLineFlag& flag,
|
||||
HelpFormat format) {
|
||||
if (format == HelpFormat::kHumanReadable)
|
||||
flags_internal::FlagHelpHumanReadable(flag, &out);
|
||||
flags_internal::FlagHelpHumanReadable(flag, out);
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
|
|
|||
|
|
@ -20,8 +20,8 @@
|
|||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
|
@ -37,7 +37,7 @@ enum class HelpFormat {
|
|||
};
|
||||
|
||||
// Outputs the help message describing specific flag.
|
||||
void FlagHelp(std::ostream& out, const flags_internal::CommandLineFlag& flag,
|
||||
void FlagHelp(std::ostream& out, const CommandLineFlag& flag,
|
||||
HelpFormat format = HelpFormat::kHumanReadable);
|
||||
|
||||
// Produces the help messages for all flags matching the filter. A flag matches
|
||||
|
|
|
|||
|
|
@ -21,15 +21,13 @@
|
|||
#include <string>
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/parse.h"
|
||||
#include "absl/flags/internal/path_util.h"
|
||||
#include "absl/flags/internal/program_name.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
#include "absl/flags/usage.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/memory/memory.h"
|
||||
#include "absl/strings/match.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
|
||||
|
|
@ -91,7 +89,7 @@ class UsageReportingTest : public testing::Test {
|
|||
}
|
||||
|
||||
private:
|
||||
flags::FlagSaver flag_saver_;
|
||||
absl::FlagSaver flag_saver_;
|
||||
};
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
|
@ -112,7 +110,7 @@ TEST_F(UsageReportingDeathTest, TestSetProgramUsageMessage) {
|
|||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_01) {
|
||||
const auto* flag = flags::FindCommandLineFlag("usage_reporting_test_flag_01");
|
||||
const auto* flag = absl::FindCommandLineFlag("usage_reporting_test_flag_01");
|
||||
std::stringstream test_buf;
|
||||
|
||||
flags::FlagHelp(test_buf, *flag, flags::HelpFormat::kHumanReadable);
|
||||
|
|
@ -124,7 +122,7 @@ TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_01) {
|
|||
}
|
||||
|
||||
TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_02) {
|
||||
const auto* flag = flags::FindCommandLineFlag("usage_reporting_test_flag_02");
|
||||
const auto* flag = absl::FindCommandLineFlag("usage_reporting_test_flag_02");
|
||||
std::stringstream test_buf;
|
||||
|
||||
flags::FlagHelp(test_buf, *flag, flags::HelpFormat::kHumanReadable);
|
||||
|
|
@ -136,7 +134,7 @@ TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_02) {
|
|||
}
|
||||
|
||||
TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_03) {
|
||||
const auto* flag = flags::FindCommandLineFlag("usage_reporting_test_flag_03");
|
||||
const auto* flag = absl::FindCommandLineFlag("usage_reporting_test_flag_03");
|
||||
std::stringstream test_buf;
|
||||
|
||||
flags::FlagHelp(test_buf, *flag, flags::HelpFormat::kHumanReadable);
|
||||
|
|
@ -148,7 +146,7 @@ TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_03) {
|
|||
}
|
||||
|
||||
TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_04) {
|
||||
const auto* flag = flags::FindCommandLineFlag("usage_reporting_test_flag_04");
|
||||
const auto* flag = absl::FindCommandLineFlag("usage_reporting_test_flag_04");
|
||||
std::stringstream test_buf;
|
||||
|
||||
flags::FlagHelp(test_buf, *flag, flags::HelpFormat::kHumanReadable);
|
||||
|
|
@ -160,7 +158,7 @@ TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_04) {
|
|||
}
|
||||
|
||||
TEST_F(UsageReportingTest, TestFlagHelpHRF_on_flag_05) {
|
||||
const auto* flag = flags::FindCommandLineFlag("usage_reporting_test_flag_05");
|
||||
const auto* flag = absl::FindCommandLineFlag("usage_reporting_test_flag_05");
|
||||
std::stringstream test_buf;
|
||||
|
||||
flags::FlagHelp(test_buf, *flag, flags::HelpFormat::kHumanReadable);
|
||||
|
|
|
|||
21
third_party/abseil_cpp/absl/flags/marshalling.cc
vendored
21
third_party/abseil_cpp/absl/flags/marshalling.cc
vendored
|
|
@ -74,15 +74,16 @@ static int NumericBase(absl::string_view text) {
|
|||
}
|
||||
|
||||
template <typename IntType>
|
||||
inline bool ParseFlagImpl(absl::string_view text, IntType* dst) {
|
||||
inline bool ParseFlagImpl(absl::string_view text, IntType& dst) {
|
||||
text = absl::StripAsciiWhitespace(text);
|
||||
|
||||
return absl::numbers_internal::safe_strtoi_base(text, dst, NumericBase(text));
|
||||
return absl::numbers_internal::safe_strtoi_base(text, &dst,
|
||||
NumericBase(text));
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, short* dst, std::string*) {
|
||||
int val;
|
||||
if (!ParseFlagImpl(text, &val)) return false;
|
||||
if (!ParseFlagImpl(text, val)) return false;
|
||||
if (static_cast<short>(val) != val) // worked, but number out of range
|
||||
return false;
|
||||
*dst = static_cast<short>(val);
|
||||
|
|
@ -91,7 +92,7 @@ bool AbslParseFlag(absl::string_view text, short* dst, std::string*) {
|
|||
|
||||
bool AbslParseFlag(absl::string_view text, unsigned short* dst, std::string*) {
|
||||
unsigned int val;
|
||||
if (!ParseFlagImpl(text, &val)) return false;
|
||||
if (!ParseFlagImpl(text, val)) return false;
|
||||
if (static_cast<unsigned short>(val) !=
|
||||
val) // worked, but number out of range
|
||||
return false;
|
||||
|
|
@ -100,28 +101,28 @@ bool AbslParseFlag(absl::string_view text, unsigned short* dst, std::string*) {
|
|||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, int* dst, std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, unsigned int* dst, std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, long* dst, std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, unsigned long* dst, std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, long long* dst, std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
bool AbslParseFlag(absl::string_view text, unsigned long long* dst,
|
||||
std::string*) {
|
||||
return ParseFlagImpl(text, dst);
|
||||
return ParseFlagImpl(text, *dst);
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
|
|
|||
45
third_party/abseil_cpp/absl/flags/parse.cc
vendored
45
third_party/abseil_cpp/absl/flags/parse.cc
vendored
|
|
@ -34,6 +34,7 @@
|
|||
#include "absl/base/config.h"
|
||||
#include "absl/base/const_init.h"
|
||||
#include "absl/base/thread_annotations.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/config.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
|
|
@ -41,8 +42,8 @@
|
|||
#include "absl/flags/internal/parse.h"
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
#include "absl/flags/internal/program_name.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/internal/usage.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
#include "absl/flags/usage.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/strings/ascii.h"
|
||||
|
|
@ -222,7 +223,7 @@ bool ArgsList::ReadFromFlagfile(const std::string& flag_file_name) {
|
|||
// Reads the environment variable with name `name` and stores results in
|
||||
// `value`. If variable is not present in environment returns false, otherwise
|
||||
// returns true.
|
||||
bool GetEnvVar(const char* var_name, std::string* var_value) {
|
||||
bool GetEnvVar(const char* var_name, std::string& var_value) {
|
||||
#ifdef _WIN32
|
||||
char buf[1024];
|
||||
auto get_res = GetEnvironmentVariableA(var_name, buf, sizeof(buf));
|
||||
|
|
@ -234,14 +235,14 @@ bool GetEnvVar(const char* var_name, std::string* var_value) {
|
|||
return false;
|
||||
}
|
||||
|
||||
*var_value = std::string(buf, get_res);
|
||||
var_value = std::string(buf, get_res);
|
||||
#else
|
||||
const char* val = ::getenv(var_name);
|
||||
if (val == nullptr) {
|
||||
return false;
|
||||
}
|
||||
|
||||
*var_value = val;
|
||||
var_value = val;
|
||||
#endif
|
||||
|
||||
return true;
|
||||
|
|
@ -289,11 +290,11 @@ std::tuple<absl::string_view, absl::string_view, bool> SplitNameAndValue(
|
|||
// found flag or nullptr
|
||||
// is negative in case of --nofoo
|
||||
std::tuple<CommandLineFlag*, bool> LocateFlag(absl::string_view flag_name) {
|
||||
CommandLineFlag* flag = flags_internal::FindCommandLineFlag(flag_name);
|
||||
CommandLineFlag* flag = absl::FindCommandLineFlag(flag_name);
|
||||
bool is_negative = false;
|
||||
|
||||
if (!flag && absl::ConsumePrefix(&flag_name, "no")) {
|
||||
flag = flags_internal::FindCommandLineFlag(flag_name);
|
||||
flag = absl::FindCommandLineFlag(flag_name);
|
||||
is_negative = true;
|
||||
}
|
||||
|
||||
|
|
@ -306,17 +307,17 @@ std::tuple<CommandLineFlag*, bool> LocateFlag(absl::string_view flag_name) {
|
|||
// back.
|
||||
void CheckDefaultValuesParsingRoundtrip() {
|
||||
#ifndef NDEBUG
|
||||
flags_internal::ForEachFlag([&](CommandLineFlag* flag) {
|
||||
if (flag->IsRetired()) return;
|
||||
flags_internal::ForEachFlag([&](CommandLineFlag& flag) {
|
||||
if (flag.IsRetired()) return;
|
||||
|
||||
#define ABSL_FLAGS_INTERNAL_IGNORE_TYPE(T, _) \
|
||||
if (flag->IsOfType<T>()) return;
|
||||
if (flag.IsOfType<T>()) return;
|
||||
|
||||
ABSL_FLAGS_INTERNAL_SUPPORTED_TYPES(ABSL_FLAGS_INTERNAL_IGNORE_TYPE)
|
||||
#undef ABSL_FLAGS_INTERNAL_IGNORE_TYPE
|
||||
|
||||
flags_internal::PrivateHandleAccessor::CheckDefaultValueParsingRoundtrip(
|
||||
*flag);
|
||||
flag);
|
||||
});
|
||||
#endif
|
||||
}
|
||||
|
|
@ -329,13 +330,13 @@ void CheckDefaultValuesParsingRoundtrip() {
|
|||
// the first flagfile in the input list are processed before the second flagfile
|
||||
// etc.
|
||||
bool ReadFlagfiles(const std::vector<std::string>& flagfiles,
|
||||
std::vector<ArgsList>* input_args) {
|
||||
std::vector<ArgsList>& input_args) {
|
||||
bool success = true;
|
||||
for (auto it = flagfiles.rbegin(); it != flagfiles.rend(); ++it) {
|
||||
ArgsList al;
|
||||
|
||||
if (al.ReadFromFlagfile(*it)) {
|
||||
input_args->push_back(al);
|
||||
input_args.push_back(al);
|
||||
} else {
|
||||
success = false;
|
||||
}
|
||||
|
|
@ -350,7 +351,7 @@ bool ReadFlagfiles(const std::vector<std::string>& flagfiles,
|
|||
// `flag_name` is a string from the input flag_names list. If successful we
|
||||
// append a single ArgList at the end of the input_args.
|
||||
bool ReadFlagsFromEnv(const std::vector<std::string>& flag_names,
|
||||
std::vector<ArgsList>* input_args,
|
||||
std::vector<ArgsList>& input_args,
|
||||
bool fail_on_absent_in_env) {
|
||||
bool success = true;
|
||||
std::vector<std::string> args;
|
||||
|
|
@ -371,7 +372,7 @@ bool ReadFlagsFromEnv(const std::vector<std::string>& flag_names,
|
|||
|
||||
const std::string envname = absl::StrCat("FLAGS_", flag_name);
|
||||
std::string envval;
|
||||
if (!GetEnvVar(envname.c_str(), &envval)) {
|
||||
if (!GetEnvVar(envname.c_str(), envval)) {
|
||||
if (fail_on_absent_in_env) {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat(envname, " not found in environment"), true);
|
||||
|
|
@ -386,7 +387,7 @@ bool ReadFlagsFromEnv(const std::vector<std::string>& flag_names,
|
|||
}
|
||||
|
||||
if (success) {
|
||||
input_args->emplace_back(args);
|
||||
input_args.emplace_back(args);
|
||||
}
|
||||
|
||||
return success;
|
||||
|
|
@ -396,8 +397,8 @@ bool ReadFlagsFromEnv(const std::vector<std::string>& flag_names,
|
|||
|
||||
// Returns success status, which is true if were able to handle all generator
|
||||
// flags (flagfile, fromenv, tryfromemv) successfully.
|
||||
bool HandleGeneratorFlags(std::vector<ArgsList>* input_args,
|
||||
std::vector<std::string>* flagfile_value) {
|
||||
bool HandleGeneratorFlags(std::vector<ArgsList>& input_args,
|
||||
std::vector<std::string>& flagfile_value) {
|
||||
bool success = true;
|
||||
|
||||
absl::MutexLock l(&flags_internal::processing_checks_guard);
|
||||
|
|
@ -422,9 +423,9 @@ bool HandleGeneratorFlags(std::vector<ArgsList>* input_args,
|
|||
if (flags_internal::flagfile_needs_processing) {
|
||||
auto flagfiles = absl::GetFlag(FLAGS_flagfile);
|
||||
|
||||
if (input_args->size() == 1) {
|
||||
flagfile_value->insert(flagfile_value->end(), flagfiles.begin(),
|
||||
flagfiles.end());
|
||||
if (input_args.size() == 1) {
|
||||
flagfile_value.insert(flagfile_value.end(), flagfiles.begin(),
|
||||
flagfiles.end());
|
||||
}
|
||||
|
||||
success &= ReadFlagfiles(flagfiles, input_args);
|
||||
|
|
@ -647,7 +648,7 @@ std::vector<char*> ParseCommandLineImpl(int argc, char* argv[],
|
|||
bool success = true;
|
||||
while (!input_args.empty()) {
|
||||
// 10. First we process the built-in generator flags.
|
||||
success &= HandleGeneratorFlags(&input_args, &flagfile_value);
|
||||
success &= HandleGeneratorFlags(input_args, flagfile_value);
|
||||
|
||||
// 30. Select top-most (most recent) arguments list. If it is empty drop it
|
||||
// and re-try.
|
||||
|
|
@ -733,7 +734,7 @@ std::vector<char*> ParseCommandLineImpl(int argc, char* argv[],
|
|||
|
||||
std::string error;
|
||||
if (!flags_internal::PrivateHandleAccessor::ParseFrom(
|
||||
flag, value, SET_FLAGS_VALUE, kCommandLine, &error)) {
|
||||
*flag, value, SET_FLAGS_VALUE, kCommandLine, error)) {
|
||||
flags_internal::ReportUsageError(error, true);
|
||||
success = false;
|
||||
} else {
|
||||
|
|
|
|||
1
third_party/abseil_cpp/absl/flags/parse.h
vendored
1
third_party/abseil_cpp/absl/flags/parse.h
vendored
|
|
@ -23,7 +23,6 @@
|
|||
#ifndef ABSL_FLAGS_PARSE_H_
|
||||
#define ABSL_FLAGS_PARSE_H_
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
|
|
|
|||
34
third_party/abseil_cpp/absl/flags/parse_test.cc
vendored
34
third_party/abseil_cpp/absl/flags/parse_test.cc
vendored
|
|
@ -28,7 +28,7 @@
|
|||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/parse.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
#include "absl/strings/str_cat.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/strings/substitute.h"
|
||||
|
|
@ -171,8 +171,8 @@ constexpr const char* const ff2_data[] = {
|
|||
// temporary directory location. This way we can test inclusion of one flagfile
|
||||
// from another flagfile.
|
||||
const char* GetFlagfileFlag(const std::vector<FlagfileData>& ffd,
|
||||
std::string* flagfile_flag) {
|
||||
*flagfile_flag = "--flagfile=";
|
||||
std::string& flagfile_flag) {
|
||||
flagfile_flag = "--flagfile=";
|
||||
absl::string_view separator;
|
||||
for (const auto& flagfile_data : ffd) {
|
||||
std::string flagfile_name =
|
||||
|
|
@ -183,11 +183,11 @@ const char* GetFlagfileFlag(const std::vector<FlagfileData>& ffd,
|
|||
flagfile_out << absl::Substitute(line, GetTestTempDir()) << "\n";
|
||||
}
|
||||
|
||||
absl::StrAppend(flagfile_flag, separator, flagfile_name);
|
||||
absl::StrAppend(&flagfile_flag, separator, flagfile_name);
|
||||
separator = ",";
|
||||
}
|
||||
|
||||
return flagfile_flag->c_str();
|
||||
return flagfile_flag.c_str();
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
|
@ -208,7 +208,7 @@ using testing::ElementsAreArray;
|
|||
|
||||
class ParseTest : public testing::Test {
|
||||
private:
|
||||
flags::FlagSaver flag_saver_;
|
||||
absl::FlagSaver flag_saver_;
|
||||
};
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
|
@ -588,14 +588,14 @@ TEST_F(ParseTest, TestSimpleValidFlagfile) {
|
|||
const char* in_args1[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff1", absl::MakeConstSpan(ff1_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
TestParse(in_args1, -1, 0.1, "q2w2 ", true);
|
||||
|
||||
const char* in_args2[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff2", absl::MakeConstSpan(ff2_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
TestParse(in_args2, 100, 0.1, "q2w2 ", false);
|
||||
}
|
||||
|
|
@ -609,7 +609,7 @@ TEST_F(ParseTest, TestValidMultiFlagfile) {
|
|||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff2", absl::MakeConstSpan(ff2_data)},
|
||||
{"parse_test.ff1", absl::MakeConstSpan(ff1_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
TestParse(in_args1, -1, 0.1, "q2w2 ", true);
|
||||
}
|
||||
|
|
@ -622,7 +622,7 @@ TEST_F(ParseTest, TestFlagfileMixedWithRegularFlags) {
|
|||
const char* in_args1[] = {
|
||||
"testbin", "--int_flag=3",
|
||||
GetFlagfileFlag({{"parse_test.ff1", absl::MakeConstSpan(ff1_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
"-double_flag=0.2"};
|
||||
TestParse(in_args1, -1, 0.2, "q2w2 ", true);
|
||||
}
|
||||
|
|
@ -637,10 +637,14 @@ TEST_F(ParseTest, TestFlagfileInFlagfile) {
|
|||
"--flagfile=$0/parse_test.ff2",
|
||||
};
|
||||
|
||||
GetFlagfileFlag({{"parse_test.ff2", absl::MakeConstSpan(ff2_data)},
|
||||
{"parse_test.ff1", absl::MakeConstSpan(ff1_data)}},
|
||||
flagfile_flag);
|
||||
|
||||
const char* in_args1[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff3", absl::MakeConstSpan(ff3_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
TestParse(in_args1, 100, 0.1, "q2w2 ", false);
|
||||
}
|
||||
|
|
@ -657,7 +661,7 @@ TEST_F(ParseDeathTest, TestInvalidFlagfiles) {
|
|||
const char* in_args1[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff4",
|
||||
absl::MakeConstSpan(ff4_data)}}, &flagfile_flag),
|
||||
absl::MakeConstSpan(ff4_data)}}, flagfile_flag),
|
||||
};
|
||||
EXPECT_DEATH_IF_SUPPORTED(InvokeParse(in_args1),
|
||||
"Unknown command line flag 'unknown_flag'");
|
||||
|
|
@ -669,7 +673,7 @@ TEST_F(ParseDeathTest, TestInvalidFlagfiles) {
|
|||
const char* in_args2[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff5",
|
||||
absl::MakeConstSpan(ff5_data)}}, &flagfile_flag),
|
||||
absl::MakeConstSpan(ff5_data)}}, flagfile_flag),
|
||||
};
|
||||
EXPECT_DEATH_IF_SUPPORTED(InvokeParse(in_args2),
|
||||
"Unknown command line flag 'int_flag 10'");
|
||||
|
|
@ -681,7 +685,7 @@ TEST_F(ParseDeathTest, TestInvalidFlagfiles) {
|
|||
const char* in_args3[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff6", absl::MakeConstSpan(ff6_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
EXPECT_DEATH_IF_SUPPORTED(InvokeParse(in_args3),
|
||||
"Flagfile can't contain position arguments or --");
|
||||
|
|
@ -702,7 +706,7 @@ TEST_F(ParseDeathTest, TestInvalidFlagfiles) {
|
|||
const char* in_args5[] = {
|
||||
"testbin",
|
||||
GetFlagfileFlag({{"parse_test.ff7", absl::MakeConstSpan(ff7_data)}},
|
||||
&flagfile_flag),
|
||||
flagfile_flag),
|
||||
};
|
||||
EXPECT_DEATH_IF_SUPPORTED(InvokeParse(in_args5),
|
||||
"Unexpected line in the flagfile .*: \\*bin\\*");
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
//
|
||||
// Copyright 2019 The Abseil Authors.
|
||||
// Copyright 2020 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
|
@ -13,46 +13,34 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/reflection.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/base/internal/raw_logging.h"
|
||||
#include "absl/base/thread_annotations.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/internal/private_handle_accessor.h"
|
||||
#include "absl/flags/internal/registry.h"
|
||||
#include "absl/flags/usage_config.h"
|
||||
#include "absl/strings/str_cat.h"
|
||||
#include "absl/strings/string_view.h"
|
||||
#include "absl/synchronization/mutex.h"
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
// FlagRegistry implementation
|
||||
// A FlagRegistry holds all flag objects indexed
|
||||
// by their names so that if you know a flag's name you can access or
|
||||
// set it.
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
// FlagRegistry
|
||||
// A FlagRegistry singleton object holds all flag objects indexed
|
||||
// by their names so that if you know a flag's name (as a C
|
||||
// string), you can access or set it. If the function is named
|
||||
// FooLocked(), you must own the registry lock before calling
|
||||
// the function; otherwise, you should *not* hold the lock, and
|
||||
// the function will acquire it itself if needed.
|
||||
// A FlagRegistry singleton object holds all flag objects indexed by their
|
||||
// names so that if you know a flag's name, you can access or set it. If the
|
||||
// function is named FooLocked(), you must own the registry lock before
|
||||
// calling the function; otherwise, you should *not* hold the lock, and the
|
||||
// function will acquire it itself if needed.
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
class FlagRegistry {
|
||||
|
|
@ -60,8 +48,8 @@ class FlagRegistry {
|
|||
FlagRegistry() = default;
|
||||
~FlagRegistry() = default;
|
||||
|
||||
// Store a flag in this registry. Takes ownership of *flag.
|
||||
void RegisterFlag(CommandLineFlag* flag);
|
||||
// Store a flag in this registry. Takes ownership of *flag.
|
||||
void RegisterFlag(CommandLineFlag& flag);
|
||||
|
||||
void Lock() ABSL_EXCLUSIVE_LOCK_FUNCTION(lock_) { lock_.Lock(); }
|
||||
void Unlock() ABSL_UNLOCK_FUNCTION(lock_) { lock_.Unlock(); }
|
||||
|
|
@ -74,12 +62,13 @@ class FlagRegistry {
|
|||
// found or not retired. Does not emit a warning.
|
||||
CommandLineFlag* FindRetiredFlagLocked(absl::string_view name);
|
||||
|
||||
static FlagRegistry* GlobalRegistry(); // returns a singleton registry
|
||||
static FlagRegistry& GlobalRegistry(); // returns a singleton registry
|
||||
|
||||
private:
|
||||
friend class FlagSaverImpl; // reads all the flags in order to copy them
|
||||
friend class flags_internal::FlagSaverImpl; // reads all the flags in order
|
||||
// to copy them
|
||||
friend void ForEachFlagUnlocked(
|
||||
std::function<void(CommandLineFlag*)> visitor);
|
||||
std::function<void(CommandLineFlag&)> visitor);
|
||||
|
||||
// The map from name to flag, for FindFlagLocked().
|
||||
using FlagMap = std::map<absl::string_view, CommandLineFlag*>;
|
||||
|
|
@ -94,74 +83,6 @@ class FlagRegistry {
|
|||
FlagRegistry& operator=(const FlagRegistry&);
|
||||
};
|
||||
|
||||
FlagRegistry* FlagRegistry::GlobalRegistry() {
|
||||
static FlagRegistry* global_registry = new FlagRegistry;
|
||||
return global_registry;
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
class FlagRegistryLock {
|
||||
public:
|
||||
explicit FlagRegistryLock(FlagRegistry* fr) : fr_(fr) { fr_->Lock(); }
|
||||
~FlagRegistryLock() { fr_->Unlock(); }
|
||||
|
||||
private:
|
||||
FlagRegistry* const fr_;
|
||||
};
|
||||
|
||||
void DestroyRetiredFlag(CommandLineFlag* flag);
|
||||
} // namespace
|
||||
|
||||
void FlagRegistry::RegisterFlag(CommandLineFlag* flag) {
|
||||
FlagRegistryLock registry_lock(this);
|
||||
std::pair<FlagIterator, bool> ins =
|
||||
flags_.insert(FlagMap::value_type(flag->Name(), flag));
|
||||
if (ins.second == false) { // means the name was already in the map
|
||||
CommandLineFlag* old_flag = ins.first->second;
|
||||
if (flag->IsRetired() != old_flag->IsRetired()) {
|
||||
// All registrations must agree on the 'retired' flag.
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat(
|
||||
"Retired flag '", flag->Name(),
|
||||
"' was defined normally in file '",
|
||||
(flag->IsRetired() ? old_flag->Filename() : flag->Filename()),
|
||||
"'."),
|
||||
true);
|
||||
} else if (flags_internal::PrivateHandleAccessor::TypeId(*flag) !=
|
||||
flags_internal::PrivateHandleAccessor::TypeId(*old_flag)) {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat("Flag '", flag->Name(),
|
||||
"' was defined more than once but with "
|
||||
"differing types. Defined in files '",
|
||||
old_flag->Filename(), "' and '", flag->Filename(), "'."),
|
||||
true);
|
||||
} else if (old_flag->IsRetired()) {
|
||||
// Retired flag can just be deleted.
|
||||
DestroyRetiredFlag(flag);
|
||||
return;
|
||||
} else if (old_flag->Filename() != flag->Filename()) {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat("Flag '", flag->Name(),
|
||||
"' was defined more than once (in files '",
|
||||
old_flag->Filename(), "' and '", flag->Filename(),
|
||||
"')."),
|
||||
true);
|
||||
} else {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat(
|
||||
"Something wrong with flag '", flag->Name(), "' in file '",
|
||||
flag->Filename(), "'. One possibility: file '", flag->Filename(),
|
||||
"' is being linked both statically and dynamically into this "
|
||||
"executable. e.g. some files listed as srcs to a test and also "
|
||||
"listed as srcs of some shared lib deps of the same test."),
|
||||
true);
|
||||
}
|
||||
// All cases above are fatal, except for the retired flags.
|
||||
std::exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
CommandLineFlag* FlagRegistry::FindFlagLocked(absl::string_view name) {
|
||||
FlagConstIterator i = flags_.find(name);
|
||||
if (i == flags_.end()) {
|
||||
|
|
@ -185,97 +106,92 @@ CommandLineFlag* FlagRegistry::FindRetiredFlagLocked(absl::string_view name) {
|
|||
return i->second;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
// FlagSaver
|
||||
// FlagSaverImpl
|
||||
// This class stores the states of all flags at construct time,
|
||||
// and restores all flags to that state at destruct time.
|
||||
// Its major implementation challenge is that it never modifies
|
||||
// pointers in the 'main' registry, so global FLAG_* vars always
|
||||
// point to the right place.
|
||||
// --------------------------------------------------------------------
|
||||
namespace {
|
||||
|
||||
class FlagSaverImpl {
|
||||
class FlagRegistryLock {
|
||||
public:
|
||||
FlagSaverImpl() = default;
|
||||
FlagSaverImpl(const FlagSaverImpl&) = delete;
|
||||
void operator=(const FlagSaverImpl&) = delete;
|
||||
|
||||
// Saves the flag states from the flag registry into this object.
|
||||
// It's an error to call this more than once.
|
||||
void SaveFromRegistry() {
|
||||
assert(backup_registry_.empty()); // call only once!
|
||||
flags_internal::ForEachFlag([&](flags_internal::CommandLineFlag* flag) {
|
||||
if (auto flag_state =
|
||||
flags_internal::PrivateHandleAccessor::SaveState(flag)) {
|
||||
backup_registry_.emplace_back(std::move(flag_state));
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// Restores the saved flag states into the flag registry.
|
||||
void RestoreToRegistry() {
|
||||
for (const auto& flag_state : backup_registry_) {
|
||||
flag_state->Restore();
|
||||
}
|
||||
}
|
||||
explicit FlagRegistryLock(FlagRegistry& fr) : fr_(fr) { fr_.Lock(); }
|
||||
~FlagRegistryLock() { fr_.Unlock(); }
|
||||
|
||||
private:
|
||||
std::vector<std::unique_ptr<flags_internal::FlagStateInterface>>
|
||||
backup_registry_;
|
||||
FlagRegistry& fr_;
|
||||
};
|
||||
|
||||
FlagSaver::FlagSaver() : impl_(new FlagSaverImpl) { impl_->SaveFromRegistry(); }
|
||||
void DestroyRetiredFlag(CommandLineFlag& flag);
|
||||
|
||||
void FlagSaver::Ignore() {
|
||||
delete impl_;
|
||||
impl_ = nullptr;
|
||||
}
|
||||
} // namespace
|
||||
|
||||
FlagSaver::~FlagSaver() {
|
||||
if (!impl_) return;
|
||||
|
||||
impl_->RestoreToRegistry();
|
||||
delete impl_;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
CommandLineFlag* FindCommandLineFlag(absl::string_view name) {
|
||||
if (name.empty()) return nullptr;
|
||||
FlagRegistry* const registry = FlagRegistry::GlobalRegistry();
|
||||
FlagRegistryLock frl(registry);
|
||||
|
||||
return registry->FindFlagLocked(name);
|
||||
}
|
||||
|
||||
CommandLineFlag* FindRetiredFlag(absl::string_view name) {
|
||||
FlagRegistry* const registry = FlagRegistry::GlobalRegistry();
|
||||
FlagRegistryLock frl(registry);
|
||||
|
||||
return registry->FindRetiredFlagLocked(name);
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
void ForEachFlagUnlocked(std::function<void(CommandLineFlag*)> visitor) {
|
||||
FlagRegistry* const registry = FlagRegistry::GlobalRegistry();
|
||||
for (FlagRegistry::FlagConstIterator i = registry->flags_.begin();
|
||||
i != registry->flags_.end(); ++i) {
|
||||
visitor(i->second);
|
||||
void FlagRegistry::RegisterFlag(CommandLineFlag& flag) {
|
||||
FlagRegistryLock registry_lock(*this);
|
||||
std::pair<FlagIterator, bool> ins =
|
||||
flags_.insert(FlagMap::value_type(flag.Name(), &flag));
|
||||
if (ins.second == false) { // means the name was already in the map
|
||||
CommandLineFlag& old_flag = *ins.first->second;
|
||||
if (flag.IsRetired() != old_flag.IsRetired()) {
|
||||
// All registrations must agree on the 'retired' flag.
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat(
|
||||
"Retired flag '", flag.Name(), "' was defined normally in file '",
|
||||
(flag.IsRetired() ? old_flag.Filename() : flag.Filename()), "'."),
|
||||
true);
|
||||
} else if (flags_internal::PrivateHandleAccessor::TypeId(flag) !=
|
||||
flags_internal::PrivateHandleAccessor::TypeId(old_flag)) {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat("Flag '", flag.Name(),
|
||||
"' was defined more than once but with "
|
||||
"differing types. Defined in files '",
|
||||
old_flag.Filename(), "' and '", flag.Filename(), "'."),
|
||||
true);
|
||||
} else if (old_flag.IsRetired()) {
|
||||
// Retired flag can just be deleted.
|
||||
DestroyRetiredFlag(flag);
|
||||
return;
|
||||
} else if (old_flag.Filename() != flag.Filename()) {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat("Flag '", flag.Name(),
|
||||
"' was defined more than once (in files '",
|
||||
old_flag.Filename(), "' and '", flag.Filename(), "')."),
|
||||
true);
|
||||
} else {
|
||||
flags_internal::ReportUsageError(
|
||||
absl::StrCat(
|
||||
"Something wrong with flag '", flag.Name(), "' in file '",
|
||||
flag.Filename(), "'. One possibility: file '", flag.Filename(),
|
||||
"' is being linked both statically and dynamically into this "
|
||||
"executable. e.g. some files listed as srcs to a test and also "
|
||||
"listed as srcs of some shared lib deps of the same test."),
|
||||
true);
|
||||
}
|
||||
// All cases above are fatal, except for the retired flags.
|
||||
std::exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
void ForEachFlag(std::function<void(CommandLineFlag*)> visitor) {
|
||||
FlagRegistry* const registry = FlagRegistry::GlobalRegistry();
|
||||
FlagRegistry& FlagRegistry::GlobalRegistry() {
|
||||
static FlagRegistry* global_registry = new FlagRegistry;
|
||||
return *global_registry;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
void ForEachFlagUnlocked(std::function<void(CommandLineFlag&)> visitor) {
|
||||
FlagRegistry& registry = FlagRegistry::GlobalRegistry();
|
||||
for (FlagRegistry::FlagConstIterator i = registry.flags_.begin();
|
||||
i != registry.flags_.end(); ++i) {
|
||||
visitor(*i->second);
|
||||
}
|
||||
}
|
||||
|
||||
void ForEachFlag(std::function<void(CommandLineFlag&)> visitor) {
|
||||
FlagRegistry& registry = FlagRegistry::GlobalRegistry();
|
||||
FlagRegistryLock frl(registry);
|
||||
ForEachFlagUnlocked(visitor);
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
bool RegisterCommandLineFlag(CommandLineFlag* flag) {
|
||||
FlagRegistry::GlobalRegistry()->RegisterFlag(flag);
|
||||
bool RegisterCommandLineFlag(CommandLineFlag& flag) {
|
||||
FlagRegistry::GlobalRegistry().RegisterFlag(flag);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -283,7 +199,7 @@ bool RegisterCommandLineFlag(CommandLineFlag* flag) {
|
|||
|
||||
namespace {
|
||||
|
||||
class RetiredFlagObj final : public flags_internal::CommandLineFlag {
|
||||
class RetiredFlagObj final : public CommandLineFlag {
|
||||
public:
|
||||
constexpr RetiredFlagObj(const char* name, FlagFastTypeId type_id)
|
||||
: name_(name), type_id_(type_id) {}
|
||||
|
|
@ -306,7 +222,7 @@ class RetiredFlagObj final : public flags_internal::CommandLineFlag {
|
|||
}
|
||||
|
||||
bool ParseFrom(absl::string_view, flags_internal::FlagSettingMode,
|
||||
flags_internal::ValueSource, std::string*) override {
|
||||
flags_internal::ValueSource, std::string&) override {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
@ -319,32 +235,74 @@ class RetiredFlagObj final : public flags_internal::CommandLineFlag {
|
|||
const FlagFastTypeId type_id_;
|
||||
};
|
||||
|
||||
void DestroyRetiredFlag(flags_internal::CommandLineFlag* flag) {
|
||||
assert(flag->IsRetired());
|
||||
delete static_cast<RetiredFlagObj*>(flag);
|
||||
void DestroyRetiredFlag(CommandLineFlag& flag) {
|
||||
assert(flag.IsRetired());
|
||||
delete static_cast<RetiredFlagObj*>(&flag);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
bool Retire(const char* name, FlagFastTypeId type_id) {
|
||||
auto* flag = new flags_internal::RetiredFlagObj(name, type_id);
|
||||
FlagRegistry::GlobalRegistry()->RegisterFlag(flag);
|
||||
FlagRegistry::GlobalRegistry().RegisterFlag(*flag);
|
||||
return true;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
bool IsRetiredFlag(absl::string_view name, bool* type_is_bool) {
|
||||
assert(!name.empty());
|
||||
CommandLineFlag* flag = flags_internal::FindRetiredFlag(name);
|
||||
if (flag == nullptr) {
|
||||
return false;
|
||||
class FlagSaverImpl {
|
||||
public:
|
||||
FlagSaverImpl() = default;
|
||||
FlagSaverImpl(const FlagSaverImpl&) = delete;
|
||||
void operator=(const FlagSaverImpl&) = delete;
|
||||
|
||||
// Saves the flag states from the flag registry into this object.
|
||||
// It's an error to call this more than once.
|
||||
void SaveFromRegistry() {
|
||||
assert(backup_registry_.empty()); // call only once!
|
||||
flags_internal::ForEachFlag([&](CommandLineFlag& flag) {
|
||||
if (auto flag_state =
|
||||
flags_internal::PrivateHandleAccessor::SaveState(flag)) {
|
||||
backup_registry_.emplace_back(std::move(flag_state));
|
||||
}
|
||||
});
|
||||
}
|
||||
assert(type_is_bool);
|
||||
*type_is_bool = flag->IsOfType<bool>();
|
||||
return true;
|
||||
}
|
||||
|
||||
// Restores the saved flag states into the flag registry.
|
||||
void RestoreToRegistry() {
|
||||
for (const auto& flag_state : backup_registry_) {
|
||||
flag_state->Restore();
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
std::vector<std::unique_ptr<flags_internal::FlagStateInterface>>
|
||||
backup_registry_;
|
||||
};
|
||||
|
||||
} // namespace flags_internal
|
||||
|
||||
FlagSaver::FlagSaver() : impl_(new flags_internal::FlagSaverImpl) {
|
||||
impl_->SaveFromRegistry();
|
||||
}
|
||||
|
||||
FlagSaver::~FlagSaver() {
|
||||
if (!impl_) return;
|
||||
|
||||
impl_->RestoreToRegistry();
|
||||
delete impl_;
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
CommandLineFlag* FindCommandLineFlag(absl::string_view name) {
|
||||
if (name.empty()) return nullptr;
|
||||
flags_internal::FlagRegistry& registry =
|
||||
flags_internal::FlagRegistry::GlobalRegistry();
|
||||
flags_internal::FlagRegistryLock frl(registry);
|
||||
|
||||
return registry.FindFlagLocked(name);
|
||||
}
|
||||
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
85
third_party/abseil_cpp/absl/flags/reflection.h
vendored
Normal file
85
third_party/abseil_cpp/absl/flags/reflection.h
vendored
Normal file
|
|
@ -0,0 +1,85 @@
|
|||
//
|
||||
// Copyright 2020 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
// -----------------------------------------------------------------------------
|
||||
// File: reflection.h
|
||||
// -----------------------------------------------------------------------------
|
||||
//
|
||||
// This file defines the routines to access and operate on an Abseil Flag's
|
||||
// reflection handle.
|
||||
|
||||
#ifndef ABSL_FLAGS_REFLECTION_H_
|
||||
#define ABSL_FLAGS_REFLECTION_H_
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "absl/base/config.h"
|
||||
#include "absl/flags/commandlineflag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
|
||||
namespace absl {
|
||||
ABSL_NAMESPACE_BEGIN
|
||||
namespace flags_internal {
|
||||
class FlagSaverImpl;
|
||||
} // namespace flags_internal
|
||||
|
||||
// FindCommandLineFlag()
|
||||
//
|
||||
// Returns the reflection handle of an Abseil flag of the specified name, or
|
||||
// `nullptr` if not found. This function will emit a warning if the name of a
|
||||
// 'retired' flag is specified.
|
||||
CommandLineFlag* FindCommandLineFlag(absl::string_view name);
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
// FlagSaver
|
||||
//------------------------------------------------------------------------------
|
||||
//
|
||||
// A FlagSaver object stores the state of flags in the scope where the FlagSaver
|
||||
// is defined, allowing modification of those flags within that scope and
|
||||
// automatic restoration of the flags to their previous state upon leaving the
|
||||
// scope.
|
||||
//
|
||||
// A FlagSaver can be used within tests to temporarily change the test
|
||||
// environment and restore the test case to its previous state.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
// void MyFunc() {
|
||||
// absl::FlagSaver fs;
|
||||
// ...
|
||||
// absl::SetFlag(FLAGS_myFlag, otherValue);
|
||||
// ...
|
||||
// } // scope of FlagSaver left, flags return to previous state
|
||||
//
|
||||
// This class is thread-safe.
|
||||
|
||||
class FlagSaver {
|
||||
public:
|
||||
FlagSaver();
|
||||
~FlagSaver();
|
||||
|
||||
FlagSaver(const FlagSaver&) = delete;
|
||||
void operator=(const FlagSaver&) = delete;
|
||||
|
||||
private:
|
||||
flags_internal::FlagSaverImpl* impl_;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
ABSL_NAMESPACE_END
|
||||
} // namespace absl
|
||||
|
||||
#endif // ABSL_FLAGS_REFLECTION_H_
|
||||
60
third_party/abseil_cpp/absl/flags/reflection_test.cc
vendored
Normal file
60
third_party/abseil_cpp/absl/flags/reflection_test.cc
vendored
Normal file
|
|
@ -0,0 +1,60 @@
|
|||
//
|
||||
// Copyright 2019 The Abseil Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// https://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "absl/flags/reflection.h"
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#include "absl/flags/internal/commandlineflag.h"
|
||||
#include "absl/flags/marshalling.h"
|
||||
#include "absl/memory/memory.h"
|
||||
|
||||
ABSL_FLAG(int, int_flag, 1, "int_flag help");
|
||||
ABSL_FLAG(std::string, string_flag, "dflt", "string_flag help");
|
||||
ABSL_RETIRED_FLAG(bool, bool_retired_flag, false, "bool_retired_flag help");
|
||||
|
||||
namespace {
|
||||
|
||||
namespace flags = absl::flags_internal;
|
||||
|
||||
class ReflectionTest : public testing::Test {
|
||||
protected:
|
||||
void SetUp() override { flag_saver_ = absl::make_unique<absl::FlagSaver>(); }
|
||||
void TearDown() override { flag_saver_.reset(); }
|
||||
|
||||
private:
|
||||
std::unique_ptr<absl::FlagSaver> flag_saver_;
|
||||
};
|
||||
|
||||
// --------------------------------------------------------------------
|
||||
|
||||
TEST_F(ReflectionTest, TestFindCommandLineFlag) {
|
||||
auto* handle = absl::FindCommandLineFlag("some_flag");
|
||||
EXPECT_EQ(handle, nullptr);
|
||||
|
||||
handle = absl::FindCommandLineFlag("int_flag");
|
||||
EXPECT_NE(handle, nullptr);
|
||||
|
||||
handle = absl::FindCommandLineFlag("string_flag");
|
||||
EXPECT_NE(handle, nullptr);
|
||||
|
||||
handle = absl::FindCommandLineFlag("bool_retired_flag");
|
||||
EXPECT_NE(handle, nullptr);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
|
@ -15,6 +15,7 @@
|
|||
|
||||
#include "absl/flags/usage_config.h"
|
||||
|
||||
#include <functional>
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue