#! /usr/bin/perl # # This file is part of the WebKit project # # Copyright (C) 1999 Waldo Bastian (bastian@kde.org) # Copyright (C) 2007, 2008, 2012 Apple Inc. All rights reserved. # Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies) # Copyright (C) 2010 Andras Becsi (abecsi@inf.u-szeged.hu), University of Szeged # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Library General Public # License as published by the Free Software Foundation; either # version 2 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Library General Public License for more details. # # You should have received a copy of the GNU Library General Public License # along with this library; see the file COPYING.LIB. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, # Boston, MA 02110-1301, USA. use Getopt::Long; use preprocessor; use strict; use warnings; my $defines; my $preprocessor; GetOptions('defines=s' => \$defines, 'preprocessor=s' => \$preprocessor); my @NAMES = applyPreprocessor("CSSPropertyNames.in", $defines, $preprocessor); my %namesHash; my @duplicates = (); my @names = (); my @aliases = (); foreach (@NAMES) { next if (m/(^\s*$)/); next if (/^#/); # Input may use a different EOL sequence than $/, so avoid chomp. $_ =~ s/[\r\n]+$//g; if (exists $namesHash{$_}) { push @duplicates, $_; } else { $namesHash{$_} = 1; } if ($_ =~ /=/) { push @aliases, $_; } else { push @names, $_; } } if (@duplicates > 0) { die 'Duplicate CSS property names: ', join(', ', @duplicates) . "\n"; } open GPERF, ">CSSPropertyNames.gperf" || die "Could not open CSSPropertyNames.gperf for writing"; print GPERF << "EOF"; %{ /* This file is automatically generated from CSSPropertyNames.in by makeprop, do not edit */ #include "config.h" #include \"CSSPropertyNames.h\" #include \"HashTools.h\" #include #include #include #include namespace WebCore { EOF print GPERF "const char* const propertyNameStrings[numCSSProperties] = {\n"; foreach my $name (@names) { print GPERF " \"$name\",\n"; } print GPERF "};\n\n"; print GPERF << "EOF"; %} %struct-type struct Property; %omit-struct-type %language=C++ %readonly-tables %global-table %compare-strncmp %define class-name CSSPropertyNamesHash %define lookup-function-name findPropertyImpl %define hash-function-name propery_hash_function %define word-array-name property_wordlist %enum %% EOF foreach my $name (@names) { my $id = $name; $id =~ s/(^[^-])|-(.)/uc($1||$2)/ge; print GPERF $name . ", CSSProperty" . $id . "\n"; } foreach my $alias (@aliases) { $alias =~ /^([^\s]*)[\s]*=[\s]*([^\s]*)/; my $name = $1; my $id = $2; $id =~ s/(^[^-])|-(.)/uc($1||$2)/ge; print GPERF $name . ", CSSProperty" . $id . "\n"; } print GPERF<< "EOF"; %% const Property* findProperty(register const char* str, register unsigned int len) { return CSSPropertyNamesHash::findPropertyImpl(str, len); } const char* getPropertyName(CSSPropertyID id) { if (id < firstCSSProperty) return 0; int index = id - firstCSSProperty; if (index >= numCSSProperties) return 0; return propertyNameStrings[index]; } const AtomicString& getPropertyNameAtomicString(CSSPropertyID id) { if (id < firstCSSProperty) return nullAtom; int index = id - firstCSSProperty; if (index >= numCSSProperties) return nullAtom; static AtomicString* propertyStrings = new AtomicString[numCSSProperties]; // Intentionally never destroyed. AtomicString& propertyString = propertyStrings[index]; if (propertyString.isNull()) { const char* propertyName = propertyNameStrings[index]; propertyString = AtomicString(propertyName, strlen(propertyName), AtomicString::ConstructFromLiteral); } return propertyString; } String getPropertyNameString(CSSPropertyID id) { // We share the StringImpl with the AtomicStrings. return getPropertyNameAtomicString(id).string(); } String getJSPropertyName(CSSPropertyID id) { char result[maxCSSPropertyNameLength + 1]; const char* cssPropertyName = getPropertyName(id); const char* propertyNamePointer = cssPropertyName; if (!propertyNamePointer) return emptyString(); char* resultPointer = result; while (char character = *propertyNamePointer++) { if (character == '-') { char nextCharacter = *propertyNamePointer++; if (!nextCharacter) break; character = (propertyNamePointer - 2 != cssPropertyName) ? toASCIIUpper(nextCharacter) : nextCharacter; } *resultPointer++ = character; } *resultPointer = '\\0'; return WTF::String(result); } } // namespace WebCore EOF open HEADER, ">CSSPropertyNames.h" || die "Could not open CSSPropertyNames.h for writing"; print HEADER << "EOF"; /* This file is automatically generated from CSSPropertyNames.in by makeprop, do not edit */ #ifndef CSSPropertyNames_h #define CSSPropertyNames_h #include #include #include namespace WTF { class AtomicString; class String; } namespace WebCore { enum CSSPropertyID { CSSPropertyInvalid = 0, #if ENABLE(CSS_VARIABLES) CSSPropertyVariable = 1, #endif EOF my $first = 1001; my $i = 1001; my $maxLen = 0; foreach my $name (@names) { my $id = $name; $id =~ s/(^[^-])|-(.)/uc($1||$2)/ge; print HEADER " CSSProperty" . $id . " = " . $i . ",\n"; $i = $i + 1; if (length($name) > $maxLen) { $maxLen = length($name); } } my $num = $i - $first; my $last = $i - 1; print HEADER "};\n\n"; print HEADER "const int firstCSSProperty = $first;\n"; print HEADER "const int numCSSProperties = $num;\n"; print HEADER "const int lastCSSProperty = $last;\n"; print HEADER "const size_t maxCSSPropertyNameLength = $maxLen;\n"; print HEADER << "EOF"; const char* getPropertyName(CSSPropertyID); const WTF::AtomicString& getPropertyNameAtomicString(CSSPropertyID id); WTF::String getPropertyNameString(CSSPropertyID id); WTF::String getJSPropertyName(CSSPropertyID); inline CSSPropertyID convertToCSSPropertyID(int value) { ASSERT((value >= firstCSSProperty && value <= lastCSSProperty) || value == CSSPropertyInvalid); return static_cast(value); } } // namespace WebCore namespace WTF { template<> struct DefaultHash { typedef IntHash Hash; }; template<> struct HashTraits : GenericHashTraits { static const bool emptyValueIsZero = true; static const bool needsDestruction = false; static void constructDeletedValue(WebCore::CSSPropertyID& slot) { slot = static_cast(WebCore::lastCSSProperty + 1); } static bool isDeletedValue(WebCore::CSSPropertyID value) { return value == (WebCore::lastCSSProperty + 1); } }; } #endif // CSSPropertyNames_h EOF close HEADER; my $gperf = $ENV{GPERF} ? $ENV{GPERF} : "gperf"; system("\"$gperf\" --key-positions=\"*\" -D -n -s 2 CSSPropertyNames.gperf --output-file=CSSPropertyNames.cpp") == 0 || die "calling gperf failed: $?";