All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
icarusalg/icarusalg/Geometry/gdml/make_gdml.pl
Go to the documentation of this file.
1 #!/usr/bin/perl
2 # Heavily revised Jan-2010 <seligman@nevis.columbia.edu>
3 
4 #
5 # Build a description of the detectors from gdml fragments
6 #
7 
8 # Use the command line arguments to give us the list of file fragments
9 # that we'll zip together. The man page for 'GetOptions' can be read
10 # with: perldoc Getopt::Long
11 
12 use Getopt::Long;
13 GetOptions( "input|i:s" => \$input,
14  "help|h" => \$help,
15  "output|o:s" => \$output);
16 
17 if ( defined $help )
18 {
19  # If the user requested help, print the usage notes and exit.
20  usage();
21  exit;
22 }
23 
24 if ( ! defined $input )
25 {
26  # If the user has not used "-i", then just take the first
27  # non-option argument.
28  if ( $#ARGV > -1 )
29  {
30  $input = $ARGV[0];
31  if ( ! -r $input )
32  {
33  print "Input file $input not found\n";
34  usage();
35  exit;
36  }
37  }
38  else
39  {
40  # Read from STDIN
41  $input = "-";
42  }
43 }
44 else
45 {
46  # The "-i" option was provided; check that the input file exists.
47  if ( ! -r $input )
48  {
49  print "Input file $input not found or cannot be read\n";
50  usage();
51  exit;
52  }
53 }
54 
55 if ( ! defined $output )
56 {
57  $output = "-"; # write to STDOUT
58 }
59 
60 # Read the list of file fragments from an XML-formatted file.
61 # (Type "perldoc XML::LibXML" for how to use this package.)
62 
63 use XML::LibXML;
64 # Create an XML parser.
65 $parser = new XML::LibXML;
66 
67 # Read the XML file. The entire contents are slurped into a DOM
68 # structure.
69 $dom = $parser->parse_file($input);
70 
71 # Note that @defFiles and @gdmlFiles are both arrays of "nodes".
72 @defFiles = $dom->findnodes('/config/constantfiles/filename');
73 @gdmlFiles = $dom->findnodes('/config/gdmlfiles/filename');
74 
75 # Keep track of how many constants we read in.
77 
78 # Developer note: If I were slicker, I'd also use XML::LibXML to read
79 # in these GDML fragments. However, the files would have to be edited
80 # to be strict XML, and that's more effort than it's worth. The script
81 # generate_gdml.pl writes strict XML documents, but there's no
82 # guarantee that this program will be used just with those
83 # files.
84 
85 #
86 # Build the table of variable replacements
87 #
88 
89 # For each node that represents a file of constants...
90 foreach $filename (@defFiles)
91 {
92  $CONSTANTS = $filename->to_literal;
93  open(CONSTANTS) or die("Could not open file $CONSTANTS");
94 
95  # For each line in the file...
96  foreach $line (<CONSTANTS>)
97  {
98  # Find the name and value as defined in a <constant> block; e.g.:
99  # <constant name="kInch" value="2.54" />
100  # will be parsed as $name="kInch" and value = "2.54"
101 
102  # If the line begins with "<constant"...
103  if ( $line =~ /^\s*\<constant / )
104  {
105  # (See "perldoc perlfaq6" for the definition of a non-greedy search.)
106  # Do a "non-greedy" search to get the text assigned to 'name'
107  $line =~ /name="(.*?)"/;
108  $name = $1;
109  # Do a "non-greedy" search to get the text assigned to 'value'
110  $line =~ /value="(.*?)"/;
111  $value = $1;
112 
113  # Append to the list of constants. Put parenthesis around
114  # the value, to avoid potential problems with arithmetic.
116  $name[$numberConstants] = $name;
117  $value[$numberConstants] = "($value)";
118  # print "$numberConstants: $name = $value[$numberConstants]\n"; # debug
119  }
120  }
121  close(CONSTANTS);
122 }
123 
124 # The main GDML keywords, used in tags. The order here is important:
125 # No matter what order these blocks are in the sub-files, this is the
126 # order in which they must be written in the final GDML output.
127 
128 # If I were being super-slick, I'd use the features of LibXML to read
129 # each of these GDML sub-files, then fiddle with the elements using
130 # XML manipulation routines. However, it's much simpler to treat them
131 # as big globs of text.
132 
133 @keywords = qw( define materials solids structure );
134 
135 # For each node that's a file of GDML statements...
136 foreach $filename ( @gdmlFiles )
137 {
138 
139  # Open the file.
140  $FILE = $filename->to_literal;
141  open(FILE) or die("Could not open file $FILE for read.");
142 
143  # Read the entire file into an array.
144  @file = <FILE>;
145  close(FILE);
146 
147  # Slurp the array into a single variable.
148  $file = join("",@file);
149 
150  foreach $keyword ( @keywords )
151  {
152  # Search the file for a keyword block. For example, if
153  # $keyword were "blorg", the following would search for
154  # <blorg>some text</blorg> and snip it out of $file.
155  while ( $file =~ s/(.*)\<$keyword\>(.*?)\<\/$keyword\>(.*)/\1\3/s )
156  {
157  # Following the above example, this would append "some
158  # text" to $keyhash{blorg}
159 
160  $keyhash{$keyword} = $keyhash{$keyword} . $2;
161  }
162  }
163 }
164 
165 # Write the final GDML file.
166 
167 $OUTPUT = ">" . $output;
168 open(OUTPUT) or die("Could not open $output for writing");
169 
170 # The preliminary material for the GDML file. This defines the GDML
171 # schema and namespaces.
172 
173 print OUTPUT <<EOF;
174 <?xml version="1.0" encoding="UTF-8" ?>
175 <gdml xmlns:gdml="http://cern.ch/2001/Schemas/GDML"
176  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
177  xsi:noNamespaceSchemaLocation="GDMLSchema/gdml.xsd">
178 EOF
179 
180 # Print to OUTPUT all the GDML sections, with each set of tags
181 # unified, in the appropriate order.
182 
183 foreach $keyword ( @keywords )
184 {
185  print OUTPUT "<$keyword>";
186 
187  # Substitute any constants in the GDML with their numeric
188  # equivalents.
189 
190  # In strict GDML, this should not be necessary; according to the
191  # specification, you should be able to define a constant and use
192  # it in subsequent GDML statements. If you use the standard GDML
193  # parser, this not a problem. ROOT, however, uses its own parser,
194  # and (as of ROOT 5.16) it could not handle variables in GDML
195  # expressions. So here we side-step the problem by performing our
196  # own substitutions.
197 
198  # Step through this list of constants in reverse order, to resolve
199  # any dependencies.
200 
201  for ( $i = $numberConstants; $i >= 0; --$i )
202  {
203  $keyhash{$keyword} =~ s/$name[$i]/$value[$i]/g;
204  }
205 
206  # Print the edited section.
207  print OUTPUT $keyhash{$keyword};
208 
209  print OUTPUT "</$keyword>\n";
210 }
211 
212 # The final section of a GDML file is the <setup></setup> section. At
213 # present, we don't define alternate setups in the same GDML file, so
214 # these lines are constant.
215 
216 print OUTPUT <<EOF;
217 
218 <setup name="Default" version="1.0">
219  <world ref="volWorld" />
220 </setup>
221 
222 </gdml>
223 EOF
224 
225 close(OUTPUT);
226 
227 
229 {
230  print "Usage: $0 [-h|--help] [-i|--input <xml-fragments-file>] [-o|--output <output-file>]\n";
231  print " -i/--input can be omitted; if no input file, defaults to STDIN\n";
232  print " if -o is omitted, output goes to STDOUT\n";
233  print " -h prints this message, then quits\n";
234 }
then source grid fermiapp products dune setup_dune_fermiapp sh exit else echo No setup file found exit fi setup
use File::Basename qw(fileparse)
foreach $filename(@defFiles)
process_name can override from command line with o or output proton mvapid_weights muon_all_BDT weights xml
Definition: runPID.fcl:28
* file
Definition: file_to_url.sh:69
GetOptions("help|h"=>\$help,"suffix|s:s"=>\$suffix,"output|o:s"=>\$output,"concrete|c:s"=>\$thickness_over,"wires|w:s"=>\$wires,"vetocrt|v:s"=>\$crt)
do one_file $F done echo for F in find $TOP name CMakeLists txt print
def write
Definition: util.py:23
BEGIN_PROLOG g
usage
Definition: doGit.sh:21
S join(S const &sep, Coll const &s)
Returns a concatenation of strings in s separated by sep.
for($it=0;$it< $RaceTrack_number;$it++)
then echo echo For and will not be changed by echo further linking echo echo B echo The symbol is in the uninitialized data multiple common symbols may appear with the echo same name If the symbol is defined the common echo symbols are treated as undefined references For more echo details on common see the discussion of warn common echo in *Note Linker see the discussion of warn common echo in *Note Linker such as a global int variable echo as opposed to a large global array echo echo I echo The symbol is an indirect reference to another symbol This echo is a GNU extension to the a out object file format which is echo rarely used echo echo N echo The symbol is a debugging symbol echo echo R echo The symbol is in a read only data section echo echo S echo The symbol is in an uninitialized data section for small echo objects echo echo T echo The symbol is in the the normal defined echo symbol is used with no error When a weak undefined symbol echo is linked and the symbol is not defined
then echo File list $list not found else cat $list while read file do echo $file sed s
Definition: file_to_url.sh:60
do echo $i
Definition: TrainMVA.sh:30
print OUTPUT<< EOF;<?xml version="1.0"encoding="UTF-8"?>< gdmlxmlns:gdml="http:xmlns:xsi="http:xsi:noNamespaceSchemaLocation="GDMLSchema/gdml.xsd"> EOF foreach $keyword(@keywords)
then echo fcl name
temporary value
print OUTPUT<< EOF;< setup name="Default"version="1.0">< worldref="volWorld"/></setup ></gdml > EOF close(OUTPUT)
esac echo uname r
std::string sub(const std::string &a, const std::string &b)
Definition: TruthText.cxx:100
open(RACETRACK) or die("Could not open file $RACETRACK for writing")