cloudy trunk
Loading...
Searching...
No Matches
parse_abundances.cpp
Go to the documentation of this file.
1/* This file is part of Cloudy and is copyright (C)1978-2013 by Gary J. Ferland and
2 * others. For conditions of distribution and use see copyright notice in license.txt */
3/*ParseAbundances parse and read in composition as set by abundances command */
4#include "cddefines.h"
5#include "grains.h"
6#include "grainvar.h"
7#include "abund.h"
8#include "phycon.h"
9#include "called.h"
10#include "elementnames.h"
11#include "input.h"
12#include "parser.h"
13
15 /* following set true by grains command,
16 * so this will not set more grains if grains already on. */
17{
18 bool lgLog;
19 long int i;
20 double absav[LIMELM],
21 chk;
22 GrainPar gp;
23
24 DEBUG_ENTRY( "ParseAbundances()" );
25
26 if( p.nMatch("STAR") )
27 {
28 /* Fred Hamann's star burst galaxy mixture -- includes a number which isn't an abundance */
30 return;
31 }
32
33 absav[0] = p.FFmtRead();
34 /* this branch at least one number on the line - an abundance */
35 if( !p.lgEOL() )
36 {
37 absav[1] = p.FFmtRead();
38 if( p.lgEOL() )
39 {
40 /* this branch, we found one, but not two, numbers -
41 * must be one of a few special cases */
42 if( p.nMatch(" ALL") )
43 {
44 /* special option, all abundances will be this number */
45 if( absav[0] <= 0. )
46 {
47 absav[0] = pow(10.,absav[0]);
48 }
49 for( i=1; i < LIMELM; i++ )
50 {
51 abund.solar[i] = (realnum)absav[0];
52 }
53
54 }
55 else if( p.nMatch("OLD ") && p.nMatch("SOLA") )
56 {
57 i = (int)absav[0];
58 /* old solar - better be the number "84" on the line */
59 if( i!=84 )
60 {
61 fprintf( ioQQQ,
62 " The only old abundance set I have is for version 84 - %3ld was requested. Sorry.\n",
63 i );
65 }
66 for( i=1; i < LIMELM; i++ )
67 {
68 /* these are the old abundances */
69 abund.SolarSave[i] = abund.OldSolar84[i];
70 abund.solar[i] = abund.OldSolar84[i];
71 }
72 }
73 else if( p.nMatch("GASS10"))
74 {
75 /* Grevesse, Asplund, Sauval, and Scott solar */
76 /* >>refer solar abund Grevesse, N., Asplund, M., Sauval, A. J., & Scott, P. 2010, Ap&SS, 48 */
77 for( i=1; i < LIMELM; i++ )
78 {
79 /* these are the GASS10 solar abundances */
80 abund.SolarSave[i] = abund.GASS10[i];
81 abund.solar[i] = abund.GASS10[i];
82 }
83 }
84 else
85 {
86 fprintf( ioQQQ,
87 " I did not recognize a sub-keyword - options are ALL, OLD SOLAR 84, and GASS10. Sorry.\n");
89 }
90
91 /* normal return */
92 return;
93 }
94
95 /* we get here if there is a second number - read in all abundances */
96 for( i=2; i < abund.npSolar; i++ )
97 {
98 absav[i] = p.FFmtRead();
99 if( p.lgEOL() )
100 {
101 /* read CONTINUE line if J scanned off end before reading all abund */
102 do
103 {
104 p.getline();
105 if( p.m_lgEOF )
106 {
107 fprintf( ioQQQ, " There MUST be%3ld abundances entered, there were only%3ld. Sorry.\n",
108 abund.npSolar, i );
110 }
111 } while( p.isComment() );
112
113 p.echo();
114
115 if( p.strcmp("CONT") != 0 )
116 {
117 fprintf( ioQQQ, " There MUST be%3ld abundances entered, there were only%3ld. Sorry.\n",
118 abund.npSolar, i );
120 }
121 else
122 {
123 absav[i] = p.FFmtRead();
124 if( p.lgEOL() )
125 {
126 fprintf( ioQQQ, " There MUST be%3ld abundances entered, there were only%3ld. Sorry.\n",
127 abund.npSolar, i);
129 }
130 }
131 }
132 }
133
134 /* fell through to here after reading in N abundances for N elements
135 * check that there are no more abundances on the line - that would
136 * be an error - a typo */
137 chk = p.FFmtRead();
138 if( !p.lgEOL() || (chk!=0.) )
139 {
140 /* got another number, not lgEOL, so too many numbers */
141 fprintf( ioQQQ, " There were more than %ld abundances entered\n",
142 abund.npSolar );
143 fprintf( ioQQQ, " Could there have been a typo somewhere?\n" );
144 }
145
146 /* are numbers scale factors, or log of abund rel to H?? */
147 lgLog = false;
148 for( i=0; i < abund.npSolar; i++ )
149 if( absav[i] < 0. )
150 lgLog = true;
151
152 if( lgLog )
153 {
154 /* entered as log of number rel to hydrogen */
155 for( i=0; i < abund.npSolar; i++ )
156 abund.solar[abund.ipSolar[i]-1] = (realnum)pow(10.,absav[i]);
157 }
158 else
159 {
160 /* scale factors relative to solar */
161 for( i=0; i < abund.npSolar; i++ )
162 abund.solar[abund.ipSolar[i]-1] *= (realnum)absav[i];
163 }
164
165 /* check whether the abundances are reasonable */
166 for( i=1; i < LIMELM; i++ )
167 {
168 if( abund.solar[i] > 0.2 )
169 {
170 fprintf( ioQQQ, " Is an abundance of %.3e relative to H reasonable for %2.2s?\n",
171 abund.solar[i], elementnames.chElementSym[i] );
172 }
173 }
174 return;
175 }
176
177 /* following set of clauses - no numbers on the line -
178 * use one of several stored abundance sets */
179 if( p.nMatch(" AGB") || p.nMatch("AGB ") || p.nMatch("PLAN") )
180 {
181 /* AGB/planetary nebula abundances */
182 /* only turn on grains if "no grains" is not present */
183 if( !p.nMatch("NO GR") )
184 {
185 /* turn on grains if not already done */
186 if( !p.m_lgDSet )
187 {
188 /* return bins allocated by previous abundances ... commands */
189 gv.clear();
190 /* now allocate new grain bins */
191 gp.dep = 1.;
192 // standard dust to gas ratio
194 gp.lgRequestQHeating = true;
195 gp.lgForbidQHeating = false;
196 gp.lgGreyGrain = false;
197
198 /* NO QHEAT option to turn off quantum heating for grains */
199 if( p.nMatch("NO QH") )
200 {
201 gp.lgForbidQHeating = true;
202 gp.lgRequestQHeating = false;
203 phycon.lgPhysOK = false;
204 }
205
206 /* actually set up the grains */
207 mie_read_opc("graphite_ism_10.opc",gp);
208 mie_read_opc("silicate_ism_10.opc",gp);
209 }
210 }
211
212 for( i=0; i < LIMELM; i++ )
213 {
214 abund.solar[i] = abund.apn[i];
215 if( !abund.lgElmONapn[i] )
216 {
217 /* turn off elements - do this way to make sure,
218 * that iso sequence limits are handled properly */
219 char chDUMMY[INPUT_LINE_LENGTH];
220 sprintf(chDUMMY,"element %s off ", elementnames.chElementName[i] );
221 p.setline(chDUMMY);
222 ParseElement( p );
223 }
224 }
225 }
226
227 else if( p.nMatch("CAME") )
228 {
229 /* mix from Cameron 1982, "Essays on Nuclear Astrophysics" */
230 /* now turn off the heavy elements */
231 for( i=0; i < LIMELM; i++ )
232 abund.solar[i] = abund.camern[i];
233 }
234
235 else if( p.nMatch("CRAB") )
236 {
237 // Crab Nebula "typical" abundances
238 for( i=0; i < LIMELM; i++ )
239 {
240 abund.solar[i] = abund.aCrab[i];
241 if( !abund.lgElmONaCrab[i] )
242 {
243 /* turn off elements - do this way to make sure,
244 * that iso sequence limits are handled properly */
245 char chDUMMY[INPUT_LINE_LENGTH];
246 sprintf(chDUMMY,"element %s off ", elementnames.chElementName[i] );
247 p.setline(chDUMMY);
248 ParseElement( p );
249 }
250 }
251 }
252 else if( p.nMatch("HII ") || p.nMatch("H II") || p.nMatch("ORIO") )
253 {
254 /* H II region abundances - turn on grains by default
255 * "no grains" to not do this */
256 if( !p.nMatch("NO GR") )
257 {
258 /* option to turn on grains */
259 if( !p.m_lgDSet )
260 {
261 /* return bins allocated by previous abundances ... commands */
262 gv.clear();
263 /* now allocate new grain bins */
264 gp.dep = 1.;
265 // standard dust to gas ratio
267 gp.lgRequestQHeating = true;
268 gp.lgForbidQHeating = false;
269 gp.lgGreyGrain = false;
270
271 /* NO QHEAT option to turn off quantum heating for grains */
272 if( p.nMatch("NO QH") )
273 {
274 gp.lgForbidQHeating = true;
275 gp.lgRequestQHeating = false;
276 phycon.lgPhysOK = false;
277 }
278 /* This scales the Orion grain abundance so that the observed
279 * dust to gas ratio that Cloudy predicts is in agreement with
280 * that observed in the Veil,
281 *>>refer grain Abel, N., Brogan, C., Ferland, G., O'Dell, C.R.,
282 *>>refercon Shaw, G., Troland, T., 2004, ApJ, submitted */
283 gp.dep *= 0.85;
284
285 mie_read_opc("graphite_orion_10.opc",gp);
286 mie_read_opc("silicate_orion_10.opc",gp);
287 }
288 }
289
290 for( i=0; i < LIMELM; i++ )
291 {
292 abund.solar[i] = abund.ahii[i];
293 if( !abund.lgElmONahii[i] )
294 {
295 /* turn off elements - do this way to make sure,
296 * that iso sequence limits are handled properly */
297 char chDUMMY[INPUT_LINE_LENGTH];
298 sprintf(chDUMMY,"element %s off ", elementnames.chElementName[i] );
299 p.setline(chDUMMY);
300 ParseElement( p );
301 }
302 }
303 }
304
305 else if( p.nMatch("ISM ") || p.nMatch(" ISM") )
306 {
307 /* ISM abundances from Cowie and Songaila Ann Rev '86 */
308 /* only turn on grains if "no grains" is not present */
309 if( !p.nMatch("NO GR") )
310 {
311 if( !p.m_lgDSet )
312 {
313 /* return bins allocated by previous abundances ... commands */
314 gv.clear();
315 /* now allocate new grain bins */
316 gp.dep = 1.;
317 // standard dust to gas ratio
319 gp.lgRequestQHeating = true;
320 gp.lgForbidQHeating = false;
321 gp.lgGreyGrain = false;
322
323 /* NO QHEAT option to turn off quantum heating */
324 if( p.nMatch("NO QH") )
325 {
326 gp.lgForbidQHeating = true;
327 gp.lgRequestQHeating = false;
328 phycon.lgPhysOK = false;
329 }
330
331 /* actually set up the grains */
332 mie_read_opc("graphite_ism_10.opc",gp);
333 mie_read_opc("silicate_ism_10.opc",gp);
334 }
335 }
336
337 for( i=0; i < LIMELM; i++ )
338 {
339 abund.solar[i] = abund.aism[i];
340 if( !abund.lgElmONaism[i] )
341 {
342 /* turn off elements - do this way to make sure,
343 * that iso sequence limits are handled properly */
344 char chDUMMY[INPUT_LINE_LENGTH];
345 sprintf(chDUMMY,"element %s off ", elementnames.chElementName[i] );
346 p.setline(chDUMMY);
347 ParseElement( p );
348 }
349 }
350 }
351
352 else if( p.nMatch("NOVA") )
353 {
354 /* Nova Cyg abundances */
355 for( i=0; i < LIMELM; i++ )
356 abund.solar[i] = abund.anova[i];
357 }
358
359 else if( p.nMatch("PRIM") )
360 {
361 /* roughly primordial abundances: He/H=.072 */
362 for( i=0; i < 4; i++ )
363 {
364 abund.solar[i] = abund.aprim[i];
365 }
366
367 /* now turn off the heavy elements */
368 for( i=4; i < LIMELM; i++ )
369 {
370 /* turn off heavy elements - do this way to make sure,
371 * that H-like and He-like level limits are handled properly */
372 char chDUMMY[INPUT_LINE_LENGTH];
373 sprintf(chDUMMY,"element %s off ", elementnames.chElementName[i] );
374 p.setline(chDUMMY);
375 ParseElement( p );
376 }
377 }
378
379 else
380 {
381 fprintf( ioQQQ,
382 " ABUNDances must have GASS10, PLAN, H II, CAMERON, CRAB, NOVA, ALL, STARBURST, OLD SOLAR 84 or PRIMORDIAL. Sorry.\n" );
384 }
385 return;
386}
t_abund abund
Definition abund.cpp:5
void abund_starburst(Parser &p)
FILE * ioQQQ
Definition cddefines.cpp:7
const int LIMELM
Definition cddefines.h:258
const int INPUT_LINE_LENGTH
Definition cddefines.h:254
#define EXIT_FAILURE
Definition cddefines.h:140
#define cdEXIT(FAIL)
Definition cddefines.h:434
float realnum
Definition cddefines.h:103
#define DEBUG_ENTRY(funcname)
Definition cddefines.h:684
bool getline(void)
Definition parser.cpp:164
double FFmtRead(void)
Definition parser.cpp:353
bool nMatch(const char *chKey) const
Definition parser.h:135
void setline(const char *const card)
Definition parser.h:69
int strcmp(const char *s2)
Definition parser.h:177
bool m_lgDSet
Definition parser.h:42
bool isComment(void) const
Definition parser.cpp:93
bool lgEOL(void) const
Definition parser.h:98
void echo(void) const
Definition parser.cpp:147
bool m_lgEOF
Definition parser.h:42
t_elementnames elementnames
void mie_read_opc(const char *, const GrainPar &)
GrainVar gv
Definition grainvar.cpp:5
@ DF_STANDARD
Definition grainvar.h:39
void ParseAbundances(Parser &p)
void ParseElement(Parser &p)
t_phycon phycon
Definition phycon.cpp:6
bool lgGreyGrain
Definition grainvar.h:117
bool lgRequestQHeating
Definition grainvar.h:118
df_type nDustFunc
Definition grainvar.h:115
bool lgForbidQHeating
Definition grainvar.h:116
double dep
Definition grainvar.h:114