// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
namespace blink {
// Note: do not add any copy or move constructors to this class: doing so will
// break test coverage that we don't clobber the class name by trying to emit
// replacements for synthesized functions.
class C {
public:
// Make sure initializers are updated to use the new names.
C()
: flag_field_(~0),
field_mentioning_http_and_https_(1),
should_rename_(0) {}
int Method() {
// Test that references to fields are updated correctly.
return instance_count_ + flag_field_ + field_mentioning_http_and_https_;
}
// Test that a field without a m_ prefix is correctly renamed.
static int instance_count_;
protected:
// Test that a field with a m_ prefix is correctly renamed.
const int flag_field_;
// Statics should be named with s_, but make sure s_ and m_ are both correctly
// stripped.
static int static_count_;
static int static_count_with_bad_name_;
// Make sure that acronyms don't confuse the underscore inserter.
int field_mentioning_http_and_https_;
// Already Google style, should not change.
int already_google_style_;
union {
// Anonymous union members should be renamed, as should contructor
// initializers of them.
char* should_rename_;
int* does_rename_;
};
};
struct Derived : public C {
using C::flag_field_;
using C::field_mentioning_http_and_https_;
};
int C::instance_count_ = 0;
// Structs are like classes.
struct S {
int integer_field_;
int wants_rename;
int google_style_already;
};
// Unions also use struct-style naming.
union U {
char four_chars[4];
short two_shorts[2];
int one_hopefully_four_byte_int;
int has_prefix_;
};
// https://crbug.com/640749#c1: Some type traits are inside blink namespace.
struct IsGarbageCollectedMixin {
static const bool value = true;
static const bool safe_to_compare_to_empty_or_deleted = false;
};
} // namespace blink
namespace not_blink {
// These are traits for WTF types that may be defined outside of blink such
// as in mojo. But their names are unique so we can globally treat them as
// type traits for renaming.
struct GloballyKnownTraits {
static const bool safe_to_compare_to_empty_or_deleted = false;
};
} // namespace not_blink
namespace WTF {
void TestForTraits() {
bool a = blink::IsGarbageCollectedMixin::safe_to_compare_to_empty_or_deleted;
bool b = not_blink::GloballyKnownTraits::safe_to_compare_to_empty_or_deleted;
}
// We don't want to capitalize fields in type traits
// (i.e. the |value| -> |kValue| rename is undesirable below).
struct TypeTrait1 {
static const bool value = true;
};
// Some type traits are implemented as classes, not structs
// (e.g. WTF::IsGarbageCollectedType or WTF::IsAssignable).
// We should not perform a |value| -> |kValue| rename in the type trait below.
template <typename T>
class TypeTrait2 {
public:
static const bool value = false;
};
template <>
class TypeTrait2<void> {
public:
static const bool value = false;
};
// Some type traits have static methods. We should not perform
// a |value| -> |kValue| rename in the type trait below.
template <typename T, typename U>
struct IsSubclass {
private:
typedef char YesType;
struct NoType {
char padding[8];
};
static YesType SubclassCheck(U*);
static NoType SubclassCheck(...);
static T* t_;
public:
static const bool value = sizeof(SubclassCheck(t_)) == sizeof(YesType);
};
// Some type traits have deleted instance methods. We should not perform
// a |value| -> |kValue| rename in the type trait below.
template <typename U = void>
struct IsTraceableInCollection {
// Expanded from STATIC_ONLY(IsTraceableInCollection) macro:
private:
IsTraceableInCollection() = delete;
IsTraceableInCollection(const IsTraceableInCollection&) = delete;
IsTraceableInCollection& operator=(const IsTraceableInCollection&) = delete;
void* operator new(unsigned long) = delete;
void* operator new(unsigned long, void*) = delete;
public:
static const bool value = true;
};
// Some type traits have a non-boolean value.
enum LifetimeManagementType {
kRefCountedLifetime,
kGarbageCollectedLifetime,
};
template <typename T>
struct LifetimeOf {
private:
// Okay to rename |isGarbageCollected| to |kIsGarbageCollected|.
static const bool kIsGarbageCollected = true;
public:
// Expecting no rename of |value|.
static const LifetimeManagementType value =
!kIsGarbageCollected ? kRefCountedLifetime : kGarbageCollectedLifetime;
};
template <typename T>
struct GenericHashTraitsBase {
// We don't want to capitalize fields in type traits
// (i.e. the |value| -> |kValue| rename is undesirable below).
// This problem is prevented by IsCallee heuristic.
static const int kWeakHandlingFlag = TypeTrait2<T>::value ? 123 : 456;
};
template <int Format>
struct IntermediateFormat {
// Some type traits have int type. Example below is loosely based on
// third_party/WebKit/Source/platform/graphics/gpu/WebGLImageConversion.cpp
static const int value = (Format == 123) ? 456 : 789;
};
}; // namespace WTF
void F() {
// Test that references to a static field are correctly rewritten.
blink::C::instance_count_++;
// Force instantiation of a copy constructor for blink::C to make sure field
// initializers for synthesized functions don't cause weird rewrites.
blink::C c;
blink::C c2 = c;
bool b1 = WTF::TypeTrait1::value;
bool b2 = WTF::TypeTrait2<void>::value;
}