Skip to content

Commit

Permalink
Bugfix #2782 develop MASSDEN (#2783)
Browse files Browse the repository at this point in the history
* Per #2782, port over fixes from the bugfix_2782_main_v11.1_MASSDEN branch over to the bugfix branch for develop. Will also add new GRIB2 filtering options in this branch.

* Per #2782, add support for 4 new GRIB2 filtering options for GRIB2_aerosol_type, GRIB2_aerosol_interval_type, GRIB2_aerosol_size_lower, and GRIB2_aerosol_size_upper. These are useful in filtering the MASSDEN records in the RRFS smoke output files.

* Per #2782, fix aerosol_size_lower() and aersol_size_upper() inline definitions.

* Per #2782, add a unit test for GRIB2 table 4.48.

* Per #2782, switch from strict equality to using the is_eq() function when checking the GRIB2_aerosol_size_lower and upper values since they're doubles and not ints.
  • Loading branch information
JohnHalleyGotway authored Jan 11, 2024
1 parent 7615f67 commit 07cacb0
Show file tree
Hide file tree
Showing 7 changed files with 157 additions and 20 deletions.
14 changes: 13 additions & 1 deletion docs/Users_Guide/config_options.rst
Original file line number Diff line number Diff line change
Expand Up @@ -1084,7 +1084,19 @@ File-format specific settings for the "field" entry:
* The "GRIB2_perc_val" is an integer specifying the requested percentile
value (0 to 100) to be used. This applies only to GRIB2 product
definition templates 4.6 and 4.10.


* The "GRIB2_aerosol_type" is an integer specifying the aerosol type
(Table 4.233). This applies only to GRIB2 product defintion templates
4.46 and 4.48.

* The "GRIB2_aerosol_interval_type" is an integer specifying the aerosol
size interval (Table 4.91). This applies only to GRIB2 product defintion
templates 4.46 and 4.48.

* The "GRIB2_aerosol_size_lower" and "GRIB2_aerosol_size_upper" are doubles
specifying the endpoints of the aerosol size interval. These applies only
to GRIB2 product defintion templates 4.46 and 4.48.

* The "GRIB2_ipdtmpl_index" and "GRIB2_ipdtmpl_val" entries are arrays
of integers which specify the product description template values to
be used. The indices are 0-based. For example, use the following to
Expand Down
17 changes: 17 additions & 0 deletions internal/test_unit/xml/unit_plot_data_plane.xml
Original file line number Diff line number Diff line change
Expand Up @@ -564,4 +564,21 @@
</output>
</test>

<test name="plot_data_plane_GRIB2_TABLE_4.48">
<exec>&MET_BIN;/plot_data_plane</exec>
<param> \
&DATA_DIR_MODEL;/grib2/rrfs/rrfs.t00z.prslev.f036.conus_3km.MASSDEN.grib2 \
&OUTPUT_DIR;/plot_data_plane/RRFS_GRIB2_TABLE_4.48_MASSDEN.ps \
'name="MASSDEN"; level="Z8"; \
GRIB2_aerosol_type=62001; \
GRIB2_aerosol_interval_type=0; \
GRIB2_aerosol_size_lower=2.5e-06;' \
-title "Mass Density of Dry Dust up to 2.5e-06" \
-v 1
</param>
<output>
<ps>&OUTPUT_DIR;/plot_data_plane/RRFS_GRIB2_TABLE_4.48_MASSDEN.ps</ps>
</output>
</test>

</met_test>
7 changes: 7 additions & 0 deletions src/basic/vx_config/config_constants.h
Original file line number Diff line number Diff line change
Expand Up @@ -555,6 +555,7 @@ static const char conf_key_GRIB1_subcenter[] = "GRIB1_subcenter";
static const char conf_key_GRIB1_rec[] = "GRIB1_rec";
static const char conf_key_GRIB1_code[] = "GRIB1_code";
static const char conf_key_GRIB1_tri[] = "GRIB1_tri";

static const char conf_key_GRIB2_disc[] = "GRIB2_disc";
static const char conf_key_GRIB2_parm_cat[] = "GRIB2_parm_cat";
static const char conf_key_GRIB2_parm[] = "GRIB2_parm";
Expand All @@ -567,6 +568,12 @@ static const char conf_key_GRIB2_ens_type[] = "GRIB2_ens_type";
static const char conf_key_GRIB2_der_type[] = "GRIB2_der_type";
static const char conf_key_GRIB2_stat_type[] = "GRIB2_stat_type";
static const char conf_key_GRIB2_perc_val[] = "GRIB2_perc_val";

static const char conf_key_GRIB2_aerosol_type[] = "GRIB2_aerosol_type";
static const char conf_key_GRIB2_aerosol_interval_type[] = "GRIB2_aerosol_interval_type";
static const char conf_key_GRIB2_aerosol_size_lower[] = "GRIB2_aerosol_size_lower";
static const char conf_key_GRIB2_aerosol_size_upper[] = "GRIB2_aerosol_size_upper";

static const char conf_key_GRIB2_ipdtmpl_index[] = "GRIB2_ipdtmpl_index";
static const char conf_key_GRIB2_ipdtmpl_val[] = "GRIB2_ipdtmpl_val";
static const char conf_key_level[] = "level";
Expand Down
44 changes: 37 additions & 7 deletions src/libcode/vx_data2d_grib2/data2d_grib2.cc
Original file line number Diff line number Diff line change
Expand Up @@ -198,8 +198,9 @@ bool MetGrib2DataFile::data_plane(VarInfo &vinfo, DataPlane &plane) {
if( 1 < listMatch.size() ){
ConcatString msg;
for(size_t i=0; i < listMatch.size(); i++) {
msg << "record " << listMatch[i]->RecNum
msg << " Record " << listMatch[i]->RecNum
<< " field " << listMatch[i]->FieldNum
<< ", table 4." << listMatch[i]->PdsTmpl
<< ": ipdtmpl[" << listMatch[i]->IPDTmpl.n()
<< "] = ";
for(int j=0; j < listMatch[i]->IPDTmpl.n(); j++) {
Expand Down Expand Up @@ -259,8 +260,9 @@ int MetGrib2DataFile::data_plane_array(VarInfo &vinfo,
if( 1 < listMatchExact.size() ){
ConcatString msg;
for(size_t i=0; i < listMatchExact.size(); i++) {
msg << "record " << listMatchExact[i]->RecNum
msg << " Record " << listMatchExact[i]->RecNum
<< " field " << listMatchExact[i]->FieldNum
<< ", table 4." << listMatchExact[i]->PdsTmpl
<< ": ipdtmpl[" << listMatchExact[i]->IPDTmpl.n()
<< "] = ";
for(int j=0; j < listMatchExact[i]->IPDTmpl.n(); j++) {
Expand Down Expand Up @@ -435,6 +437,14 @@ void MetGrib2DataFile::find_record_matches(VarInfoGrib2* vinfo,
continue;
}

// test aerosol config file options
if( (!is_bad_data(vinfo->aerosol_type()) && vinfo->aerosol_type() != (*it)->AerosolType ) ||
(!is_bad_data(vinfo->aerosol_interval_type()) && vinfo->aerosol_interval_type() != (*it)->AerosolIntervalType ) ||
(!is_bad_data(vinfo->aerosol_size_lower()) && !is_eq(vinfo->aerosol_size_lower(), (*it)->AerosolSizeLower )) ||
(!is_bad_data(vinfo->aerosol_size_upper()) && !is_eq(vinfo->aerosol_size_upper(), (*it)->AerosolSizeUpper )) ){
continue;
}

// test ipdtmpl array values
if(vinfo->n_ipdtmpl() > 0) {
int i, j;
Expand Down Expand Up @@ -728,11 +738,17 @@ void MetGrib2DataFile::read_grib2_record_list() {
rec->PdsTmpl = gfld->ipdtnum;
rec->ParmCat = gfld->ipdtmpl[0];
rec->Parm = gfld->ipdtmpl[1];
rec->Process = gfld->ipdtmpl[2];

// get the process id
if( gfld->ipdtnum != 46 && gfld->ipdtnum != 48 ) {
rec->Process = gfld->ipdtmpl[2];
}

// get the level type
if( gfld->ipdtnum == 46 ) {
rec->LvlTyp = gfld->ipdtmpl[15];
} else if( gfld->ipdtnum == 48 ) {
rec->LvlTyp = gfld->ipdtmpl[20];
} else {
rec->LvlTyp = gfld->ipdtmpl[9];
}
Expand All @@ -745,10 +761,16 @@ void MetGrib2DataFile::read_grib2_record_list() {
// check for template number 46
if( gfld->ipdtnum == 46 ) {
rec->LvlVal1 = scaled2dbl(gfld->ipdtmpl[16], gfld->ipdtmpl[17]);
rec->LvlVal2 = rec->LvlVal1;
// check for special fixed level types (1 through 10 or 101) and set the level values to 0
// Reference: https://www.nco.ncep.noaa.gov/pmb/docs/grib2/grib2_doc/grib2_table4-5.shtml
} else if( (rec->LvlTyp >= 1 && rec->LvlTyp <= 10) || rec->LvlTyp == 101 ) {
rec->LvlVal2 = rec->LvlVal1;
}
// check for template number 48
else if( gfld->ipdtnum == 48 ) {
rec->LvlVal1 = scaled2dbl(gfld->ipdtmpl[21], gfld->ipdtmpl[22]);
rec->LvlVal2 = rec->LvlVal1;
}
// check for special fixed level types (1 through 10 or 101) and set the level values to 0
// Reference: https://www.nco.ncep.noaa.gov/pmb/docs/grib2/grib2_doc/grib2_table4-5.shtml
else if( (rec->LvlTyp >= 1 && rec->LvlTyp <= 10) || rec->LvlTyp == 101 ) {
rec->LvlVal1 = 0;
rec->LvlVal2 = 0;
} else {
Expand Down Expand Up @@ -805,6 +827,14 @@ void MetGrib2DataFile::read_grib2_record_list() {
rec->PercVal = gfld->ipdtmpl[15];
}

// aerosol type and size for templates 46 and 48
if( 46 == gfld->ipdtnum || 48 == gfld->ipdtnum ){
rec->AerosolType = gfld->ipdtmpl[2];
rec->AerosolIntervalType = gfld->ipdtmpl[3];
rec->AerosolSizeLower = scaled2dbl(gfld->ipdtmpl[4], gfld->ipdtmpl[5]);
rec->AerosolSizeUpper = scaled2dbl(gfld->ipdtmpl[6], gfld->ipdtmpl[7]);
}

// depending on the template number, determine the reference times
if( 8 <= gfld->ipdtnum && 12 >= gfld->ipdtnum ){

Expand Down
4 changes: 4 additions & 0 deletions src/libcode/vx_data2d_grib2/data2d_grib2.h
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,10 @@ typedef struct {
int DerType;
int StatType;
int PercVal;
int AerosolType;
int AerosolIntervalType;
double AerosolSizeLower;
double AerosolSizeUpper;
IntArray IPDTmpl;
} Grib2Record;

Expand Down
71 changes: 59 additions & 12 deletions src/libcode/vx_data2d_grib2/var_info_grib2.cc
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,11 @@ void VarInfoGrib2::assign(const VarInfoGrib2 &v) {
StatType = v.StatType;
PercVal = v.PercVal;

AerosolType = v.AerosolType;
AerosolIntervalType = v.AerosolIntervalType;
AerosolSizeLower = v.AerosolSizeLower;
AerosolSizeUpper = v.AerosolSizeUpper;

IPDTmplIndex = v.IPDTmplIndex;
IPDTmplVal = v.IPDTmplVal;

Expand Down Expand Up @@ -137,6 +142,11 @@ void VarInfoGrib2::clear() {
StatType = bad_data_int;
PercVal = bad_data_int;

AerosolType = bad_data_int;
AerosolIntervalType = bad_data_int;
AerosolSizeLower = bad_data_double;
AerosolSizeUpper = bad_data_double;

IPDTmplIndex.clear();
IPDTmplVal.clear();

Expand All @@ -149,18 +159,22 @@ void VarInfoGrib2::dump(ostream &out) const {

// Dump out the contents
out << "VarInfoGrib2::dump():\n"
<< " Record = " << Record << "\n"
<< " Discipline = " << Discipline << "\n"
<< " MTable = " << MTable << "\n"
<< " LTable = " << LTable << "\n"
<< " ParmCat = " << ParmCat << "\n"
<< " Parm = " << Parm << "\n"
<< " PDTmpl = " << PDTmpl << "\n"
<< " Process = " << Process << "\n"
<< " EnsType = " << EnsType << "\n"
<< " DerType = " << DerType << "\n"
<< " StatType = " << StatType << "\n"
<< " PercVal = " << PercVal << "\n";
<< " Record = " << Record << "\n"
<< " Discipline = " << Discipline << "\n"
<< " MTable = " << MTable << "\n"
<< " LTable = " << LTable << "\n"
<< " ParmCat = " << ParmCat << "\n"
<< " Parm = " << Parm << "\n"
<< " PDTmpl = " << PDTmpl << "\n"
<< " Process = " << Process << "\n"
<< " EnsType = " << EnsType << "\n"
<< " DerType = " << DerType << "\n"
<< " StatType = " << StatType << "\n"
<< " PercVal = " << PercVal << "\n"
<< " AerosolType = " << AerosolType << "\n"
<< " AerosolIntervalType = " << AerosolIntervalType << "\n"
<< " AerosolSizeLower = " << AerosolSizeLower << "\n"
<< " AerosolSizeUpper = " << AerosolSizeUpper << "\n";
out << " IPDTmplIndex:\n";
IPDTmplIndex.dump(out);
out << " IPDTmplVal:\n";
Expand Down Expand Up @@ -255,6 +269,34 @@ void VarInfoGrib2::set_perc_val(int v) {

///////////////////////////////////////////////////////////////////////////////

void VarInfoGrib2::set_aerosol_type(int v) {
AerosolType = v;
return;
}

///////////////////////////////////////////////////////////////////////////////

void VarInfoGrib2::set_aerosol_interval_type(int v) {
AerosolIntervalType = v;
return;
}

///////////////////////////////////////////////////////////////////////////////

void VarInfoGrib2::set_aerosol_size_lower(double v) {
AerosolSizeLower = v;
return;
}

///////////////////////////////////////////////////////////////////////////////

void VarInfoGrib2::set_aerosol_size_upper(double v) {
AerosolSizeUpper = v;
return;
}

///////////////////////////////////////////////////////////////////////////////

void VarInfoGrib2::set_ipdtmpl_index(const IntArray &v) {
IPDTmplIndex = v;
return;
Expand Down Expand Up @@ -292,6 +334,11 @@ void VarInfoGrib2::set_dict(Dictionary & dict) {
StatType = dict.lookup_int (conf_key_GRIB2_stat_type, false);
PercVal = dict.lookup_int (conf_key_GRIB2_perc_val, false);

AerosolType = dict.lookup_int (conf_key_GRIB2_aerosol_type, false);
AerosolIntervalType = dict.lookup_int (conf_key_GRIB2_aerosol_interval_type, false);
AerosolSizeLower = dict.lookup_double(conf_key_GRIB2_aerosol_size_lower, false);
AerosolSizeUpper = dict.lookup_double(conf_key_GRIB2_aerosol_size_upper, false);

IPDTmplIndex = dict.lookup_int_array(conf_key_GRIB2_ipdtmpl_index, false);
IPDTmplVal = dict.lookup_int_array(conf_key_GRIB2_ipdtmpl_val, false);

Expand Down
20 changes: 20 additions & 0 deletions src/libcode/vx_data2d_grib2/var_info_grib2.h
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,11 @@ class VarInfoGrib2 : public VarInfo
int StatType; // Statistical Processing Type (Table 4.10)
int PercVal; // Percentile Value (Octet 35 for Templates 4.6 and 4.10)

int AerosolType; // Aerosol Type (Table 4.46 and 4.48)
int AerosolIntervalType; // Aerosol Interval Type (Table 4.46 and 4.48)
double AerosolSizeLower; // Lower limit of Aerosol Size
double AerosolSizeUpper; // Upper limit of Aerosol Size

IntArray IPDTmplIndex; // Index into the GRIB2 ipdtmpl array
IntArray IPDTmplVal; // Corresponding GRIB2 ipdtmpl value

Expand Down Expand Up @@ -89,6 +94,11 @@ class VarInfoGrib2 : public VarInfo
int stat_type() const;
int perc_val() const;

int aerosol_type() const;
int aerosol_interval_type() const;
double aerosol_size_lower() const;
double aerosol_size_upper() const;

int n_ipdtmpl() const;
int ipdtmpl_index(int) const;
int ipdtmpl_val(int) const;
Expand All @@ -111,6 +121,10 @@ class VarInfoGrib2 : public VarInfo
void set_der_type(int);
void set_stat_type(int);
void set_perc_val(int);
void set_aerosol_type(int);
void set_aerosol_interval_type(int);
void set_aerosol_size_lower(double);
void set_aerosol_size_upper(double);
void set_ipdtmpl_index(const IntArray &);
void set_ipdtmpl_val(const IntArray &);

Expand Down Expand Up @@ -145,6 +159,12 @@ inline int VarInfoGrib2::ens_type() const { return(EnsType); }
inline int VarInfoGrib2::der_type() const { return(DerType); }
inline int VarInfoGrib2::stat_type() const { return(StatType); }
inline int VarInfoGrib2::perc_val() const { return(PercVal); }

inline int VarInfoGrib2::aerosol_type() const { return(AerosolType); }
inline int VarInfoGrib2::aerosol_interval_type() const { return(AerosolIntervalType); }
inline double VarInfoGrib2::aerosol_size_lower() const { return(AerosolSizeLower); }
inline double VarInfoGrib2::aerosol_size_upper() const { return(AerosolSizeUpper); }

inline int VarInfoGrib2::n_ipdtmpl() const {
return(IPDTmplIndex.n()); }
inline int VarInfoGrib2::ipdtmpl_index(int i) const {
Expand Down

0 comments on commit 07cacb0

Please sign in to comment.