| OLD | NEW | 
|---|
|  | (Empty) | 
| 1 #!/usr/bin/perl -w |  | 
| 2 |  | 
| 3 # Copyright (C) 2005, 2006, 2007, 2009 Apple Inc. All rights reserved. |  | 
| 4 # Copyright (C) 2009, Julien Chaffraix <jchaffraix@webkit.org> |  | 
| 5 # Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmob
      ile.com/) |  | 
| 6 # Copyright (C) 2011 Ericsson AB. All rights reserved. |  | 
| 7 # |  | 
| 8 # Redistribution and use in source and binary forms, with or without |  | 
| 9 # modification, are permitted provided that the following conditions |  | 
| 10 # are met: |  | 
| 11 # |  | 
| 12 # 1.  Redistributions of source code must retain the above copyright |  | 
| 13 #     notice, this list of conditions and the following disclaimer. |  | 
| 14 # 2.  Redistributions in binary form must reproduce the above copyright |  | 
| 15 #     notice, this list of conditions and the following disclaimer in the |  | 
| 16 #     documentation and/or other materials provided with the distribution. |  | 
| 17 # 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of |  | 
| 18 #     its contributors may be used to endorse or promote products derived |  | 
| 19 #     from this software without specific prior written permission. |  | 
| 20 # |  | 
| 21 # THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY |  | 
| 22 # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |  | 
| 23 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |  | 
| 24 # DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY |  | 
| 25 # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |  | 
| 26 # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |  | 
| 27 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |  | 
| 28 # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |  | 
| 29 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |  | 
| 30 # THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |  | 
| 31 |  | 
| 32 use strict; |  | 
| 33 |  | 
| 34 use StaticString; |  | 
| 35 use Config; |  | 
| 36 use Getopt::Long; |  | 
| 37 use File::Path; |  | 
| 38 use File::Spec; |  | 
| 39 use IO::File; |  | 
| 40 use InFilesParser; |  | 
| 41 |  | 
| 42 sub readTags($$); |  | 
| 43 sub readAttrs($$); |  | 
| 44 |  | 
| 45 my $printFactory = 0; |  | 
| 46 my $fontNamesIn = ""; |  | 
| 47 my $tagsFile = ""; |  | 
| 48 my $attrsFile = ""; |  | 
| 49 my $outputDir = "."; |  | 
| 50 my %parsedTags = (); |  | 
| 51 my %parsedAttrs = (); |  | 
| 52 my %enabledTags = (); |  | 
| 53 my %enabledAttrs = (); |  | 
| 54 my %allTags = (); |  | 
| 55 my %allAttrs = (); |  | 
| 56 my %allStrings = (); |  | 
| 57 my %parameters = (); |  | 
| 58 my $extraDefines = 0; |  | 
| 59 my $initDefaults = 1; |  | 
| 60 my %extensionAttrs = (); |  | 
| 61 |  | 
| 62 require Config; |  | 
| 63 |  | 
| 64 my $gccLocation = ""; |  | 
| 65 if ($ENV{CC}) { |  | 
| 66     $gccLocation = $ENV{CC}; |  | 
| 67 } elsif (($Config::Config{'osname'}) =~ /solaris/i) { |  | 
| 68     $gccLocation = "/usr/sfw/bin/gcc"; |  | 
| 69 } else { |  | 
| 70     $gccLocation = "/usr/bin/gcc"; |  | 
| 71 } |  | 
| 72 my $preprocessor = $gccLocation . " -E -x c++"; |  | 
| 73 |  | 
| 74 GetOptions( |  | 
| 75     'tags=s' => \$tagsFile, |  | 
| 76     'attrs=s' => \$attrsFile, |  | 
| 77     'factory' => \$printFactory, |  | 
| 78     'outputDir=s' => \$outputDir, |  | 
| 79     'extraDefines=s' => \$extraDefines, |  | 
| 80     'preprocessor=s' => \$preprocessor, |  | 
| 81     'fonts=s' => \$fontNamesIn, |  | 
| 82 ); |  | 
| 83 |  | 
| 84 mkpath($outputDir); |  | 
| 85 |  | 
| 86 if (length($fontNamesIn)) { |  | 
| 87     my $familyNamesFileBase = "FontFamily"; |  | 
| 88     my $familyNamesPrefix = "CSS"; |  | 
| 89     createGenericNamesFile($fontNamesIn, $familyNamesFileBase, $familyNamesPrefi
      x); |  | 
| 90 } |  | 
| 91 |  | 
| 92 die "You must specify at least one of --tags <file> or --attrs <file>" unless (l
      ength($tagsFile) || length($attrsFile)); |  | 
| 93 |  | 
| 94 if (length($tagsFile)) { |  | 
| 95     %allTags = %{readTags($tagsFile, 0)}; |  | 
| 96     %enabledTags = %{readTags($tagsFile, 1)}; |  | 
| 97     namesToStrings(\%allTags, \%allStrings); |  | 
| 98 } |  | 
| 99 |  | 
| 100 if (length($attrsFile)) { |  | 
| 101     %allAttrs = %{readAttrs($attrsFile, 0)}; |  | 
| 102     %enabledAttrs = %{readAttrs($attrsFile, 1)}; |  | 
| 103     namesToStrings(\%allAttrs, \%allStrings); |  | 
| 104 } |  | 
| 105 |  | 
| 106 die "You must specify a namespace (e.g. SVG) for <namespace>Names.h" unless $par
      ameters{namespace}; |  | 
| 107 die "You must specify a namespaceURI (e.g. http://www.w3.org/2000/svg)" unless $
      parameters{namespaceURI}; |  | 
| 108 |  | 
| 109 $parameters{namespacePrefix} = $parameters{namespace} unless $parameters{namespa
      cePrefix}; |  | 
| 110 $parameters{fallbackJSInterfaceName} = $parameters{fallbackInterfaceName} unless
       $parameters{fallbackJSInterfaceName}; |  | 
| 111 |  | 
| 112 my $namesBasePath = "$outputDir/$parameters{namespace}Names"; |  | 
| 113 my $factoryBasePath = "$outputDir/$parameters{namespace}ElementFactory"; |  | 
| 114 my $wrapperFactoryFileName = "$parameters{namespace}ElementWrapperFactory"; |  | 
| 115 |  | 
| 116 printNamesHeaderFile("$namesBasePath.h"); |  | 
| 117 printNamesCppFile("$namesBasePath.cpp"); |  | 
| 118 |  | 
| 119 if ($printFactory) { |  | 
| 120     printFactoryCppFile("$factoryBasePath.cpp"); |  | 
| 121     printFactoryHeaderFile("$factoryBasePath.h"); |  | 
| 122 } |  | 
| 123 |  | 
| 124 printWrapperFactoryCppFile($outputDir, $wrapperFactoryFileName); |  | 
| 125 printWrapperFactoryHeaderFile($outputDir, $wrapperFactoryFileName); |  | 
| 126 |  | 
| 127 ### Hash initialization |  | 
| 128 |  | 
| 129 sub defaultTagPropertyHash |  | 
| 130 { |  | 
| 131     return ( |  | 
| 132         'constructorNeedsCreatedByParser' => 0, |  | 
| 133         'constructorNeedsFormElement' => 0, |  | 
| 134         'noConstructor' => 0, |  | 
| 135         'interfaceName' => defaultInterfaceName($_[0]), |  | 
| 136         # By default, the JSInterfaceName is the same as the interfaceName. |  | 
| 137         'JSInterfaceName' => defaultInterfaceName($_[0]), |  | 
| 138         'mapToTagName' => '', |  | 
| 139         'wrapperOnlyIfMediaIsAvailable' => 0, |  | 
| 140         'conditional' => 0, |  | 
| 141         'contextConditional' => 0, |  | 
| 142         'runtimeConditional' => 0 |  | 
| 143     ); |  | 
| 144 } |  | 
| 145 |  | 
| 146 sub defaultParametersHash |  | 
| 147 { |  | 
| 148     return ( |  | 
| 149         'namespace' => '', |  | 
| 150         'namespacePrefix' => '', |  | 
| 151         'namespaceURI' => '', |  | 
| 152         'guardFactoryWith' => '', |  | 
| 153         'tagsNullNamespace' => 0, |  | 
| 154         'attrsNullNamespace' => 0, |  | 
| 155         'fallbackInterfaceName' => '', |  | 
| 156         'fallbackJSInterfaceName' => '' |  | 
| 157     ); |  | 
| 158 } |  | 
| 159 |  | 
| 160 sub defaultInterfaceName |  | 
| 161 { |  | 
| 162     die "No namespace found" if !$parameters{namespace}; |  | 
| 163     return $parameters{namespace} . upperCaseName($_[0]) . "Element" |  | 
| 164 } |  | 
| 165 |  | 
| 166 ### Parsing handlers |  | 
| 167 |  | 
| 168 sub valueForName |  | 
| 169 { |  | 
| 170     my $name = shift; |  | 
| 171     my $value = $extensionAttrs{$name}; |  | 
| 172 |  | 
| 173     if (!$value) { |  | 
| 174         $value = $name; |  | 
| 175         $value =~ s/_/-/g; |  | 
| 176     } |  | 
| 177 |  | 
| 178     return $value; |  | 
| 179 } |  | 
| 180 |  | 
| 181 sub namesToStrings |  | 
| 182 { |  | 
| 183     my $namesRef = shift; |  | 
| 184     my $stringsRef = shift; |  | 
| 185 |  | 
| 186     my %names = %$namesRef; |  | 
| 187 |  | 
| 188     for my $name (keys %names) { |  | 
| 189         $stringsRef->{$name} = valueForName($name); |  | 
| 190     } |  | 
| 191 } |  | 
| 192 |  | 
| 193 sub tagsHandler |  | 
| 194 { |  | 
| 195     my ($tag, $property, $value) = @_; |  | 
| 196 |  | 
| 197     $tag =~ s/-/_/g; |  | 
| 198 |  | 
| 199     # Initialize default property values. |  | 
| 200     $parsedTags{$tag} = { defaultTagPropertyHash($tag) } if !defined($parsedTags
      {$tag}); |  | 
| 201 |  | 
| 202     if ($property) { |  | 
| 203         die "Unknown property $property for tag $tag\n" if !defined($parsedTags{
      $tag}{$property}); |  | 
| 204 |  | 
| 205         # The code relies on JSInterfaceName deriving from interfaceName to chec
      k for custom JSInterfaceName. |  | 
| 206         # So override JSInterfaceName if it was not already set. |  | 
| 207         $parsedTags{$tag}{JSInterfaceName} = $value if $property eq "interfaceNa
      me" && $parsedTags{$tag}{JSInterfaceName} eq $parsedTags{$tag}{interfaceName}; |  | 
| 208 |  | 
| 209         $parsedTags{$tag}{$property} = $value; |  | 
| 210     } |  | 
| 211 } |  | 
| 212 |  | 
| 213 sub attrsHandler |  | 
| 214 { |  | 
| 215     my ($attr, $property, $value) = @_; |  | 
| 216     # Translate HTML5 extension attributes of the form 'x-webkit-feature' to 'we
      bkitfeature'. |  | 
| 217     # We don't just check for the 'x-' prefix because there are attributes such 
      as x-height |  | 
| 218     # which should follow the default path below. |  | 
| 219     if ($attr =~ m/^x-webkit-(.*)/) { |  | 
| 220         my $newAttr = "webkit$1"; |  | 
| 221         $extensionAttrs{$newAttr} = $attr; |  | 
| 222         $attr = $newAttr; |  | 
| 223     } |  | 
| 224     $attr =~ s/-/_/g; |  | 
| 225 |  | 
| 226     # Initialize default properties' values. |  | 
| 227     $parsedAttrs{$attr} = {} if !defined($parsedAttrs{$attr}); |  | 
| 228 |  | 
| 229     if ($property) { |  | 
| 230         die "Unknown property $property for attribute $attr\n" if !defined($pars
      edAttrs{$attr}{$property}); |  | 
| 231         $parsedAttrs{$attr}{$property} = $value; |  | 
| 232     } |  | 
| 233 } |  | 
| 234 |  | 
| 235 sub parametersHandler |  | 
| 236 { |  | 
| 237     my ($parameter, $value) = @_; |  | 
| 238 |  | 
| 239     # Initialize default properties' values. |  | 
| 240     %parameters = defaultParametersHash() if (!(keys %parameters) && $initDefaul
      ts); |  | 
| 241 |  | 
| 242     # If the input is an array, we want the strings to have the same value as th
      e key. |  | 
| 243     if ( $value eq 1) { |  | 
| 244         $value = $parameter; |  | 
| 245     } |  | 
| 246 |  | 
| 247     die "Unknown parameter $parameter for tags/attrs\n" if (!defined($parameters
      {$parameter}) && $initDefaults); |  | 
| 248     $parameters{$parameter} = $value; |  | 
| 249 } |  | 
| 250 |  | 
| 251 ## Support routines |  | 
| 252 |  | 
| 253 sub preprocessorCommand() |  | 
| 254 { |  | 
| 255     return $preprocessor if $extraDefines eq 0; |  | 
| 256     return $preprocessor . " -D" . join(" -D", split(" ", $extraDefines)); |  | 
| 257 } |  | 
| 258 |  | 
| 259 sub readNames($$$$) |  | 
| 260 { |  | 
| 261     my ($namesFile, $hashToFillRef, $handler, $usePreprocessor) = @_; |  | 
| 262 |  | 
| 263     my $names = new IO::File; |  | 
| 264     if ($usePreprocessor) { |  | 
| 265         open($names, preprocessorCommand() . " " . $namesFile . "|") or die "Fai
      led to open file: $namesFile"; |  | 
| 266     } else { |  | 
| 267         open($names, $namesFile) or die "Failed to open file: $namesFile"; |  | 
| 268     } |  | 
| 269 |  | 
| 270     my $InParser = InFilesParser->new(); |  | 
| 271     $InParser->parse($names, \¶metersHandler, $handler); |  | 
| 272 |  | 
| 273     close($names); |  | 
| 274     die "Failed to read names from file: $namesFile" if (keys %{$hashToFillRef} 
      == 0); |  | 
| 275     return $hashToFillRef; |  | 
| 276 } |  | 
| 277 |  | 
| 278 sub readAttrs($$) |  | 
| 279 { |  | 
| 280     my ($namesFile, $usePreprocessor) = @_; |  | 
| 281     %parsedAttrs = (); |  | 
| 282     return readNames($namesFile, \%parsedAttrs, \&attrsHandler, $usePreprocessor
      ); |  | 
| 283 } |  | 
| 284 |  | 
| 285 sub readTags($$) |  | 
| 286 { |  | 
| 287     my ($namesFile, $usePreprocessor) = @_; |  | 
| 288     %parsedTags = (); |  | 
| 289     return readNames($namesFile, \%parsedTags, \&tagsHandler, $usePreprocessor); |  | 
| 290 } |  | 
| 291 |  | 
| 292 sub printMacros |  | 
| 293 { |  | 
| 294     my ($F, $macro, $suffix, $namesRef) = @_; |  | 
| 295     my %names = %$namesRef; |  | 
| 296 |  | 
| 297     for my $name (sort keys %names) { |  | 
| 298         print F "$macro $name","$suffix;\n"; |  | 
| 299     } |  | 
| 300 } |  | 
| 301 |  | 
| 302 sub usesDefaultWrapper |  | 
| 303 { |  | 
| 304     my $tagName = shift; |  | 
| 305     return $tagName eq $parameters{namespace} . "Element"; |  | 
| 306 } |  | 
| 307 |  | 
| 308 # Build a direct mapping from the tags to the Element to create. |  | 
| 309 sub buildConstructorMap |  | 
| 310 { |  | 
| 311     my %tagConstructorMap = (); |  | 
| 312     for my $tagName (keys %enabledTags) { |  | 
| 313         my $interfaceName = $enabledTags{$tagName}{interfaceName}; |  | 
| 314 |  | 
| 315         if ($enabledTags{$tagName}{mapToTagName}) { |  | 
| 316             die "Cannot handle multiple mapToTagName for $tagName\n" if $enabled
      Tags{$enabledTags{$tagName}{mapToTagName}}{mapToTagName}; |  | 
| 317             $interfaceName = $enabledTags{ $enabledTags{$tagName}{mapToTagName} 
      }{interfaceName}; |  | 
| 318         } |  | 
| 319 |  | 
| 320         # Chop the string to keep the interesting part. |  | 
| 321         $interfaceName =~ s/$parameters{namespace}(.*)Element/$1/; |  | 
| 322         $tagConstructorMap{$tagName} = lc($interfaceName); |  | 
| 323     } |  | 
| 324 |  | 
| 325     return %tagConstructorMap; |  | 
| 326 } |  | 
| 327 |  | 
| 328 # Helper method that print the constructor's signature avoiding |  | 
| 329 # unneeded arguments. |  | 
| 330 sub printConstructorSignature |  | 
| 331 { |  | 
| 332     my ($F, $tagName, $constructorName, $constructorTagName) = @_; |  | 
| 333 |  | 
| 334     print F "static PassRefPtr<$parameters{namespace}Element> ${constructorName}
      Constructor(const QualifiedName& $constructorTagName, Document& document"; |  | 
| 335     if ($parameters{namespace} eq "HTML") { |  | 
| 336         print F ", HTMLFormElement*"; |  | 
| 337         print F " formElement" if $enabledTags{$tagName}{constructorNeedsFormEle
      ment}; |  | 
| 338     } |  | 
| 339     print F ", bool"; |  | 
| 340     print F " createdByParser" if $enabledTags{$tagName}{constructorNeedsCreated
      ByParser}; |  | 
| 341     print F ")\n{\n"; |  | 
| 342 } |  | 
| 343 |  | 
| 344 # Helper method to dump the constructor interior and call the |  | 
| 345 # Element constructor with the right arguments. |  | 
| 346 # The variable names should be kept in sync with the previous method. |  | 
| 347 sub printConstructorInterior |  | 
| 348 { |  | 
| 349     my ($F, $tagName, $interfaceName, $constructorTagName) = @_; |  | 
| 350 |  | 
| 351     # Handle media elements. |  | 
| 352     if ($enabledTags{$tagName}{wrapperOnlyIfMediaIsAvailable}) { |  | 
| 353         print F <<END |  | 
| 354     Settings* settings = document.settings(); |  | 
| 355     if (!RuntimeEnabledFeatures::mediaEnabled() || (settings && !settings->media
      Enabled())) |  | 
| 356         return 0; |  | 
| 357 |  | 
| 358 END |  | 
| 359 ; |  | 
| 360     } |  | 
| 361 |  | 
| 362     my $contextConditional = $enabledTags{$tagName}{contextConditional}; |  | 
| 363     if ($contextConditional) { |  | 
| 364         print F <<END |  | 
| 365     if (!ContextFeatures::${contextConditional}Enabled(&document)) |  | 
| 366         return 0; |  | 
| 367 END |  | 
| 368 ; |  | 
| 369     } |  | 
| 370 |  | 
| 371     my $runtimeConditional = $enabledTags{$tagName}{runtimeConditional}; |  | 
| 372     if ($runtimeConditional) { |  | 
| 373         print F <<END |  | 
| 374     if (!RuntimeEnabledFeatures::${runtimeConditional}Enabled()) |  | 
| 375         return 0; |  | 
| 376 END |  | 
| 377 ; |  | 
| 378     } |  | 
| 379 |  | 
| 380     # Call the constructor with the right parameters. |  | 
| 381     print F "    return ${interfaceName}::create($constructorTagName, document"; |  | 
| 382     print F ", formElement" if $enabledTags{$tagName}{constructorNeedsFormElemen
      t}; |  | 
| 383     print F ", createdByParser" if $enabledTags{$tagName}{constructorNeedsCreate
      dByParser}; |  | 
| 384     print F ");\n}\n\n"; |  | 
| 385 } |  | 
| 386 |  | 
| 387 sub printConstructors |  | 
| 388 { |  | 
| 389     my ($F, $tagConstructorMapRef) = @_; |  | 
| 390     my %tagConstructorMap = %$tagConstructorMapRef; |  | 
| 391 |  | 
| 392     # This is to avoid generating the same constructor several times. |  | 
| 393     my %uniqueTags = (); |  | 
| 394     for my $tagName (sort keys %tagConstructorMap) { |  | 
| 395         my $interfaceName = $enabledTags{$tagName}{interfaceName}; |  | 
| 396 |  | 
| 397         # Ignore the mapped tag |  | 
| 398         # FIXME: It could be moved inside this loop but was split for readibilit
      y. |  | 
| 399         next if (defined($uniqueTags{$interfaceName}) || $enabledTags{$tagName}{
      mapToTagName}); |  | 
| 400         # Tags can have wrappers without constructors. |  | 
| 401         # This is useful to make user-agent shadow elements internally testable |  | 
| 402         # while keeping them from being avaialble in the HTML markup. |  | 
| 403         next if $enabledTags{$tagName}{noConstructor}; |  | 
| 404 |  | 
| 405         $uniqueTags{$interfaceName} = '1'; |  | 
| 406 |  | 
| 407         my $conditional = $enabledTags{$tagName}{conditional}; |  | 
| 408         if ($conditional) { |  | 
| 409             my $conditionalString = "ENABLE(" . join(") && ENABLE(", split(/&/, 
      $conditional)) . ")"; |  | 
| 410             print F "#if ${conditionalString}\n\n"; |  | 
| 411         } |  | 
| 412 |  | 
| 413         printConstructorSignature($F, $tagName, $tagConstructorMap{$tagName}, "t
      agName"); |  | 
| 414         printConstructorInterior($F, $tagName, $interfaceName, "tagName"); |  | 
| 415 |  | 
| 416         if ($conditional) { |  | 
| 417             print F "#endif\n"; |  | 
| 418         } |  | 
| 419     } |  | 
| 420 |  | 
| 421     # Mapped tag name uses a special wrapper to keep their prefix and namespaceU
      RI while using the mapped localname. |  | 
| 422     for my $tagName (sort keys %tagConstructorMap) { |  | 
| 423         if ($enabledTags{$tagName}{mapToTagName}) { |  | 
| 424             my $mappedName = $enabledTags{$tagName}{mapToTagName}; |  | 
| 425             printConstructorSignature($F, $mappedName, $mappedName . "To" . $tag
      Name, "tagName"); |  | 
| 426             printConstructorInterior($F, $mappedName, $enabledTags{$mappedName}{
      interfaceName}, "QualifiedName(tagName.prefix(), ${mappedName}Tag.localName(), t
      agName.namespaceURI())"); |  | 
| 427         } |  | 
| 428     } |  | 
| 429 } |  | 
| 430 |  | 
| 431 sub printFunctionInits |  | 
| 432 { |  | 
| 433     my ($F, $tagConstructorMap) = @_; |  | 
| 434     my %tagConstructorMap = %$tagConstructorMap; |  | 
| 435 |  | 
| 436     for my $tagName (sort keys %tagConstructorMap) { |  | 
| 437         next if $enabledTags{$tagName}{noConstructor}; |  | 
| 438 |  | 
| 439         my $conditional = $enabledTags{$tagName}{conditional}; |  | 
| 440         if ($conditional) { |  | 
| 441             my $conditionalString = "ENABLE(" . join(") && ENABLE(", split(/&/, 
      $conditional)) . ")"; |  | 
| 442             print F "#if ${conditionalString}\n"; |  | 
| 443         } |  | 
| 444 |  | 
| 445         if ($enabledTags{$tagName}{mapToTagName}) { |  | 
| 446             print F "    addTag(${tagName}Tag, $enabledTags{$tagName}{mapToTagNa
      me}To${tagName}Constructor);\n"; |  | 
| 447         } else { |  | 
| 448             print F "    addTag(${tagName}Tag, $tagConstructorMap{$tagName}Const
      ructor);\n"; |  | 
| 449         } |  | 
| 450 |  | 
| 451         if ($conditional) { |  | 
| 452             print F "#endif\n\n"; |  | 
| 453         } |  | 
| 454     } |  | 
| 455 } |  | 
| 456 |  | 
| 457 sub svgCapitalizationHacks |  | 
| 458 { |  | 
| 459     my $name = shift; |  | 
| 460 |  | 
| 461     $name = "FE" . ucfirst $1 if $name =~ /^fe(.+)$/; |  | 
| 462 |  | 
| 463     return $name; |  | 
| 464 } |  | 
| 465 |  | 
| 466 sub upperCaseName |  | 
| 467 { |  | 
| 468     my $name = shift; |  | 
| 469 |  | 
| 470     $name = svgCapitalizationHacks($name) if ($parameters{namespace} eq "SVG"); |  | 
| 471 |  | 
| 472     while ($name =~ /^(.*?)_(.*)/) { |  | 
| 473         $name = $1 . ucfirst $2; |  | 
| 474     } |  | 
| 475 |  | 
| 476     return ucfirst $name; |  | 
| 477 } |  | 
| 478 |  | 
| 479 sub printHeaderHead |  | 
| 480 { |  | 
| 481     my ($F, $prefix, $nsName, $includes) = @_; |  | 
| 482 |  | 
| 483     print F "#ifndef ${prefix}_${nsName}Names_h\n"; |  | 
| 484     print F "#define ${prefix}_${nsName}Names_h\n\n"; |  | 
| 485     print F "$includes\n\n"; |  | 
| 486 |  | 
| 487     print F "namespace WebCore {\n\n"; |  | 
| 488     print F "namespace ${nsName}Names {\n\n"; |  | 
| 489 |  | 
| 490     print F "#ifndef ${prefix}_${nsName}NAMES_HIDE_GLOBALS\n"; |  | 
| 491 } |  | 
| 492 |  | 
| 493 sub printCppHead |  | 
| 494 { |  | 
| 495     my ($F, $prefix, $nsName, $usedNamespace) = @_; |  | 
| 496 |  | 
| 497     print F "#include \"config.h\"\n\n"; |  | 
| 498     print F "#ifdef SKIP_STATIC_CONSTRUCTORS_ON_GCC\n"; |  | 
| 499     print F "#define ${prefix}_${nsName}NAMES_HIDE_GLOBALS 1\n"; |  | 
| 500     print F "#else\n"; |  | 
| 501     print F "#define QNAME_DEFAULT_CONSTRUCTOR 1\n"; |  | 
| 502     print F "#endif\n\n"; |  | 
| 503 |  | 
| 504     print F "#include \"${nsName}Names.h\"\n\n"; |  | 
| 505     print F "#include \"wtf/StaticConstructors.h\"\n"; |  | 
| 506 |  | 
| 507     print F "namespace WebCore {\n\n"; |  | 
| 508     print F "namespace ${nsName}Names {\n\n"; |  | 
| 509     print F "using namespace $usedNamespace;\n\n"; |  | 
| 510 } |  | 
| 511 |  | 
| 512 sub printInit |  | 
| 513 { |  | 
| 514     my ($F, $isDefinition) = @_; |  | 
| 515 |  | 
| 516     if ($isDefinition) { |  | 
| 517         print F "\nvoid init();\n\n"; |  | 
| 518         print F "} }\n\n"; |  | 
| 519         print F "#endif\n\n"; |  | 
| 520         return; |  | 
| 521     } |  | 
| 522 |  | 
| 523 print F "\nvoid init() |  | 
| 524 { |  | 
| 525     // Use placement new to initialize the globals. |  | 
| 526 |  | 
| 527 "; |  | 
| 528 } |  | 
| 529 |  | 
| 530 sub printLicenseHeader |  | 
| 531 { |  | 
| 532     my $F = shift; |  | 
| 533     print F "/* |  | 
| 534  * THIS FILE WAS AUTOMATICALLY GENERATED, DO NOT EDIT. |  | 
| 535  * |  | 
| 536  * This file was generated by the core/scripts/make_names.pl script. |  | 
| 537  * |  | 
| 538  * Copyright (C) 2005, 2006, 2007, 2008, 2009 Apple Inc.  All rights reserved. |  | 
| 539  * |  | 
| 540  * Redistribution and use in source and binary forms, with or without |  | 
| 541  * modification, are permitted provided that the following conditions |  | 
| 542  * are met: |  | 
| 543  * 1. Redistributions of source code must retain the above copyright |  | 
| 544  *    notice, this list of conditions and the following disclaimer. |  | 
| 545  * 2. Redistributions in binary form must reproduce the above copyright |  | 
| 546  *    notice, this list of conditions and the following disclaimer in the |  | 
| 547  *    documentation and/or other materials provided with the distribution. |  | 
| 548  * |  | 
| 549  * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY |  | 
| 550  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |  | 
| 551  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR |  | 
| 552  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR |  | 
| 553  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |  | 
| 554  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, |  | 
| 555  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR |  | 
| 556  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY |  | 
| 557  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |  | 
| 558  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |  | 
| 559  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |  | 
| 560  */ |  | 
| 561 |  | 
| 562 "; |  | 
| 563 } |  | 
| 564 |  | 
| 565 sub printNamesHeaderFile |  | 
| 566 { |  | 
| 567     my ($headerPath) = shift; |  | 
| 568     my $F; |  | 
| 569     open F, ">$headerPath"; |  | 
| 570 |  | 
| 571     printLicenseHeader($F); |  | 
| 572     printHeaderHead($F, "DOM", $parameters{namespace}, "#include \"core/dom/Qual
      ifiedName.h\""); |  | 
| 573 |  | 
| 574     my $lowerNamespace = lc($parameters{namespacePrefix}); |  | 
| 575     print F "// Namespace\n"; |  | 
| 576     print F "extern const WTF::AtomicString ${lowerNamespace}NamespaceURI;\n\n"; |  | 
| 577 |  | 
| 578     if (keys %allTags) { |  | 
| 579         print F "// Tags\n"; |  | 
| 580         printMacros($F, "extern const WebCore::QualifiedName", "Tag", \%allTags)
      ; |  | 
| 581     } |  | 
| 582 |  | 
| 583     if (keys %allAttrs) { |  | 
| 584         print F "// Attributes\n"; |  | 
| 585         printMacros($F, "extern const WebCore::QualifiedName", "Attr", \%allAttr
      s); |  | 
| 586     } |  | 
| 587     print F "#endif\n\n"; |  | 
| 588 |  | 
| 589     if (keys %allTags) { |  | 
| 590         print F "const unsigned $parameters{namespace}TagsCount = ", scalar(keys
       %allTags), ";\n"; |  | 
| 591         print F "WebCore::QualifiedName** get$parameters{namespace}Tags();\n"; |  | 
| 592     } |  | 
| 593 |  | 
| 594     if (keys %allAttrs) { |  | 
| 595         print F "const unsigned $parameters{namespace}AttrsCount = ", scalar(key
      s %allAttrs), ";\n"; |  | 
| 596         print F "WebCore::QualifiedName** get$parameters{namespace}Attrs();\n"; |  | 
| 597     } |  | 
| 598 |  | 
| 599     printInit($F, 1); |  | 
| 600     close F; |  | 
| 601 } |  | 
| 602 |  | 
| 603 sub printNamesCppFile |  | 
| 604 { |  | 
| 605     my $cppPath = shift; |  | 
| 606     my $F; |  | 
| 607     open F, ">$cppPath"; |  | 
| 608 |  | 
| 609     printLicenseHeader($F); |  | 
| 610     printCppHead($F, "DOM", $parameters{namespace}, "WebCore"); |  | 
| 611 |  | 
| 612     my $lowerNamespace = lc($parameters{namespacePrefix}); |  | 
| 613 |  | 
| 614     print F "DEFINE_GLOBAL(AtomicString, ${lowerNamespace}NamespaceURI)\n\n"; |  | 
| 615 |  | 
| 616     if (keys %allTags) { |  | 
| 617         print F "// Tags\n"; |  | 
| 618         for my $name (sort keys %allTags) { |  | 
| 619             print F "DEFINE_GLOBAL(QualifiedName, ", $name, "Tag)\n"; |  | 
| 620         } |  | 
| 621 |  | 
| 622         print F "\n\nWebCore::QualifiedName** get$parameters{namespace}Tags()\n"
      ; |  | 
| 623         print F "{\n    static WebCore::QualifiedName* $parameters{namespace}Tag
      s[] = {\n"; |  | 
| 624         for my $name (sort keys %allTags) { |  | 
| 625             print F "        (WebCore::QualifiedName*)&${name}Tag,\n"; |  | 
| 626         } |  | 
| 627         print F "    };\n"; |  | 
| 628         print F "    return $parameters{namespace}Tags;\n"; |  | 
| 629         print F "}\n"; |  | 
| 630     } |  | 
| 631 |  | 
| 632     if (keys %allAttrs) { |  | 
| 633         print F "\n// Attributes\n"; |  | 
| 634         for my $name (sort keys %allAttrs) { |  | 
| 635             print F "DEFINE_GLOBAL(QualifiedName, ", $name, "Attr)\n"; |  | 
| 636         } |  | 
| 637         print F "\n\nWebCore::QualifiedName** get$parameters{namespace}Attrs()\n
      "; |  | 
| 638         print F "{\n    static WebCore::QualifiedName* $parameters{namespace}Att
      r[] = {\n"; |  | 
| 639         for my $name (sort keys %allAttrs) { |  | 
| 640             print F "        (WebCore::QualifiedName*)&${name}Attr,\n"; |  | 
| 641         } |  | 
| 642         print F "    };\n"; |  | 
| 643         print F "    return $parameters{namespace}Attr;\n"; |  | 
| 644         print F "}\n"; |  | 
| 645     } |  | 
| 646 |  | 
| 647     printInit($F, 0); |  | 
| 648 |  | 
| 649     print(F "    AtomicString ${lowerNamespace}NS(\"$parameters{namespaceURI}\",
       AtomicString::ConstructFromLiteral);\n\n"); |  | 
| 650 |  | 
| 651     print(F "    // Namespace\n"); |  | 
| 652     print(F "    new ((void*)&${lowerNamespace}NamespaceURI) AtomicString(${lowe
      rNamespace}NS);\n"); |  | 
| 653     print(F "\n"); |  | 
| 654     print F StaticString::GenerateStringImpls(\%allStrings); |  | 
| 655 |  | 
| 656     if (keys %allTags) { |  | 
| 657         my $tagsNamespace = $parameters{tagsNullNamespace} ? "nullAtom" : "${low
      erNamespace}NS"; |  | 
| 658         printDefinitions($F, \%allTags, "tags", $tagsNamespace); |  | 
| 659     } |  | 
| 660     if (keys %allAttrs) { |  | 
| 661         my $attrsNamespace = $parameters{attrsNullNamespace} ? "nullAtom" : "${l
      owerNamespace}NS"; |  | 
| 662         printDefinitions($F, \%allAttrs, "attributes", $attrsNamespace); |  | 
| 663     } |  | 
| 664 |  | 
| 665     print F "}\n\n} }\n\n"; |  | 
| 666     close F; |  | 
| 667 } |  | 
| 668 |  | 
| 669 sub printJSElementIncludes |  | 
| 670 { |  | 
| 671     my $F = shift; |  | 
| 672 |  | 
| 673     my %tagsSeen; |  | 
| 674     for my $tagName (sort keys %enabledTags) { |  | 
| 675         my $JSInterfaceName = $enabledTags{$tagName}{JSInterfaceName}; |  | 
| 676         next if defined($tagsSeen{$JSInterfaceName}) || usesDefaultJSWrapper($ta
      gName); |  | 
| 677         if ($enabledTags{$tagName}{conditional}) { |  | 
| 678             # We skip feature-define-specific #includes here since we handle the
      m separately. |  | 
| 679             next; |  | 
| 680         } |  | 
| 681         $tagsSeen{$JSInterfaceName} = 1; |  | 
| 682 |  | 
| 683         print F "#include \"V8${JSInterfaceName}.h\"\n"; |  | 
| 684     } |  | 
| 685     print F "#include \"V8$parameters{fallbackJSInterfaceName}.h\"\n"; |  | 
| 686 } |  | 
| 687 |  | 
| 688 sub printElementIncludes |  | 
| 689 { |  | 
| 690     my $F = shift; |  | 
| 691 |  | 
| 692     my %tagsSeen; |  | 
| 693     for my $tagName (sort keys %enabledTags) { |  | 
| 694         my $interfaceName = $enabledTags{$tagName}{interfaceName}; |  | 
| 695         next if defined($tagsSeen{$interfaceName}); |  | 
| 696         if ($enabledTags{$tagName}{conditional}) { |  | 
| 697             # We skip feature-define-specific #includes here since we handle the
      m separately. |  | 
| 698             next; |  | 
| 699         } |  | 
| 700         $tagsSeen{$interfaceName} = 1; |  | 
| 701 |  | 
| 702         print F "#include \"${interfaceName}.h\"\n"; |  | 
| 703     } |  | 
| 704     print F "#include \"$parameters{fallbackInterfaceName}.h\"\n"; |  | 
| 705 } |  | 
| 706 |  | 
| 707 sub printConditionalElementIncludes |  | 
| 708 { |  | 
| 709     my ($F, $shouldIncludeV8Headers) = @_; |  | 
| 710 |  | 
| 711     my %conditionals; |  | 
| 712     my %unconditionalElementIncludes; |  | 
| 713     my %unconditionalJSElementIncludes; |  | 
| 714 |  | 
| 715     for my $tagName (keys %enabledTags) { |  | 
| 716         my $conditional = $enabledTags{$tagName}{conditional}; |  | 
| 717         my $interfaceName = $enabledTags{$tagName}{interfaceName}; |  | 
| 718         my $JSInterfaceName = $enabledTags{$tagName}{JSInterfaceName}; |  | 
| 719 |  | 
| 720         if ($conditional) { |  | 
| 721             $conditionals{$conditional}{interfaceNames}{$interfaceName} = 1; |  | 
| 722             $conditionals{$conditional}{JSInterfaceNames}{$JSInterfaceName} = 1; |  | 
| 723         } else { |  | 
| 724             $unconditionalElementIncludes{$interfaceName} = 1; |  | 
| 725             $unconditionalJSElementIncludes{$JSInterfaceName} = 1; |  | 
| 726         } |  | 
| 727     } |  | 
| 728 |  | 
| 729     for my $conditional (sort keys %conditionals) { |  | 
| 730         print F "\n#if ENABLE($conditional)\n"; |  | 
| 731         for my $interfaceName (sort keys %{$conditionals{$conditional}{interface
      Names}}) { |  | 
| 732             next if $unconditionalElementIncludes{$interfaceName}; |  | 
| 733             print F "#include \"$interfaceName.h\"\n"; |  | 
| 734         } |  | 
| 735         if ($shouldIncludeV8Headers) { |  | 
| 736             for my $JSInterfaceName (sort keys %{$conditionals{$conditional}{JSI
      nterfaceNames}}) { |  | 
| 737                 next if $unconditionalJSElementIncludes{$JSInterfaceName}; |  | 
| 738                 print F "#include \"V8$JSInterfaceName.h\"\n"; |  | 
| 739             } |  | 
| 740         } |  | 
| 741         print F "#endif\n"; |  | 
| 742     } |  | 
| 743 } |  | 
| 744 |  | 
| 745 sub printDefinitions |  | 
| 746 { |  | 
| 747     my ($F, $namesRef, $type, $namespaceURI) = @_; |  | 
| 748     my $singularType = substr($type, 0, -1); |  | 
| 749     my $shortType = substr($singularType, 0, 4); |  | 
| 750     my $shortCamelType = ucfirst($shortType); |  | 
| 751     my $shortUpperType = uc($shortType); |  | 
| 752 |  | 
| 753     print F "    // " . ucfirst($type) . "\n"; |  | 
| 754 |  | 
| 755     for my $name (sort keys %$namesRef) { |  | 
| 756         # To generate less code in init(), the common case of nullAtom for the n
      amespace, we call createQualifiedName() without passing $namespaceURI. |  | 
| 757         if ($namespaceURI eq "nullAtom") { |  | 
| 758             print F "    createQualifiedName((void*)&$name","${shortCamelType}, 
      ${name}Impl);\n"; |  | 
| 759         } else { |  | 
| 760             print F "    createQualifiedName((void*)&$name","${shortCamelType}, 
      ${name}Impl, $namespaceURI);\n"; |  | 
| 761         } |  | 
| 762     } |  | 
| 763 } |  | 
| 764 |  | 
| 765 ## ElementFactory routines |  | 
| 766 |  | 
| 767 sub printFactoryCppFile |  | 
| 768 { |  | 
| 769     my $cppPath = shift; |  | 
| 770     my $F; |  | 
| 771     open F, ">$cppPath"; |  | 
| 772 |  | 
| 773 printLicenseHeader($F); |  | 
| 774 |  | 
| 775 print F <<END |  | 
| 776 #include "config.h" |  | 
| 777 END |  | 
| 778 ; |  | 
| 779 |  | 
| 780 print F "\n#if $parameters{guardFactoryWith}\n\n" if $parameters{guardFactoryWit
      h}; |  | 
| 781 |  | 
| 782 print F <<END |  | 
| 783 #include "$parameters{namespace}ElementFactory.h" |  | 
| 784 #include "$parameters{namespace}Names.h" |  | 
| 785 END |  | 
| 786 ; |  | 
| 787 |  | 
| 788 printElementIncludes($F); |  | 
| 789 |  | 
| 790 print F "\n#include \"wtf/HashMap.h\"\n"; |  | 
| 791 |  | 
| 792 printConditionalElementIncludes($F); |  | 
| 793 |  | 
| 794 print F <<END |  | 
| 795 |  | 
| 796 #include "RuntimeEnabledFeatures.h" |  | 
| 797 #include "core/dom/ContextFeatures.h" |  | 
| 798 #include "core/dom/custom/CustomElement.h" |  | 
| 799 #include "core/dom/custom/CustomElementRegistrationContext.h" |  | 
| 800 #include "core/dom/Document.h" |  | 
| 801 #include "core/page/Settings.h" |  | 
| 802 |  | 
| 803 namespace WebCore { |  | 
| 804 |  | 
| 805 using namespace $parameters{namespace}Names; |  | 
| 806 |  | 
| 807 END |  | 
| 808 ; |  | 
| 809 |  | 
| 810 print F "typedef PassRefPtr<$parameters{namespace}Element> (*ConstructorFunction
      )(const QualifiedName&, Document&"; |  | 
| 811 print F ", HTMLFormElement*" if $parameters{namespace} eq "HTML"; |  | 
| 812 print F ", bool createdByParser);\n"; |  | 
| 813 print F <<END |  | 
| 814 typedef HashMap<StringImpl*, ConstructorFunction> FunctionMap; |  | 
| 815 |  | 
| 816 static FunctionMap* gFunctionMap = 0; |  | 
| 817 |  | 
| 818 END |  | 
| 819 ; |  | 
| 820 |  | 
| 821 my %tagConstructorMap = buildConstructorMap(); |  | 
| 822 |  | 
| 823 printConstructors($F, \%tagConstructorMap); |  | 
| 824 |  | 
| 825 print F <<END |  | 
| 826 static void addTag(const QualifiedName& tag, ConstructorFunction func) |  | 
| 827 { |  | 
| 828     gFunctionMap->set(tag.localName().impl(), func); |  | 
| 829 } |  | 
| 830 |  | 
| 831 static void createFunctionMap() |  | 
| 832 { |  | 
| 833     ASSERT(!gFunctionMap); |  | 
| 834 |  | 
| 835     // Create the table. |  | 
| 836     gFunctionMap = new FunctionMap; |  | 
| 837 |  | 
| 838     // Populate it with constructor functions. |  | 
| 839 END |  | 
| 840 ; |  | 
| 841 |  | 
| 842 printFunctionInits($F, \%tagConstructorMap); |  | 
| 843 |  | 
| 844 print F "}\n"; |  | 
| 845 |  | 
| 846 |  | 
| 847 print F "\nPassRefPtr<$parameters{namespace}Element> $parameters{namespace}Eleme
      ntFactory::create$parameters{namespace}Element(const QualifiedName& qName, Docum
      ent* document"; |  | 
| 848 print F ", HTMLFormElement* formElement" if $parameters{namespace} eq "HTML"; |  | 
| 849 print F ", bool createdByParser)\n{\n"; |  | 
| 850 |  | 
| 851 print F <<END |  | 
| 852     if (!document) |  | 
| 853         return 0; |  | 
| 854 |  | 
| 855     if (CustomElement::isValidName(qName.localName()) && document->registrationC
      ontext()) { |  | 
| 856         RefPtr<Element> element = document->registrationContext()->createCustomT
      agElement(*document, qName, createdByParser ? CustomElementRegistrationContext::
      CreatedByParser : CustomElementRegistrationContext::NotCreatedByParser); |  | 
| 857         ASSERT_WITH_SECURITY_IMPLICATION(element->is$parameters{namespace}Elemen
      t()); |  | 
| 858         return static_pointer_cast<$parameters{namespace}Element>(element.releas
      e()); |  | 
| 859     } |  | 
| 860 |  | 
| 861     if (!gFunctionMap) |  | 
| 862         createFunctionMap(); |  | 
| 863     if (ConstructorFunction function = gFunctionMap->get(qName.localName().impl(
      ))) { |  | 
| 864 END |  | 
| 865 ; |  | 
| 866 |  | 
| 867 if ($parameters{namespace} eq "HTML") { |  | 
| 868     print F "        if (PassRefPtr<$parameters{namespace}Element> element = fun
      ction(qName, *document, formElement, createdByParser))\n"; |  | 
| 869     print F "            return element;\n"; |  | 
| 870 } else { |  | 
| 871     print F "        if (PassRefPtr<$parameters{namespace}Element> element = fun
      ction(qName, *document, createdByParser))\n"; |  | 
| 872     print F "            return element;\n"; |  | 
| 873 } |  | 
| 874 print F <<END |  | 
| 875     } |  | 
| 876 |  | 
| 877     return $parameters{fallbackInterfaceName}::create(qName, *document); |  | 
| 878 } |  | 
| 879 |  | 
| 880 } // namespace WebCore |  | 
| 881 |  | 
| 882 END |  | 
| 883 ; |  | 
| 884 |  | 
| 885     print F "#endif\n" if $parameters{guardFactoryWith}; |  | 
| 886 |  | 
| 887     close F; |  | 
| 888 } |  | 
| 889 |  | 
| 890 sub printFactoryHeaderFile |  | 
| 891 { |  | 
| 892     my $headerPath = shift; |  | 
| 893     my $F; |  | 
| 894     open F, ">$headerPath"; |  | 
| 895 |  | 
| 896     printLicenseHeader($F); |  | 
| 897 |  | 
| 898     print F<<END |  | 
| 899 #ifndef $parameters{namespace}ElementFactory_h |  | 
| 900 #define $parameters{namespace}ElementFactory_h |  | 
| 901 |  | 
| 902 #include "wtf/Forward.h" |  | 
| 903 #include "wtf/PassRefPtr.h" |  | 
| 904 |  | 
| 905 namespace WebCore { |  | 
| 906     class Element; |  | 
| 907     class Document; |  | 
| 908     class QualifiedName; |  | 
| 909 } |  | 
| 910 |  | 
| 911 namespace WebCore { |  | 
| 912 |  | 
| 913     class $parameters{namespace}Element; |  | 
| 914 END |  | 
| 915 ; |  | 
| 916 |  | 
| 917 print F "     class HTMLFormElement;\n" if $parameters{namespace} eq "HTML"; |  | 
| 918 |  | 
| 919 print F<<END |  | 
| 920     // The idea behind this class is that there will eventually be a mapping fro
      m namespace URIs to ElementFactories that can dispense |  | 
| 921     // elements. In a compound document world, the generic createElement functio
      n (will end up being virtual) will be called. |  | 
| 922     class $parameters{namespace}ElementFactory { |  | 
| 923     public: |  | 
| 924         PassRefPtr<Element> createElement(const WebCore::QualifiedName&, WebCore
      ::Document*, bool createdByParser = true); |  | 
| 925 END |  | 
| 926 ; |  | 
| 927 print F "        static PassRefPtr<$parameters{namespace}Element> create$paramet
      ers{namespace}Element(const WebCore::QualifiedName&, WebCore::Document*"; |  | 
| 928 print F ", HTMLFormElement* = 0" if $parameters{namespace} eq "HTML"; |  | 
| 929 print F ", bool createdByParser = true);\n"; |  | 
| 930 |  | 
| 931 printf F<<END |  | 
| 932     }; |  | 
| 933 } |  | 
| 934 |  | 
| 935 #endif // $parameters{namespace}ElementFactory_h |  | 
| 936 |  | 
| 937 END |  | 
| 938 ; |  | 
| 939 |  | 
| 940     close F; |  | 
| 941 } |  | 
| 942 |  | 
| 943 ## Wrapper Factory routines |  | 
| 944 |  | 
| 945 sub usesDefaultJSWrapper |  | 
| 946 { |  | 
| 947     my $name = shift; |  | 
| 948 |  | 
| 949     # A tag reuses the default wrapper if its JSInterfaceName matches the defaul
      t namespace Element. |  | 
| 950     return $enabledTags{$name}{JSInterfaceName} eq $parameters{namespace} . "Ele
      ment"; |  | 
| 951 } |  | 
| 952 |  | 
| 953 sub printWrapperFunctions |  | 
| 954 { |  | 
| 955     my $F = shift; |  | 
| 956 |  | 
| 957     my %tagsSeen; |  | 
| 958     for my $tagName (sort keys %enabledTags) { |  | 
| 959         # Avoid defining the same wrapper method twice. |  | 
| 960         my $JSInterfaceName = $enabledTags{$tagName}{JSInterfaceName}; |  | 
| 961         next if defined($tagsSeen{$JSInterfaceName}) || (usesDefaultJSWrapper($t
      agName) && ($parameters{fallbackJSInterfaceName} eq $parameters{namespace} . "El
      ement")); |  | 
| 962         $tagsSeen{$JSInterfaceName} = 1; |  | 
| 963 |  | 
| 964         my $conditional = $enabledTags{$tagName}{conditional}; |  | 
| 965         if ($conditional) { |  | 
| 966             my $conditionalString = "ENABLE(" . join(") && ENABLE(", split(/&/, 
      $conditional)) . ")"; |  | 
| 967             print F "#if ${conditionalString}\n\n"; |  | 
| 968         } |  | 
| 969 |  | 
| 970         if ($enabledTags{$tagName}{wrapperOnlyIfMediaIsAvailable}) { |  | 
| 971             print F <<END |  | 
| 972 static v8::Handle<v8::Object> create${JSInterfaceName}Wrapper($parameters{namesp
      ace}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isola
      te) |  | 
| 973 { |  | 
| 974     Settings* settings = element->document().settings(); |  | 
| 975     if (!RuntimeEnabledFeatures::mediaEnabled() || (settings && !settings->media
      Enabled())) |  | 
| 976         return createV8$parameters{namespace}FallbackWrapper(to$parameters{fallb
      ackInterfaceName}(element), creationContext, isolate); |  | 
| 977     return wrap(static_cast<${JSInterfaceName}*>(element), creationContext, isol
      ate); |  | 
| 978 } |  | 
| 979 |  | 
| 980 END |  | 
| 981 ; |  | 
| 982         } elsif ($enabledTags{$tagName}{contextConditional}) { |  | 
| 983             my $contextConditional = $enabledTags{$tagName}{contextConditional}; |  | 
| 984             print F <<END |  | 
| 985 static v8::Handle<v8::Object> create${JSInterfaceName}Wrapper($parameters{namesp
      ace}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isola
      te) |  | 
| 986 { |  | 
| 987     if (!ContextFeatures::${contextConditional}Enabled(&element->document())) |  | 
| 988         return createV8$parameters{namespace}FallbackWrapper(to$parameters{fallb
      ackInterfaceName}(element), creationContext, isolate); |  | 
| 989     return wrap(static_cast<${JSInterfaceName}*>(element), creationContext, isol
      ate); |  | 
| 990 } |  | 
| 991 END |  | 
| 992 ; |  | 
| 993         } elsif ($enabledTags{$tagName}{runtimeConditional}) { |  | 
| 994             my $runtimeConditional = $enabledTags{$tagName}{runtimeConditional}; |  | 
| 995             print F <<END |  | 
| 996 static v8::Handle<v8::Object> create${JSInterfaceName}Wrapper($parameters{namesp
      ace}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isola
      te) |  | 
| 997 { |  | 
| 998     if (!RuntimeEnabledFeatures::${runtimeConditional}Enabled()) |  | 
| 999         return createV8$parameters{namespace}FallbackWrapper(to$parameters{fallb
      ackInterfaceName}(element), creationContext, isolate); |  | 
| 1000     return wrap(static_cast<${JSInterfaceName}*>(element), creationContext, isol
      ate); |  | 
| 1001 } |  | 
| 1002 END |  | 
| 1003 ; |  | 
| 1004         } elsif (${JSInterfaceName} eq "HTMLElement") { |  | 
| 1005             print F <<END |  | 
| 1006 static v8::Handle<v8::Object> create${JSInterfaceName}Wrapper($parameters{namesp
      ace}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isola
      te) |  | 
| 1007 { |  | 
| 1008     ASSERT_NOT_REACHED(); |  | 
| 1009     return v8::Handle<v8::Object>(); |  | 
| 1010 } |  | 
| 1011 |  | 
| 1012 END |  | 
| 1013 ; |  | 
| 1014         } else { |  | 
| 1015             print F <<END |  | 
| 1016 static v8::Handle<v8::Object> create${JSInterfaceName}Wrapper($parameters{namesp
      ace}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isola
      te) |  | 
| 1017 { |  | 
| 1018     return wrap(static_cast<${JSInterfaceName}*>(element), creationContext, isol
      ate); |  | 
| 1019 } |  | 
| 1020 |  | 
| 1021 |  | 
| 1022 END |  | 
| 1023 ; |  | 
| 1024         } |  | 
| 1025 |  | 
| 1026         if ($conditional) { |  | 
| 1027             print F "#endif\n\n"; |  | 
| 1028         } |  | 
| 1029     } |  | 
| 1030 } |  | 
| 1031 |  | 
| 1032 sub printWrapperFactoryCppFile |  | 
| 1033 { |  | 
| 1034     my $outputDir = shift; |  | 
| 1035     my $wrapperFactoryFileName = shift; |  | 
| 1036     my $F; |  | 
| 1037     open F, ">" . $outputDir . "/V8" . $wrapperFactoryFileName . ".cpp"; |  | 
| 1038 |  | 
| 1039     printLicenseHeader($F); |  | 
| 1040 |  | 
| 1041     print F "#include \"config.h\"\n"; |  | 
| 1042     print F "#include \"V8$parameters{namespace}ElementWrapperFactory.h\"\n"; |  | 
| 1043 |  | 
| 1044     print F "\n#if $parameters{guardFactoryWith}\n\n" if $parameters{guardFactor
      yWith}; |  | 
| 1045 |  | 
| 1046     printJSElementIncludes($F); |  | 
| 1047 |  | 
| 1048     print F "\n#include \"$parameters{namespace}Names.h\"\n\n"; |  | 
| 1049 |  | 
| 1050     printElementIncludes($F); |  | 
| 1051 |  | 
| 1052     print F "\n#include \"wtf/StdLibExtras.h\"\n"; |  | 
| 1053 |  | 
| 1054     printConditionalElementIncludes($F, 1); |  | 
| 1055 |  | 
| 1056     print F <<END |  | 
| 1057 |  | 
| 1058 #include "RuntimeEnabledFeatures.h" |  | 
| 1059 #include "core/dom/ContextFeatures.h" |  | 
| 1060 #include "core/dom/Document.h" |  | 
| 1061 #include "core/page/Settings.h" |  | 
| 1062 |  | 
| 1063 #include "V8$parameters{namespace}Element.h" |  | 
| 1064 |  | 
| 1065 #include "bindings/v8/CustomElementWrapper.h" |  | 
| 1066 |  | 
| 1067 #include <v8.h> |  | 
| 1068 |  | 
| 1069 namespace WebCore { |  | 
| 1070 |  | 
| 1071 using namespace $parameters{namespace}Names; |  | 
| 1072 |  | 
| 1073 typedef v8::Handle<v8::Object> (*Create$parameters{namespace}ElementWrapperFunct
      ion)($parameters{namespace}Element*, v8::Handle<v8::Object> creationContext, v8:
      :Isolate*); |  | 
| 1074 |  | 
| 1075 END |  | 
| 1076 ; |  | 
| 1077 |  | 
| 1078     printWrapperFunctions($F); |  | 
| 1079 |  | 
| 1080     print F <<END |  | 
| 1081 v8::Handle<v8::Object> createV8$parameters{namespace}Wrapper($parameters{namespa
      ce}Element* element, v8::Handle<v8::Object> creationContext, v8::Isolate* isolat
      e) |  | 
| 1082 { |  | 
| 1083     typedef HashMap<WTF::StringImpl*, Create$parameters{namespace}ElementWrapper
      Function> FunctionMap; |  | 
| 1084     DEFINE_STATIC_LOCAL(FunctionMap, map, ()); |  | 
| 1085     if (map.isEmpty()) { |  | 
| 1086 END |  | 
| 1087 ; |  | 
| 1088 |  | 
| 1089     for my $tag (sort keys %enabledTags) { |  | 
| 1090         # Do not add the name to the map if it does not have a JS wrapper constr
      uctor or uses the default wrapper. |  | 
| 1091         next if (usesDefaultJSWrapper($tag, \%enabledTags) && ($parameters{fallb
      ackJSInterfaceName} eq $parameters{namespace} . "Element")); |  | 
| 1092 |  | 
| 1093         my $conditional = $enabledTags{$tag}{conditional}; |  | 
| 1094         if ($conditional) { |  | 
| 1095             my $conditionalString = "ENABLE(" . join(") && ENABLE(", split(/&/, 
      $conditional)) . ")"; |  | 
| 1096             print F "#if ${conditionalString}\n"; |  | 
| 1097         } |  | 
| 1098 |  | 
| 1099         my $ucTag = $enabledTags{$tag}{JSInterfaceName}; |  | 
| 1100         print F "       map.set(${tag}Tag.localName().impl(), create${ucTag}Wrap
      per);\n"; |  | 
| 1101 |  | 
| 1102         if ($conditional) { |  | 
| 1103             print F "#endif\n"; |  | 
| 1104         } |  | 
| 1105     } |  | 
| 1106 |  | 
| 1107     print F <<END |  | 
| 1108     } |  | 
| 1109 |  | 
| 1110     Create$parameters{namespace}ElementWrapperFunction createWrapperFunction = m
      ap.get(element->localName().impl()); |  | 
| 1111 END |  | 
| 1112 ; |  | 
| 1113     if ($parameters{namespace} eq "HTML") { |  | 
| 1114         print F <<END |  | 
| 1115     if (createWrapperFunction == createHTMLElementWrapper) |  | 
| 1116         createWrapperFunction = createV8HTMLDirectWrapper; |  | 
| 1117 END |  | 
| 1118 ; |  | 
| 1119     } |  | 
| 1120     print F <<END |  | 
| 1121     if (element->isCustomElement()) |  | 
| 1122         return CustomElementWrapper<$parameters{namespace}Element, V8$parameters
      {namespace}Element>::wrap(element, creationContext, isolate, createWrapperFuncti
      on); |  | 
| 1123 |  | 
| 1124     if (createWrapperFunction) |  | 
| 1125         return createWrapperFunction(element, creationContext, isolate); |  | 
| 1126 END |  | 
| 1127 ; |  | 
| 1128     if ($parameters{namespace} eq "SVG") { |  | 
| 1129         print F <<END |  | 
| 1130     return V8SVGElement::createWrapper(element, creationContext, isolate); |  | 
| 1131 END |  | 
| 1132 ; |  | 
| 1133     } else { |  | 
| 1134         print F <<END |  | 
| 1135     return wrap(to$parameters{fallbackInterfaceName}(element), creationContext, 
      isolate); |  | 
| 1136 END |  | 
| 1137 ; |  | 
| 1138     } |  | 
| 1139 |  | 
| 1140     my $fallbackWrapper = $parameters{fallbackInterfaceName}; |  | 
| 1141     if ($parameters{namespace} eq "SVG") { |  | 
| 1142         $fallbackWrapper = "SVGElement"; |  | 
| 1143     } |  | 
| 1144 |  | 
| 1145     print F <<END |  | 
| 1146 } |  | 
| 1147 |  | 
| 1148 WrapperTypeInfo* findWrapperTypeFor$parameters{namespace}TagName(const AtomicStr
      ing& name) |  | 
| 1149 { |  | 
| 1150     typedef HashMap<WTF::StringImpl*, WrapperTypeInfo*> NameTypeMap; |  | 
| 1151     DEFINE_STATIC_LOCAL(NameTypeMap, map, ()); |  | 
| 1152     if (map.isEmpty()) { |  | 
| 1153 END |  | 
| 1154 ; |  | 
| 1155 |  | 
| 1156     for my $tagName (sort keys %enabledTags) { |  | 
| 1157         if (!usesDefaultJSWrapper($tagName)) { |  | 
| 1158             my $conditional = $enabledTags{$tagName}{conditional}; |  | 
| 1159             if ($conditional) { |  | 
| 1160                 my $conditionalString = "ENABLE(" . join(") && ENABLE(", split(/
      &/, $conditional)) . ")"; |  | 
| 1161                 print F "#if ${conditionalString}\n"; |  | 
| 1162             } |  | 
| 1163 |  | 
| 1164             my $JSInterfaceName = $enabledTags{$tagName}{JSInterfaceName}; |  | 
| 1165             print F "       map.set(${tagName}Tag.localName().impl(), WrapperTyp
      eTraits<${JSInterfaceName}>::info());\n"; |  | 
| 1166 |  | 
| 1167             if ($conditional) { |  | 
| 1168                 print F "#endif\n"; |  | 
| 1169             } |  | 
| 1170         } |  | 
| 1171     } |  | 
| 1172 |  | 
| 1173     print F <<END |  | 
| 1174     } |  | 
| 1175 |  | 
| 1176     if (WrapperTypeInfo* result = map.get(name.impl())) |  | 
| 1177         return result; |  | 
| 1178 |  | 
| 1179     return WrapperTypeTraits<$fallbackWrapper>::info(); |  | 
| 1180 } |  | 
| 1181 |  | 
| 1182 END |  | 
| 1183 ; |  | 
| 1184 |  | 
| 1185     print F "}\n\n"; |  | 
| 1186     print F "#endif\n" if $parameters{guardFactoryWith}; |  | 
| 1187 |  | 
| 1188     close F; |  | 
| 1189 } |  | 
| 1190 |  | 
| 1191 sub printWrapperFactoryHeaderFile |  | 
| 1192 { |  | 
| 1193     my $outputDir = shift; |  | 
| 1194     my $wrapperFactoryFileName = shift; |  | 
| 1195     my $F; |  | 
| 1196     open F, ">" . $outputDir . "/V8" . $wrapperFactoryFileName . ".h"; |  | 
| 1197 |  | 
| 1198     printLicenseHeader($F); |  | 
| 1199 |  | 
| 1200     print F "#ifndef V8$parameters{namespace}ElementWrapperFactory_h\n"; |  | 
| 1201     print F "#define V8$parameters{namespace}ElementWrapperFactory_h\n\n"; |  | 
| 1202 |  | 
| 1203     print F "#if $parameters{guardFactoryWith}\n" if $parameters{guardFactoryWit
      h}; |  | 
| 1204 |  | 
| 1205     print F <<END |  | 
| 1206 #include <V8$parameters{namespace}Element.h> |  | 
| 1207 #include <V8$parameters{fallbackJSInterfaceName}.h> |  | 
| 1208 #include <v8.h> |  | 
| 1209 |  | 
| 1210 namespace WebCore { |  | 
| 1211 |  | 
| 1212     class $parameters{namespace}Element; |  | 
| 1213 |  | 
| 1214     WrapperTypeInfo* findWrapperTypeFor$parameters{namespace}TagName(const Atomi
      cString& name); |  | 
| 1215 |  | 
| 1216     v8::Handle<v8::Object> createV8$parameters{namespace}Wrapper($parameters{nam
      espace}Element*, v8::Handle<v8::Object> creationContext, v8::Isolate*); |  | 
| 1217     inline v8::Handle<v8::Object> createV8$parameters{namespace}DirectWrapper($p
      arameters{namespace}Element* element, v8::Handle<v8::Object> creationContext, v8
      ::Isolate* isolate) |  | 
| 1218     { |  | 
| 1219         return V8$parameters{namespace}Element::createWrapper(element, creationC
      ontext, isolate); |  | 
| 1220     } |  | 
| 1221     inline v8::Handle<v8::Object> createV8$parameters{namespace}FallbackWrapper(
      $parameters{fallbackJSInterfaceName}* element, v8::Handle<v8::Object> creationCo
      ntext, v8::Isolate* isolate) |  | 
| 1222     { |  | 
| 1223         return V8$parameters{fallbackJSInterfaceName}::createWrapper(element, cr
      eationContext, isolate); |  | 
| 1224     } |  | 
| 1225 } |  | 
| 1226 END |  | 
| 1227 ; |  | 
| 1228     print F "#endif // $parameters{guardFactoryWith}\n\n" if $parameters{guardFa
      ctoryWith}; |  | 
| 1229 |  | 
| 1230     print F "#endif // V8$parameters{namespace}ElementWrapperFactory_h\n"; |  | 
| 1231 |  | 
| 1232     close F; |  | 
| 1233 } |  | 
| 1234 |  | 
| 1235 sub createGenericNamesFile |  | 
| 1236 { |  | 
| 1237     my $inputName = shift; |  | 
| 1238     my $baseName = shift; |  | 
| 1239     my $basePrefix = shift; |  | 
| 1240 |  | 
| 1241     my $names = new IO::File; |  | 
| 1242     open($names, $inputName) or die "Failed to open file: $inputName"; |  | 
| 1243 |  | 
| 1244     $initDefaults = 0; |  | 
| 1245     my $Parser = InFilesParser->new(); |  | 
| 1246     my $dummy; |  | 
| 1247     $Parser->parse($names, \¶metersHandler, \&dummy); |  | 
| 1248 |  | 
| 1249     my $F; |  | 
| 1250     my $header = File::Spec->catfile($outputDir, "${baseName}Names.h"); |  | 
| 1251     open F, ">$header" or die "Unable to open $header for writing."; |  | 
| 1252 |  | 
| 1253     printLicenseHeader($F); |  | 
| 1254     printHeaderHead($F, $basePrefix, $baseName, "#include \"wtf/text/AtomicStrin
      g.h\""); |  | 
| 1255 |  | 
| 1256     printMacros($F, "extern const WTF::AtomicString", "", \%parameters); |  | 
| 1257     print F "#endif\n\n"; |  | 
| 1258 |  | 
| 1259     printInit($F, 1); |  | 
| 1260     close F; |  | 
| 1261 |  | 
| 1262     my $source = File::Spec->catfile($outputDir, "${baseName}Names.cpp"); |  | 
| 1263     open F, ">$source" or die "Unable to open $source for writing."; |  | 
| 1264 |  | 
| 1265     printLicenseHeader($F); |  | 
| 1266     printCppHead($F, $basePrefix, $baseName, "WTF"); |  | 
| 1267 |  | 
| 1268     while ( my ($name, $identifier) = each %parameters ) { |  | 
| 1269         print F "DEFINE_GLOBAL(AtomicString, $name)\n"; |  | 
| 1270     } |  | 
| 1271 |  | 
| 1272     printInit($F, 0); |  | 
| 1273 |  | 
| 1274     print F "\n"; |  | 
| 1275     print F StaticString::GenerateStringImpls(\%parameters); |  | 
| 1276 |  | 
| 1277     while ( my ($name, $identifier) = each %parameters ) { |  | 
| 1278         print F "    new ((void*)&$name) AtomicString(${name}Impl);\n"; |  | 
| 1279     } |  | 
| 1280 |  | 
| 1281     print F "}\n}\n}\n"; |  | 
| 1282     close F; |  | 
| 1283     exit 0; |  | 
| 1284 } |  | 
| OLD | NEW | 
|---|