OLD | NEW |
1 #!/usr/bin/perl -w | 1 #!/usr/bin/perl -w |
2 # | 2 # |
3 # Copyright (C) 2011 Google Inc. All rights reserved. | 3 # Copyright (C) 2011 Google Inc. All rights reserved. |
4 # | 4 # |
5 # This library is free software; you can redistribute it and/or | 5 # This library is free software; you can redistribute it and/or |
6 # modify it under the terms of the GNU Library General Public | 6 # modify it under the terms of the GNU Library General Public |
7 # License as published by the Free Software Foundation; either | 7 # License as published by the Free Software Foundation; either |
8 # version 2 of the License, or (at your option) any later version. | 8 # version 2 of the License, or (at your option) any later version. |
9 # | 9 # |
10 # This library is distributed in the hope that it will be useful, | 10 # This library is distributed in the hope that it will be useful, |
(...skipping 10 matching lines...) Expand all Loading... |
21 use strict; | 21 use strict; |
22 | 22 |
23 use File::Basename; | 23 use File::Basename; |
24 use Getopt::Long; | 24 use Getopt::Long; |
25 use Cwd; | 25 use Cwd; |
26 | 26 |
27 my $defines; | 27 my $defines; |
28 my $preprocessor; | 28 my $preprocessor; |
29 my $idlFilesList; | 29 my $idlFilesList; |
30 my $supplementalDependencyFile; | 30 my $supplementalDependencyFile; |
| 31 my $windowConstructorsFile; |
31 | 32 |
32 GetOptions('defines=s' => \$defines, | 33 GetOptions('defines=s' => \$defines, |
33 'preprocessor=s' => \$preprocessor, | 34 'preprocessor=s' => \$preprocessor, |
34 'idlFilesList=s' => \$idlFilesList, | 35 'idlFilesList=s' => \$idlFilesList, |
35 'supplementalDependencyFile=s' => \$supplementalDependencyFile); | 36 'supplementalDependencyFile=s' => \$supplementalDependencyFile, |
| 37 'windowConstructorsFile=s' => \$windowConstructorsFile); |
36 | 38 |
37 die('Must specify an output file using --supplementalDependencyFile.') unless de
fined($supplementalDependencyFile); | 39 die('Must specify an output file using --supplementalDependencyFile.') unless de
fined($supplementalDependencyFile); |
| 40 die('Must specify an output file using --windowConstructorsFile.') unless define
d($windowConstructorsFile); |
38 die('Must specify the file listing all IDLs using --idlFilesList.') unless defin
ed($idlFilesList); | 41 die('Must specify the file listing all IDLs using --idlFilesList.') unless defin
ed($idlFilesList); |
39 | 42 |
40 open FH, "< $idlFilesList" or die "Cannot open $idlFilesList\n"; | 43 open FH, "< $idlFilesList" or die "Cannot open $idlFilesList\n"; |
41 my @idlFiles = <FH>; | 44 my @idlFiles = <FH>; |
42 chomp(@idlFiles); | 45 chomp(@idlFiles); |
43 close FH; | 46 close FH; |
44 | 47 |
45 # Parse all IDL files. | 48 # Parse all IDL files. |
46 my %interfaceNameToIdlFile; | 49 my %interfaceNameToIdlFile; |
47 my %idlFileToInterfaceName; | 50 my %idlFileToInterfaceName; |
48 my %supplementalDependencies; | 51 my %supplementalDependencies; |
49 my %supplementals; | 52 my %supplementals; |
| 53 my $constructorAttributesCode = ""; |
50 foreach my $idlFile (@idlFiles) { | 54 foreach my $idlFile (@idlFiles) { |
51 my $fullPath = Cwd::realpath($idlFile); | 55 my $fullPath = Cwd::realpath($idlFile); |
52 my $partialInterfaceName = getPartialInterfaceNameFromIDLFile($fullPath); | 56 my $idlFileContents = getFileContents($fullPath); |
| 57 my $partialInterfaceName = getPartialInterfaceNameFromIDL($idlFileContents); |
53 if ($partialInterfaceName) { | 58 if ($partialInterfaceName) { |
54 $supplementalDependencies{$fullPath} = $partialInterfaceName; | 59 $supplementalDependencies{$fullPath} = $partialInterfaceName; |
| 60 next; |
55 } | 61 } |
56 my $interfaceName = fileparse(basename($idlFile), ".idl"); | 62 my $interfaceName = fileparse(basename($idlFile), ".idl"); |
| 63 unless (isCallbackInterfaceFromIDL($idlFileContents)) { |
| 64 my $extendedAttributes = getInterfaceExtendedAttributesFromIDL($idlFileC
ontents); |
| 65 unless ($extendedAttributes->{"NoInterfaceObject"}) { |
| 66 $constructorAttributesCode .= GenerateConstructorAttribute($interfac
eName, $extendedAttributes); |
| 67 } |
| 68 } |
57 $interfaceNameToIdlFile{$interfaceName} = $fullPath; | 69 $interfaceNameToIdlFile{$interfaceName} = $fullPath; |
58 $idlFileToInterfaceName{$fullPath} = $interfaceName; | 70 $idlFileToInterfaceName{$fullPath} = $interfaceName; |
59 $supplementals{$fullPath} = []; | 71 $supplementals{$fullPath} = []; |
60 } | 72 } |
61 | 73 |
| 74 # Generate DOMWindow Constructors partial interface. |
| 75 open PARTIAL_WINDOW_FH, "> $windowConstructorsFile" or die "Cannot open $windowC
onstructorsFile\n"; |
| 76 print PARTIAL_WINDOW_FH "partial interface DOMWindow {\n"; |
| 77 print PARTIAL_WINDOW_FH $constructorAttributesCode; |
| 78 print PARTIAL_WINDOW_FH "};\n"; |
| 79 close PARTIAL_WINDOW_FH; |
| 80 $supplementalDependencies{$windowConstructorsFile} = "DOMWindow"; |
| 81 |
62 # Resolves partial interfaces dependencies. | 82 # Resolves partial interfaces dependencies. |
63 foreach my $idlFile (keys %supplementalDependencies) { | 83 foreach my $idlFile (keys %supplementalDependencies) { |
64 my $baseFile = $supplementalDependencies{$idlFile}; | 84 my $baseFile = $supplementalDependencies{$idlFile}; |
65 my $targetIdlFile = $interfaceNameToIdlFile{$baseFile}; | 85 my $targetIdlFile = $interfaceNameToIdlFile{$baseFile}; |
66 push(@{$supplementals{$targetIdlFile}}, $idlFile); | 86 push(@{$supplementals{$targetIdlFile}}, $idlFile); |
67 delete $supplementals{$idlFile}; | 87 delete $supplementals{$idlFile}; |
68 } | 88 } |
69 | 89 |
70 # Outputs the dependency. | 90 # Outputs the dependency. |
71 # The format of a supplemental dependency file: | 91 # The format of a supplemental dependency file: |
72 # | 92 # |
73 # DOMWindow.idl P.idl Q.idl R.idl | 93 # DOMWindow.idl P.idl Q.idl R.idl |
74 # Document.idl S.idl | 94 # Document.idl S.idl |
75 # Event.idl | 95 # Event.idl |
76 # ... | 96 # ... |
77 # | 97 # |
78 # The above indicates that DOMWindow.idl is supplemented by P.idl, Q.idl and R.i
dl, | 98 # The above indicates that DOMWindow.idl is supplemented by P.idl, Q.idl and R.i
dl, |
79 # Document.idl is supplemented by S.idl, and Event.idl is supplemented by no IDL
s. | 99 # Document.idl is supplemented by S.idl, and Event.idl is supplemented by no IDL
s. |
80 # The IDL that supplements another IDL (e.g. P.idl) never appears in the depende
ncy file. | 100 # The IDL that supplements another IDL (e.g. P.idl) never appears in the depende
ncy file. |
81 | 101 |
82 open FH, "> $supplementalDependencyFile" or die "Cannot open $supplementalDepend
encyFile\n"; | 102 open FH, "> $supplementalDependencyFile" or die "Cannot open $supplementalDepend
encyFile\n"; |
83 | 103 |
84 foreach my $idlFile (sort keys %supplementals) { | 104 foreach my $idlFile (sort keys %supplementals) { |
85 print FH $idlFile, " @{$supplementals{$idlFile}}\n"; | 105 print FH $idlFile, " @{$supplementals{$idlFile}}\n"; |
86 } | 106 } |
87 close FH; | 107 close FH; |
88 | 108 |
89 sub getPartialInterfaceNameFromIDLFile | 109 sub GenerateConstructorAttribute |
| 110 { |
| 111 my $interfaceName = shift; |
| 112 my $extendedAttributes = shift; |
| 113 |
| 114 my $code = " "; |
| 115 my @extendedAttributesList; |
| 116 foreach my $attributeName (keys %{$extendedAttributes}) { |
| 117 next unless ($attributeName eq "Conditional" || $attributeName eq "Enabled
AtRuntime" || $attributeName eq "EnabledPerContext"); |
| 118 my $extendedAttribute = $attributeName; |
| 119 $extendedAttribute .= "=" . $extendedAttributes->{$attributeName} unless $
extendedAttributes->{$attributeName} eq "VALUE_IS_MISSING"; |
| 120 push(@extendedAttributesList, $extendedAttribute); |
| 121 } |
| 122 $code .= "[" . join(', ', @extendedAttributesList) . "] " if @extendedAttrib
utesList; |
| 123 |
| 124 my $originalInterfaceName = $interfaceName; |
| 125 $interfaceName = $extendedAttributes->{"InterfaceName"} if $extendedAttribut
es->{"InterfaceName"}; |
| 126 $code .= "attribute " . $originalInterfaceName . "Constructor $interfaceName
;\n"; |
| 127 |
| 128 # In addition to the regular property, for every [NamedConstructor] extended
attribute on an interface, |
| 129 # a corresponding property MUST exist on the ECMAScript global object. |
| 130 if ($extendedAttributes->{"NamedConstructor"}) { |
| 131 my $constructorName = $extendedAttributes->{"NamedConstructor"}; |
| 132 $constructorName =~ s/\(.*//g; # Extract function name. |
| 133 $code .= " "; |
| 134 $code .= "[" . join(', ', @extendedAttributesList) . "] " if @extendedAt
tributesList; |
| 135 $code .= "attribute " . $originalInterfaceName . "ConstructorConstructor
$constructorName;\n"; |
| 136 } |
| 137 return $code; |
| 138 } |
| 139 |
| 140 sub getFileContents |
90 { | 141 { |
91 my $idlFile = shift; | 142 my $idlFile = shift; |
92 | 143 |
93 open FILE, "<", $idlFile; | 144 open FILE, "<", $idlFile; |
94 my @lines = <FILE>; | 145 my @lines = <FILE>; |
95 close FILE; | 146 close FILE; |
96 | 147 |
97 my $fileContents = join('', @lines); | 148 # Filter out preprocessor lines. |
| 149 @lines = grep(!/^\s*#/, @lines); |
| 150 |
| 151 return join('', @lines); |
| 152 } |
| 153 |
| 154 sub getPartialInterfaceNameFromIDL |
| 155 { |
| 156 my $fileContents = shift; |
| 157 |
98 if ($fileContents =~ /partial\s+interface\s+(\w+)/gs) { | 158 if ($fileContents =~ /partial\s+interface\s+(\w+)/gs) { |
99 return $1; | 159 return $1; |
100 } | 160 } |
101 } | 161 } |
| 162 |
| 163 sub isCallbackInterfaceFromIDL |
| 164 { |
| 165 my $fileContents = shift; |
| 166 return ($fileContents =~ /callback\s+interface\s+\w+/gs); |
| 167 } |
| 168 |
| 169 sub trim |
| 170 { |
| 171 my $string = shift; |
| 172 $string =~ s/^\s+|\s+$//g; |
| 173 return $string; |
| 174 } |
| 175 |
| 176 sub getInterfaceExtendedAttributesFromIDL |
| 177 { |
| 178 my $fileContents = shift; |
| 179 |
| 180 my $extendedAttributes = {}; |
| 181 |
| 182 if ($fileContents =~ /\[(.*)\]\s+(interface|exception)\s+(\w+)/gs) { |
| 183 my @parts = split(',', $1); |
| 184 foreach my $part (@parts) { |
| 185 my @keyValue = split('=', $part); |
| 186 my $key = trim($keyValue[0]); |
| 187 next unless length($key); |
| 188 my $value = "VALUE_IS_MISSING"; |
| 189 $value = trim($keyValue[1]) if @keyValue > 1; |
| 190 $extendedAttributes->{$key} = $value; |
| 191 } |
| 192 } |
| 193 |
| 194 return $extendedAttributes; |
| 195 } |
OLD | NEW |