diff --git a/dartwrf/dart_nml.py b/dartwrf/dart_nml.py
index c11c9a99181f5bbb64881e1ffc24d90525a1ecff..e2b490023f4097663771853945e63b15dc04aee2 100644
--- a/dartwrf/dart_nml.py
+++ b/dartwrf/dart_nml.py
@@ -5,6 +5,7 @@ from config.cluster import cluster
 
 earth_radius_km = 6370
 
+
 def read_namelist(filepath):
     """Read the DART namelist file into a dictionary.
     
@@ -64,7 +65,7 @@ def read_namelist(filepath):
 
             param_data.append(val)
 
-            print('this iteration var, val ...', {param: param_data})
+            # print('this iteration var, val ...', {param: param_data})
 
             # add variable to dictionary
             d[section][param] = param_data
@@ -86,7 +87,7 @@ def write_namelist_from_dict(d, filepath):
 
             try:
                 parameters = d[section].keys()
-                print(parameters, [len(p) for p in parameters])
+                # print(parameters, [len(p) for p in parameters])
                 max_width_of_parameter_name = max([len(p) for p in parameters])
                 width = max_width_of_parameter_name + 1
             except:
@@ -107,9 +108,9 @@ def write_namelist_from_dict(d, filepath):
 
 
                     if i == 0:
-                        f.write('   '+parameter.ljust(width)+' = '+line+'\n')
+                        f.write('   '+parameter.ljust(width)+' = '+line+',\n')
                     else:
-                        f.write('   '+' '*width+' = '+line+'\n')
+                        f.write('   '+' '*width+'   '+line+',\n')
             f.write('   /\n\n')
 
 
@@ -191,7 +192,8 @@ def _get_list_of_localizations():
 
 
 def _to_fortran_list(l):
-    """Ensure formatting as "arg1", "arg2", """
+    """Ensure formatting with quotation mark, e.g. parameter = "arg1", "arg2", 
+    """
     assert isinstance(l, list)
 
     if len(l) > 1:  # multiple entries
@@ -243,7 +245,6 @@ def write_namelist(just_prior_values=False):
     nml['&location_nml']['special_vert_normalization_heights'] = [_to_fortran_list(list_loc_vert_km)]
     nml['&location_nml']['special_vert_normalization_scale_heights'] = [_to_fortran_list(list_loc_vert_scaleheight)]
 
-    print(nml['&location_nml']['special_vert_normalization_obs_types'])
 
     # overwrite namelist with experiment configuration
     for section, sdata in exp.dart_nml.items():
diff --git a/tests/input.nml.desired_output b/tests/input.nml.desired_output
new file mode 100644
index 0000000000000000000000000000000000000000..64635bd3a885d1243c24f5553df7343b47d1c613
--- /dev/null
+++ b/tests/input.nml.desired_output
@@ -0,0 +1,579 @@
+&perfect_model_obs_nml
+   read_input_state_from_file = .true.
+   single_file_in             = .false.
+   input_state_files          = 'wrfinput_d01'
+   init_time_days             = -1
+   init_time_seconds          = -1
+
+   write_output_state_to_file = .false.
+   single_file_out            = .false.
+   output_state_files         = 'perfect_output_d01.nc'
+   output_interval            = 1
+
+   obs_seq_in_file_name       = "obs_seq.in"
+   obs_seq_out_file_name      = "obs_seq.out"
+   first_obs_days             = -1
+   first_obs_seconds          = -1
+   last_obs_days              = -1
+   last_obs_seconds           = -1
+
+   async                      = 0
+   adv_ens_command            = "../shell_scripts/advance_model.csh"
+
+   trace_execution            = .true.
+   output_timestamps          = .false.
+   print_every_nth_obs        = -1
+   output_forward_op_errors   = .true.
+   silence                    = .false.
+   /
+
+&filter_nml
+   async                    = 0,
+   adv_ens_command          = "../shell_scripts/advance_model.csh",
+   ens_size                 = 999,
+   obs_sequence_in_name     = "obs_seq.out",
+   obs_sequence_out_name    = "obs_seq.final",
+   input_state_file_list    = "input_list.txt"
+   output_state_file_list   = "output_list.txt"
+   init_time_days           = -1,
+   init_time_seconds        = -1,
+   first_obs_days           = -1,
+   first_obs_seconds        = -1,
+   last_obs_days            = -1,
+   last_obs_seconds         = -1,
+   num_output_state_members = 999,
+   num_output_obs_members   = 999,
+   output_interval          = 1,
+   num_groups               = 1,
+   distributed_state        = .true.
+   compute_posterior        = .true.
+   output_forward_op_errors = .false.,
+   output_timestamps        = .false.,
+   trace_execution          = .false.,
+
+   stages_to_write          = 'preassim', 'output'
+   output_members           = .false.
+   output_mean              = .true.
+   output_sd                = .false.
+   write_all_stages_at_end  = .false.
+
+   inf_flavor                  = 2,                      0,
+   inf_initial_from_restart    = .true.,                 .false.,
+   inf_sd_initial_from_restart = .true.,                 .false.,
+   inf_initial                 = 1.0,                     1.00,
+   inf_lower_bound             = 1.0,                     1.0,
+   inf_upper_bound             = 1000000.0,               1000000.0,
+   inf_damping                 = 0.9,                     1.0,
+   inf_sd_initial              = 0.6,                     0.0,
+   inf_sd_lower_bound          = 0.6,                     0.0,
+   inf_sd_max_change           = 1.05,                    1.05,
+   /
+
+&quality_control_nml
+   input_qc_threshold          = 3.0,
+   outlier_threshold           = 3.0,
+   enable_special_outlier_code = .false.
+   /
+
+&fill_inflation_restart_nml
+   write_prior_inf = .true.
+   prior_inf_mean  = 1.00
+   prior_inf_sd    = 0.6
+
+   write_post_inf  = .false.
+   post_inf_mean   = 1.00
+   post_inf_sd     = 0.6
+
+   input_state_files = 'wrfinput_d01', 'wrfinput_d02'
+   single_file       = .false.
+   verbose           = .false.
+   /
+
+&smoother_nml
+   num_lags              = 0,
+   start_from_restart    = .false.,
+   output_restart        = .false.,
+   restart_in_file_name  = 'smoother_ics',
+   restart_out_file_name = 'smoother_restart',
+   /
+
+# cutoff is in radians; for the earth, 0.05 is about 300 km.
+# cutoff is defined to be the half-width of the localization radius,
+# so 0.05 radians for cutoff is about an 600 km effective
+# localization radius, where the influence of an obs decreases
+# to ~half at 300 km, and ~0 at the edges of the area.
+&assim_tools_nml
+   filter_kind                     = 1,
+   cutoff                          = 0.05,
+   sort_obs_inc                    = .false.,
+   spread_restoration              = .false.,
+   sampling_error_correction       = .true.,
+   adaptive_localization_threshold = -1,
+   output_localization_diagnostics = .false.,
+   localization_diagnostics_file   = 'localization_diagnostics',
+   convert_all_state_verticals_first = .true.
+   convert_all_obs_verticals_first   = .true.
+   print_every_nth_obs               = 0,
+   /
+
+&cov_cutoff_nml
+   select_localization = 1,
+   /
+
+&obs_sequence_nml
+   write_binary_obs_sequence = .false.,
+   /
+
+&preprocess_nml
+   overwrite_output        = .true.
+   input_obs_qty_mod_file  = '../../../assimilation_code/modules/observations/DEFAULT_obs_kind_mod.F90'
+   output_obs_qty_mod_file = '../../../assimilation_code/modules/observations/obs_kind_mod.f90'
+   input_obs_def_mod_file  = '../../../observations/forward_operators/DEFAULT_obs_def_mod.F90'
+   output_obs_def_mod_file = '../../../observations/forward_operators/obs_def_mod.f90'
+   quantity_files          = '../../../assimilation_code/modules/observations/atmosphere_quantities_mod.f90'
+   obs_type_files          = '../../../observations/forward_operators/obs_def_reanalysis_bufr_mod.f90',
+                             '../../../observations/forward_operators/obs_def_radar_mod.f90',
+                             '../../../observations/forward_operators/obs_def_metar_mod.f90',
+                             '../../../observations/forward_operators/obs_def_dew_point_mod.f90',
+                             '../../../observations/forward_operators/obs_def_rel_humidity_mod.f90',
+                             '../../../observations/forward_operators/obs_def_altimeter_mod.f90',
+                             '../../../observations/forward_operators/obs_def_gps_mod.f90',
+                             '../../../observations/forward_operators/obs_def_vortex_mod.f90',
+                             '../../../observations/forward_operators/obs_def_gts_mod.f90',
+                             '../../../observations/forward_operators/obs_def_rttov_mod.f90'
+   /
+
+&obs_kind_nml
+   assimilate_these_obs_types = 'RADIOSONDE_TEMPERATURE',
+                                'RADIOSONDE_U_WIND_COMPONENT',
+                                'RADIOSONDE_V_WIND_COMPONENT',
+                                'SAT_U_WIND_COMPONENT',
+                                'SAT_V_WIND_COMPONENT',
+                                'AIRCRAFT_U_WIND_COMPONENT',
+                                'AIRCRAFT_V_WIND_COMPONENT',
+                                'AIRCRAFT_TEMPERATURE',
+                                'ACARS_U_WIND_COMPONENT',
+                                'ACARS_V_WIND_COMPONENT',
+                                'ACARS_TEMPERATURE',
+                                'GPSRO_REFRACTIVITY',
+                                'DOPPLER_RADIAL_VELOCITY',
+                                'RADAR_REFLECTIVITY',
+                                'MSG_4_SEVIRI_RADIANCE',
+                                'MSG_4_SEVIRI_TB',
+                                'MSG_4_SEVIRI_BDRF',
+                                'LAND_SFC_PRESSURE',
+                                'SYNOP_SURFACE_PRESSURE',
+                                'SYNOP_TEMPERATURE',
+                                'SYNOP_SPECIFIC_HUMIDITY',
+                                'GPS_PRECIPITABLE_WATER'
+   evaluate_these_obs_types   = 'RADIOSONDE_SPECIFIC_HUMIDITY',
+   /
+
+# Notes for obs_def_radar_mod_nml:
+# (1) Reflectivity limit can be applied to observations and/or forward operator.
+# (2) The default constants below match the WRF defaults.  They will need to
+# be changed for other cases, depending on which microphysics scheme is used.
+#
+
+&obs_def_radar_mod_nml
+   apply_ref_limit_to_obs      =   .false.,
+   reflectivity_limit_obs      =  -10.0,
+   lowest_reflectivity_obs     =  -10.0,
+   apply_ref_limit_to_fwd_op   =   .false.,
+   reflectivity_limit_fwd_op   =  -10.0,
+   lowest_reflectivity_fwd_op  =  -10.0,
+   max_radial_vel_obs          =   1000000,
+   allow_wet_graupel           =   .false.,
+   microphysics_type           =       2  ,
+   allow_dbztowt_conv          =   .false.,
+   dielectric_factor           =  0.224,
+   n0_rain                     =  8.0e6,
+   n0_graupel                  =  4.0e6,
+   n0_snow                     =  3.0e6,
+   rho_rain                    = 1000.0,
+   rho_graupel                 =  400.0,
+   rho_snow                    =  100.0,
+   /
+
+
+# Notes for model_nml:
+# (1) vert_localization_coord must be one of:
+#     1 = model level
+#     2 = pressure
+#     3 = height
+#     4 = scale height
+
+# set default_state_variables to .false. to use the explicit list.
+# otherwise it uses a hardcoded default list: U, V, W, PH, T, MU, QV only.
+# see ../wrf_state_variables_table for a full list of what wrf fields are
+# supported in the DART state vector, and what settings should be used here.
+# 'UPDATE' and 'NO_COPY_BACK' are supported in the 4th column; 'NO_UPDATE' is
+# not yet supported.
+
+&model_nml
+   default_state_variables = .false.,
+   wrf_state_variables = 'U',     'QTY_U_WIND_COMPONENT',     'TYPE_U',    'UPDATE','999',
+                         'V',     'QTY_V_WIND_COMPONENT',     'TYPE_V',    'UPDATE','999',
+                         'W',     'QTY_VERTICAL_VELOCITY',    'TYPE_W',    'UPDATE','999',
+                         'PH',    'QTY_GEOPOTENTIAL_HEIGHT',  'TYPE_GZ',   'UPDATE','999',
+                         'T',     'QTY_POTENTIAL_TEMPERATURE','TYPE_T',    'UPDATE','999',
+                         'MU',    'QTY_PRESSURE',             'TYPE_MU',   'UPDATE','999',
+                         'QVAPOR','QTY_VAPOR_MIXING_RATIO',   'TYPE_QV',   'UPDATE','999',
+                         'QICE',  'QTY_ICE_MIXING_RATIO',     'TYPE_QI',   'UPDATE','999',
+                         'QCLOUD','QTY_CLOUDWATER_MIXING_RATIO','TYPE_QC', 'UPDATE','999',
+                         'CLDFRA','QTY_CLOUD_FRACTION',       'TYPE_CFRAC','UPDATE','999',
+                         'PSFC',  'QTY_SURFACE_PRESSURE',     'TYPE_PSFC', 'UPDATE','999',
+                         'T2',    'QTY_2M_TEMPERATURE',       'TYPE_T',    'UPDATE','999',
+                         'TSK',   'QTY_SKIN_TEMPERATURE',     'TYPE_T',    'UPDATE','999',
+                         'REFL_10CM','QTY_RADAR_REFLECTIVITY','TYPE_REFL', 'UPDATE','999',
+   wrf_state_bounds    = 'QVAPOR','0.0','NULL','CLAMP',
+                         'QRAIN', '0.0','NULL','CLAMP',
+                         'QCLOUD','0.0','NULL','CLAMP',
+                         'QICE','0.0','NULL','CLAMP',
+                         'CLDFRA','0.0','1.0','CLAMP',
+   num_domains                 = 1,
+   calendar_type               = 3,
+   assimilation_period_seconds = 21600,
+   vert_localization_coord     = 3,
+   center_search_half_length   = 500000.,
+   center_spline_grid_scale    = 10,
+   sfc_elev_max_diff           = -1.0,
+   circulation_pres_level      = 80000.0,
+   circulation_radius          = 108000.0,
+   allow_obs_below_vol         = .false.
+   /
+
+# vert_normalization_X is amount of X equiv to 1 radian in horiz.
+# vert localization is 'cutoff' times the pressure/height/levels,
+# only if horiz_dist_only is set to .false. in the namelist below.
+# the default nlon/nlat should be good for most experiments. it sets 
+# an internal structure that speeds up searches.  don't change it
+# based on your grid size.  nlon must be an odd number.
+&location_nml
+   horiz_dist_only             = .false.,
+   vert_normalization_pressure = 6666666.7,
+   vert_normalization_height   = 5000000.0,
+   vert_normalization_level    = 2666.7,
+   vert_normalization_scale_height = 10.0,
+   approximate_distance        = .false.,
+   nlon                        = 71,
+   nlat                        = 36,
+   output_box_info             = .false.,
+   /
+
+&utilities_nml
+   TERMLEVEL = 1,
+   module_details = .false.,
+   logfilename = 'dart_log.out',
+   nmlfilename = 'dart_log.nml',
+   write_nml   = 'file',
+   /
+
+&mpi_utilities_nml
+   /
+
+&reg_factor_nml
+   select_regression    = 1,
+   input_reg_file       = "time_mean_reg",
+   save_reg_diagnostics = .false.,
+   reg_diagnostics_file = "reg_diagnostics",
+   /
+
+# layout = 2 spreads the IO tasks across the nodes.
+# This can greatly improve the performance in IO if
+# tasks_per_node is set to match your hardware
+&ensemble_manager_nml
+   layout = 2,
+   tasks_per_node = 16
+   /
+
+&obs_def_gps_nml
+   max_gpsro_obs = 100000,
+   / 
+
+&obs_def_tpw_nml
+   /
+
+# The times in the namelist for the obs_diag program are vectors
+# that follow the following sequence:
+# year   month   day   hour   minute   second
+# max_num_bins can be used to specify a fixed number of bins,
+# in which case last_bin_center should be safely in the future.
+#
+# Acceptable latitudes range from  [-90,  90]
+# Acceptable longitudes range from [  0, Inf]
+
+&obs_diag_nml
+   obs_sequence_name  = 'obs_seq.final',
+   obs_sequence_list  = '',
+   first_bin_center   =  2003, 1, 1, 0, 0, 0 ,
+   last_bin_center    =  2003, 1, 2, 0, 0, 0 ,
+   bin_separation     =     0, 0, 0,12, 0, 0 ,
+   bin_width          =     0, 0, 0, 6, 0, 0 ,
+   time_to_skip       =     0, 0, 0, 0, 0, 0 ,
+   max_num_bins       = 1000,
+   trusted_obs        = 'null',
+   Nregions   = 4,
+   lonlim1    =   0.0,   0.0,   0.0, 235.0,
+   lonlim2    = 360.0, 360.0, 360.0, 295.0,
+   latlim1    =  20.0, -80.0, -20.0,  25.0,
+   latlim2    =  80.0, -20.0,  20.0,  55.0,
+   reg_names  = 'Northern Hemisphere', 'Southern Hemisphere', 'Tropics', 'North America',
+   print_mismatched_locs = .false.,
+   create_rank_histogram = .true.,
+   outliers_in_histogram = .true.,
+   use_zero_error_obs    = .false.,
+   verbose               = .false.
+   /
+
+&schedule_nml
+   calendar        = 'Gregorian',  
+   first_bin_start =  1601,  1,  1,  0,  0,  0,
+   first_bin_end   =  2999,  1,  1,  0,  0,  0,
+   last_bin_end    =  2999,  1,  1,  0,  0,  0,
+   bin_interval_days    = 1000000,
+   bin_interval_seconds = 0,   
+   max_num_bins         = 1000,
+   print_table          = .true.,
+   /
+   
+&obs_seq_to_netcdf_nml  
+   obs_sequence_name = 'obs_seq.final',
+   obs_sequence_list = '',
+   append_to_netcdf  = .false.,
+   lonlim1    =    0.0,
+   lonlim2    =  360.0,
+   latlim1    =  -90.0,
+   latlim2    =   90.0,
+   verbose    = .false.,
+   /
+
+# There is one GIGANTIC difference between the obsdef_mask.txt and .nc
+# The netCDF file intentionally ignores the effect of nTmin/nTmax.
+# The netCDF file has ALL matching stations, regardless of temporal coverage.
+
+&obs_seq_coverage_nml
+   obs_sequences     = ''
+   obs_sequence_list = 'obs_coverage_list.txt'
+   obs_of_interest   = 'METAR_U_10_METER_WIND'
+   textfile_out      = 'METAR_U_10_METER_WIND_obsdef_mask.txt'
+   netcdf_out        = 'METAR_U_10_METER_WIND_obsdef_mask.nc'
+   first_analysis    =  2003, 1, 1, 0, 0, 0
+   last_analysis     =  2003, 1, 2, 0, 0, 0
+   forecast_length_days          = 1
+   forecast_length_seconds       = 0
+   verification_interval_seconds = 21600
+   temporal_coverage_percent     = 100.0
+   lonlim1    =    0.0
+   lonlim2    =  360.0
+   latlim1    =  -90.0
+   latlim2    =   90.0
+   verbose    = .true.
+   /
+
+# selections_file is a list of obs_defs output
+# from the obs_seq_coverage utility.
+
+&obs_selection_nml
+   filename_seq          = 'obs_seq.out', 
+   filename_seq_list     = '', 
+   filename_out          = 'obs_seq.processed', 
+   selections_file       = 'obsdef_mask.txt', 
+   selections_is_obs_seq = .false.,
+   print_only            = .false., 
+   calendar              = 'gregorian',
+   /
+
+&obs_seq_verify_nml
+   obs_sequences     = ''
+   obs_sequence_list = 'obs_verify_list.txt'
+   input_template    = 'obsdef_mask.nc'
+   netcdf_out        = 'forecast.nc'
+   obtype_string     = 'METAR_U_10_METER_WIND'
+   print_every       = 10000
+   verbose           = .true.
+   debug             = .false.
+   /
+
+&obs_sequence_tool_nml
+   num_input_files   = 1, 
+   filename_seq      = 'obs_seq.out',
+   filename_out      = 'obs_seq.processed', 
+   first_obs_days    = -1, 
+   first_obs_seconds = -1, 
+   last_obs_days     = -1, 
+   last_obs_seconds  = -1, 
+   obs_types         = '', 
+   keep_types        = .false., 
+   print_only        = .false., 
+   min_lat           = -90.0, 
+   max_lat           =  90.0, 
+   min_lon           =   0.0, 
+   max_lon           = 360.0,
+   /
+
+&replace_wrf_fields_nml
+   debug = .false.,
+   fail_on_missing_field = .false.,
+   fieldnames = "SNOWC",
+                "ALBBCK",
+                "TMN",
+                "TSK",
+                "SH2O",
+                "SMOIS",
+                "SEAICE",
+                "HGT_d01",
+                "TSLB",
+                "SST",
+                "SNOWH",
+                "SNOW",
+   fieldlist_file = '',
+   /
+
+&obs_common_subset_nml
+   num_to_compare_at_once = 2,
+   filename_seq           = 'obs_seq1.final', 'obs_seq2.final',
+   filename_seq_list      = '',
+   filename_out_suffix    = '.common' ,
+   calendar               = 'Gregorian',
+   print_every            = 1000,
+   dart_qc_threshold      = 3,
+   print_only             = .false.,
+   /
+
+&wrf_dart_to_fields_nml
+   include_slp             = .true.,
+   include_wind_components = .true.,
+   include_height_on_pres  = .true.,
+   include_temperature     = .true.,
+   include_rel_humidity    = .true.,
+   include_surface_fields  = .false.,
+   include_sat_ir_temp     = .false.,
+   pres_levels             = 70000.,
+   /
+
+&ncepobs_nml
+   year = 2010,
+   month = 06,
+   day = 00,
+   tot_days = 1,
+   max_num = 1000000,
+   ObsBase = 'temp_obs.',
+   select_obs  = 0,
+   ADPUPA = .false.,
+   AIRCAR = .false.,
+   AIRCFT = .false.,
+   SATEMP = .false.,
+   SFCSHP = .false.,
+   ADPSFC = .false.,
+   SATWND = .true.,
+   obs_U  = .false.,
+   obs_V  = .false.,
+   obs_T  = .false.,
+   obs_PS = .false.,
+   obs_QV = .false.,
+   daily_file = .true.,
+   obs_time = .false.,
+   lat1 = 10.00,
+   lat2 = 60.00,
+   lon1 = 210.0,
+   lon2 = 300.0
+   /
+
+&prep_bufr_nml
+   obs_window_upa = 1.0,
+   obs_window_air = 1.0,
+   obs_window_cw = 1.0,
+   otype_use      = 242.0, 243.0, 245.0, 246.0, 251.0, 252.0, 253.0, 257.0, 259.0
+   qctype_use     = 0, 1, 2, 3, 4, 9, 15
+   /
+
+&convert_cosmic_gps_nml
+   gpsro_netcdf_file     = '',
+   gpsro_netcdf_filelist = 'flist',
+   gpsro_out_file        = 'obs_seq.gpsro',
+   local_operator        = .true.,
+   obs_levels            = 0.22, 0.55, 1.1, 1.8, 2.7, 3.7, 4.9,
+                           6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 12.0, 13.0,
+   ray_ds                = 5000.0,
+   ray_htop              = 13000.1,
+   /
+
+&wrf_obs_preproc_nml
+
+   file_name_input          = 'obs_seq20110901'
+   file_name_output         = 'obs_seq.europe.prev'
+  
+   overwrite_obs_time       = .false.  
+  
+   obs_boundary             = 0.0   
+   increase_bdy_error       = .false.  
+   maxobsfac                = 2.5   
+   obsdistbdy               = 1.0  
+  
+   sfc_elevation_check      = .false.  
+   sfc_elevation_tol        = 3000.0  
+   obs_pressure_top         = 0.0  
+   obs_height_top           = 2.0e10  
+  
+   include_sig_data         = .true.   
+   tc_sonde_radii           = -1.0  
+  
+   superob_aircraft         = .true.  
+   aircraft_horiz_int       = 800.0  
+   aircraft_pres_int        = 25000.0  
+  
+   superob_sat_winds        = .true.    
+   sat_wind_horiz_int       = 800.0   
+   sat_wind_pres_int        = 25000.0  
+  
+   overwrite_ncep_satwnd_qc = .false.    
+   overwrite_ncep_sfc_qc    = .false.  
+   /
+
+!  sonde_extra              = 'obs_seq.rawin'
+!  land_sfc_extra           = 'obs_seq.land_sfc'
+!  metar_extra              = 'obs_seq.metar'
+!  marine_sfc_extra         = 'obs_seq.marine'
+!  sat_wind_extra           = 'obs_seq.satwnd'
+!  profiler_extra           = 'obs_seq.profiler'
+!  gpsro_extra              = 'obs_seq.gpsro'
+!  acars_extra              = 'obs_seq.acars'
+!  trop_cyclone_extra       = 'obs_seq.tc'
+
+&state_vector_io_nml
+   single_precision_output    = .true.,
+   /
+
+&compare_states_nml
+   /
+
+&closest_member_tool_nml 
+   input_restart_file_list   = 'input_file_list_d01.txt',
+   output_file_name          = 'closest_results.txt'
+   ens_size                  = 3,
+   single_restart_file_in    = .false.,
+   difference_method         = 4,
+   use_only_qtys             = 'QTY_U_WIND_COMPONENT'
+   /
+
+# To test both domains, you must change 'model_nml:num_domains = 2'
+
+&model_mod_check_nml
+   input_state_files     = 'wrfinput_d01', 'wrfinput_d02'
+   output_state_files    = 'mmc_output1.nc', 'mmc_output2.nc'
+   test1thru             = 0
+   run_tests             = 1,2,3,4,5
+   x_ind                 = 87370
+   loc_of_interest       = 231.0, 40.0, 10.0
+   quantity_of_interest  = 'QTY_U_WIND_COMPONENT'
+   interp_test_dlon      = 0.1
+   interp_test_dlat      = 0.1
+   interp_test_dvert     = 1000.0
+   interp_test_lonrange  = 250.0,  260.0
+   interp_test_latrange  =  30.0,   45.0
+   interp_test_vertrange = 2000.0, 4000.0
+   interp_test_vertcoord = 'VERTISHEIGHT'
+   verbose               = .false.
+   /
+
diff --git a/tests/input.nml.original b/tests/input.nml.original
new file mode 100644
index 0000000000000000000000000000000000000000..c7f6fee6762770e30b4f649e406e91b38e984c71
--- /dev/null
+++ b/tests/input.nml.original
@@ -0,0 +1,579 @@
+&perfect_model_obs_nml
+   read_input_state_from_file = .true.
+   single_file_in             = .false.
+   input_state_files          = 'wrfinput_d01'
+   init_time_days             = -1
+   init_time_seconds          = -1
+
+   write_output_state_to_file = .false.
+   single_file_out            = .false.
+   output_state_files         = 'perfect_output_d01.nc'
+   output_interval            = 1
+
+   obs_seq_in_file_name       = "obs_seq.in"
+   obs_seq_out_file_name      = "obs_seq.out"
+   first_obs_days             = -1
+   first_obs_seconds          = -1
+   last_obs_days              = -1
+   last_obs_seconds           = -1
+
+   async                      = 0
+   adv_ens_command            = "../shell_scripts/advance_model.csh"
+
+   trace_execution            = .true.
+   output_timestamps          = .false.
+   print_every_nth_obs        = -1
+   output_forward_op_errors   = .true.
+   silence                    = .false.
+   /
+
+&filter_nml
+   async                    = 0,
+   adv_ens_command          = "../shell_scripts/advance_model.csh",
+   ens_size                 = 3,
+   obs_sequence_in_name     = "obs_seq.out",
+   obs_sequence_out_name    = "obs_seq.final",
+   input_state_file_list    = "input_list.txt"
+   output_state_file_list   = "output_list.txt"
+   init_time_days           = -1,
+   init_time_seconds        = -1,
+   first_obs_days           = -1,
+   first_obs_seconds        = -1,
+   last_obs_days            = -1,
+   last_obs_seconds         = -1,
+   num_output_state_members = 0,
+   num_output_obs_members   = 32,
+   output_interval          = 1,
+   num_groups               = 1,
+   distributed_state        = .true.
+   compute_posterior        = .true.
+   output_forward_op_errors = .false.,
+   output_timestamps        = .false.,
+   trace_execution          = .false.,
+
+   stages_to_write          = 'preassim', 'output'
+   output_members           = .false.
+   output_mean              = .true.
+   output_sd                = .false.
+   write_all_stages_at_end  = .false.
+
+   inf_flavor                  = 2,                      0,
+   inf_initial_from_restart    = .true.,                 .false.,
+   inf_sd_initial_from_restart = .true.,                 .false.,
+   inf_initial                 = 1.0,                     1.00,
+   inf_lower_bound             = 1.0,                     1.0,
+   inf_upper_bound             = 1000000.0,               1000000.0,
+   inf_damping                 = 0.9,                     1.0,
+   inf_sd_initial              = 0.6,                     0.0,
+   inf_sd_lower_bound          = 0.6,                     0.0,
+   inf_sd_max_change           = 1.05,                    1.05,
+   /
+
+&quality_control_nml
+   input_qc_threshold          = 3.0,
+   outlier_threshold           = 3.0,
+   enable_special_outlier_code = .false.
+   /
+
+&fill_inflation_restart_nml
+   write_prior_inf = .true.
+   prior_inf_mean  = 1.00
+   prior_inf_sd    = 0.6
+
+   write_post_inf  = .false.
+   post_inf_mean   = 1.00
+   post_inf_sd     = 0.6
+
+   input_state_files = 'wrfinput_d01', 'wrfinput_d02'
+   single_file       = .false.
+   verbose           = .false.
+   /
+
+&smoother_nml
+   num_lags              = 0,
+   start_from_restart    = .false.,
+   output_restart        = .false.,
+   restart_in_file_name  = 'smoother_ics',
+   restart_out_file_name = 'smoother_restart',
+   /
+
+# cutoff is in radians; for the earth, 0.05 is about 300 km.
+# cutoff is defined to be the half-width of the localization radius,
+# so 0.05 radians for cutoff is about an 600 km effective
+# localization radius, where the influence of an obs decreases
+# to ~half at 300 km, and ~0 at the edges of the area.
+&assim_tools_nml
+   filter_kind                     = 1,
+   cutoff                          = 0.05,
+   sort_obs_inc                    = .false.,
+   spread_restoration              = .false.,
+   sampling_error_correction       = .true.,
+   adaptive_localization_threshold = -1,
+   output_localization_diagnostics = .false.,
+   localization_diagnostics_file   = 'localization_diagnostics',
+   convert_all_state_verticals_first = .true.
+   convert_all_obs_verticals_first   = .true.
+   print_every_nth_obs               = 0,
+   /
+
+&cov_cutoff_nml
+   select_localization = 1,
+   /
+
+&obs_sequence_nml
+   write_binary_obs_sequence = .false.,
+   /
+
+&preprocess_nml
+   overwrite_output        = .true.
+   input_obs_qty_mod_file  = '../../../assimilation_code/modules/observations/DEFAULT_obs_kind_mod.F90'
+   output_obs_qty_mod_file = '../../../assimilation_code/modules/observations/obs_kind_mod.f90'
+   input_obs_def_mod_file  = '../../../observations/forward_operators/DEFAULT_obs_def_mod.F90'
+   output_obs_def_mod_file = '../../../observations/forward_operators/obs_def_mod.f90'
+   quantity_files          = '../../../assimilation_code/modules/observations/atmosphere_quantities_mod.f90'
+   obs_type_files          = '../../../observations/forward_operators/obs_def_reanalysis_bufr_mod.f90',
+                             '../../../observations/forward_operators/obs_def_radar_mod.f90',
+                             '../../../observations/forward_operators/obs_def_metar_mod.f90',
+                             '../../../observations/forward_operators/obs_def_dew_point_mod.f90',
+                             '../../../observations/forward_operators/obs_def_rel_humidity_mod.f90',
+                             '../../../observations/forward_operators/obs_def_altimeter_mod.f90',
+                             '../../../observations/forward_operators/obs_def_gps_mod.f90',
+                             '../../../observations/forward_operators/obs_def_vortex_mod.f90',
+                             '../../../observations/forward_operators/obs_def_gts_mod.f90',
+                             '../../../observations/forward_operators/obs_def_rttov_mod.f90'
+   /
+
+&obs_kind_nml
+   assimilate_these_obs_types = 'RADIOSONDE_TEMPERATURE',
+                                'RADIOSONDE_U_WIND_COMPONENT',
+                                'RADIOSONDE_V_WIND_COMPONENT',
+                                'SAT_U_WIND_COMPONENT',
+                                'SAT_V_WIND_COMPONENT',
+                                'AIRCRAFT_U_WIND_COMPONENT',
+                                'AIRCRAFT_V_WIND_COMPONENT',
+                                'AIRCRAFT_TEMPERATURE',
+                                'ACARS_U_WIND_COMPONENT',
+                                'ACARS_V_WIND_COMPONENT',
+                                'ACARS_TEMPERATURE',
+                                'GPSRO_REFRACTIVITY',
+                                'DOPPLER_RADIAL_VELOCITY',
+                                'RADAR_REFLECTIVITY',
+                                'MSG_4_SEVIRI_RADIANCE',
+                                'MSG_4_SEVIRI_TB',
+                                'MSG_4_SEVIRI_BDRF',
+                                'LAND_SFC_PRESSURE',
+                                'SYNOP_SURFACE_PRESSURE',
+                                'SYNOP_TEMPERATURE',
+                                'SYNOP_SPECIFIC_HUMIDITY',
+                                'GPS_PRECIPITABLE_WATER'
+   evaluate_these_obs_types   = 'RADIOSONDE_SPECIFIC_HUMIDITY',
+   /
+
+# Notes for obs_def_radar_mod_nml:
+# (1) Reflectivity limit can be applied to observations and/or forward operator.
+# (2) The default constants below match the WRF defaults.  They will need to
+# be changed for other cases, depending on which microphysics scheme is used.
+#
+
+&obs_def_radar_mod_nml
+   apply_ref_limit_to_obs      =   .false.,
+   reflectivity_limit_obs      =  -10.0,
+   lowest_reflectivity_obs     =  -10.0,
+   apply_ref_limit_to_fwd_op   =   .false.,
+   reflectivity_limit_fwd_op   =  -10.0,
+   lowest_reflectivity_fwd_op  =  -10.0,
+   max_radial_vel_obs          =   1000000,
+   allow_wet_graupel           =   .false.,
+   microphysics_type           =       2  ,
+   allow_dbztowt_conv          =   .false.,
+   dielectric_factor           =  0.224,
+   n0_rain                     =  8.0e6,
+   n0_graupel                  =  4.0e6,
+   n0_snow                     =  3.0e6,
+   rho_rain                    = 1000.0,
+   rho_graupel                 =  400.0,
+   rho_snow                    =  100.0,
+   /
+
+
+# Notes for model_nml:
+# (1) vert_localization_coord must be one of:
+#     1 = model level
+#     2 = pressure
+#     3 = height
+#     4 = scale height
+
+# set default_state_variables to .false. to use the explicit list.
+# otherwise it uses a hardcoded default list: U, V, W, PH, T, MU, QV only.
+# see ../wrf_state_variables_table for a full list of what wrf fields are
+# supported in the DART state vector, and what settings should be used here.
+# 'UPDATE' and 'NO_COPY_BACK' are supported in the 4th column; 'NO_UPDATE' is
+# not yet supported.
+
+&model_nml
+   default_state_variables = .false.,
+   wrf_state_variables = 'U',     'QTY_U_WIND_COMPONENT',     'TYPE_U',    'UPDATE','999',
+                         'V',     'QTY_V_WIND_COMPONENT',     'TYPE_V',    'UPDATE','999',
+                         'W',     'QTY_VERTICAL_VELOCITY',    'TYPE_W',    'UPDATE','999',
+                         'PH',    'QTY_GEOPOTENTIAL_HEIGHT',  'TYPE_GZ',   'UPDATE','999',
+                         'T',     'QTY_POTENTIAL_TEMPERATURE','TYPE_T',    'UPDATE','999',
+                         'MU',    'QTY_PRESSURE',             'TYPE_MU',   'UPDATE','999',
+                         'QVAPOR','QTY_VAPOR_MIXING_RATIO',   'TYPE_QV',   'UPDATE','999',
+                         'QICE',  'QTY_ICE_MIXING_RATIO',     'TYPE_QI',   'UPDATE','999',
+                         'QCLOUD','QTY_CLOUDWATER_MIXING_RATIO','TYPE_QC', 'UPDATE','999',
+                         'CLDFRA','QTY_CLOUD_FRACTION',       'TYPE_CFRAC','UPDATE','999',
+                         'PSFC',  'QTY_SURFACE_PRESSURE',     'TYPE_PSFC', 'UPDATE','999',
+                         'T2',    'QTY_2M_TEMPERATURE',       'TYPE_T',    'UPDATE','999',
+                         'TSK',   'QTY_SKIN_TEMPERATURE',     'TYPE_T',    'UPDATE','999',
+                         'REFL_10CM','QTY_RADAR_REFLECTIVITY','TYPE_REFL', 'UPDATE','999',
+   wrf_state_bounds    = 'QVAPOR','0.0','NULL','CLAMP',
+                         'QRAIN', '0.0','NULL','CLAMP',
+                         'QCLOUD','0.0','NULL','CLAMP',
+                         'QICE','0.0','NULL','CLAMP',
+                         'CLDFRA','0.0','1.0','CLAMP',
+   num_domains                 = 1,
+   calendar_type               = 3,
+   assimilation_period_seconds = 21600,
+   vert_localization_coord     = 3,
+   center_search_half_length   = 500000.,
+   center_spline_grid_scale    = 10,
+   sfc_elev_max_diff           = -1.0,
+   circulation_pres_level      = 80000.0,
+   circulation_radius          = 108000.0,
+   allow_obs_below_vol         = .false.
+   /
+
+# vert_normalization_X is amount of X equiv to 1 radian in horiz.
+# vert localization is 'cutoff' times the pressure/height/levels,
+# only if horiz_dist_only is set to .false. in the namelist below.
+# the default nlon/nlat should be good for most experiments. it sets 
+# an internal structure that speeds up searches.  don't change it
+# based on your grid size.  nlon must be an odd number.
+&location_nml
+   horiz_dist_only             = .false.,
+   vert_normalization_pressure = 6666666.7,
+   vert_normalization_height   = 5000000.0,
+   vert_normalization_level    = 2666.7,
+   vert_normalization_scale_height = 10.0,
+   approximate_distance        = .false.,
+   nlon                        = 71,
+   nlat                        = 36,
+   output_box_info             = .false.,
+   /
+
+&utilities_nml
+   TERMLEVEL = 1,
+   module_details = .false.,
+   logfilename = 'dart_log.out',
+   nmlfilename = 'dart_log.nml',
+   write_nml   = 'file',
+   /
+
+&mpi_utilities_nml
+   /
+
+&reg_factor_nml
+   select_regression    = 1,
+   input_reg_file       = "time_mean_reg",
+   save_reg_diagnostics = .false.,
+   reg_diagnostics_file = "reg_diagnostics",
+   /
+
+# layout = 2 spreads the IO tasks across the nodes.
+# This can greatly improve the performance in IO if
+# tasks_per_node is set to match your hardware
+&ensemble_manager_nml
+   layout = 2,
+   tasks_per_node = 16
+   /
+
+&obs_def_gps_nml
+   max_gpsro_obs = 100000,
+   / 
+
+&obs_def_tpw_nml
+   /
+
+# The times in the namelist for the obs_diag program are vectors
+# that follow the following sequence:
+# year   month   day   hour   minute   second
+# max_num_bins can be used to specify a fixed number of bins,
+# in which case last_bin_center should be safely in the future.
+#
+# Acceptable latitudes range from  [-90,  90]
+# Acceptable longitudes range from [  0, Inf]
+
+&obs_diag_nml
+   obs_sequence_name  = 'obs_seq.final',
+   obs_sequence_list  = '',
+   first_bin_center   =  2003, 1, 1, 0, 0, 0 ,
+   last_bin_center    =  2003, 1, 2, 0, 0, 0 ,
+   bin_separation     =     0, 0, 0,12, 0, 0 ,
+   bin_width          =     0, 0, 0, 6, 0, 0 ,
+   time_to_skip       =     0, 0, 0, 0, 0, 0 ,
+   max_num_bins       = 1000,
+   trusted_obs        = 'null',
+   Nregions   = 4,
+   lonlim1    =   0.0,   0.0,   0.0, 235.0,
+   lonlim2    = 360.0, 360.0, 360.0, 295.0,
+   latlim1    =  20.0, -80.0, -20.0,  25.0,
+   latlim2    =  80.0, -20.0,  20.0,  55.0,
+   reg_names  = 'Northern Hemisphere', 'Southern Hemisphere', 'Tropics', 'North America',
+   print_mismatched_locs = .false.,
+   create_rank_histogram = .true.,
+   outliers_in_histogram = .true.,
+   use_zero_error_obs    = .false.,
+   verbose               = .false.
+   /
+
+&schedule_nml
+   calendar        = 'Gregorian',  
+   first_bin_start =  1601,  1,  1,  0,  0,  0,
+   first_bin_end   =  2999,  1,  1,  0,  0,  0,
+   last_bin_end    =  2999,  1,  1,  0,  0,  0,
+   bin_interval_days    = 1000000,
+   bin_interval_seconds = 0,   
+   max_num_bins         = 1000,
+   print_table          = .true.,
+   /
+   
+&obs_seq_to_netcdf_nml  
+   obs_sequence_name = 'obs_seq.final',
+   obs_sequence_list = '',
+   append_to_netcdf  = .false.,
+   lonlim1    =    0.0,
+   lonlim2    =  360.0,
+   latlim1    =  -90.0,
+   latlim2    =   90.0,
+   verbose    = .false.,
+   /
+
+# There is one GIGANTIC difference between the obsdef_mask.txt and .nc
+# The netCDF file intentionally ignores the effect of nTmin/nTmax.
+# The netCDF file has ALL matching stations, regardless of temporal coverage.
+
+&obs_seq_coverage_nml
+   obs_sequences     = ''
+   obs_sequence_list = 'obs_coverage_list.txt'
+   obs_of_interest   = 'METAR_U_10_METER_WIND'
+   textfile_out      = 'METAR_U_10_METER_WIND_obsdef_mask.txt'
+   netcdf_out        = 'METAR_U_10_METER_WIND_obsdef_mask.nc'
+   first_analysis    =  2003, 1, 1, 0, 0, 0
+   last_analysis     =  2003, 1, 2, 0, 0, 0
+   forecast_length_days          = 1
+   forecast_length_seconds       = 0
+   verification_interval_seconds = 21600
+   temporal_coverage_percent     = 100.0
+   lonlim1    =    0.0
+   lonlim2    =  360.0
+   latlim1    =  -90.0
+   latlim2    =   90.0
+   verbose    = .true.
+   /
+
+# selections_file is a list of obs_defs output
+# from the obs_seq_coverage utility.
+
+&obs_selection_nml
+   filename_seq          = 'obs_seq.out', 
+   filename_seq_list     = '', 
+   filename_out          = 'obs_seq.processed', 
+   selections_file       = 'obsdef_mask.txt', 
+   selections_is_obs_seq = .false.,
+   print_only            = .false., 
+   calendar              = 'gregorian',
+   /
+
+&obs_seq_verify_nml
+   obs_sequences     = ''
+   obs_sequence_list = 'obs_verify_list.txt'
+   input_template    = 'obsdef_mask.nc'
+   netcdf_out        = 'forecast.nc'
+   obtype_string     = 'METAR_U_10_METER_WIND'
+   print_every       = 10000
+   verbose           = .true.
+   debug             = .false.
+   /
+
+&obs_sequence_tool_nml
+   num_input_files   = 1, 
+   filename_seq      = 'obs_seq.out',
+   filename_out      = 'obs_seq.processed', 
+   first_obs_days    = -1, 
+   first_obs_seconds = -1, 
+   last_obs_days     = -1, 
+   last_obs_seconds  = -1, 
+   obs_types         = '', 
+   keep_types        = .false., 
+   print_only        = .false., 
+   min_lat           = -90.0, 
+   max_lat           =  90.0, 
+   min_lon           =   0.0, 
+   max_lon           = 360.0,
+   /
+
+&replace_wrf_fields_nml
+   debug = .false.,
+   fail_on_missing_field = .false.,
+   fieldnames = "SNOWC",
+                "ALBBCK",
+                "TMN",
+                "TSK",
+                "SH2O",
+                "SMOIS",
+                "SEAICE",
+                "HGT_d01",
+                "TSLB",
+                "SST",
+                "SNOWH",
+                "SNOW",
+   fieldlist_file = '',
+   /
+
+&obs_common_subset_nml
+   num_to_compare_at_once = 2,
+   filename_seq           = 'obs_seq1.final', 'obs_seq2.final',
+   filename_seq_list      = '',
+   filename_out_suffix    = '.common' ,
+   calendar               = 'Gregorian',
+   print_every            = 1000,
+   dart_qc_threshold      = 3,
+   print_only             = .false.,
+   /
+
+&wrf_dart_to_fields_nml
+   include_slp             = .true.,
+   include_wind_components = .true.,
+   include_height_on_pres  = .true.,
+   include_temperature     = .true.,
+   include_rel_humidity    = .true.,
+   include_surface_fields  = .false.,
+   include_sat_ir_temp     = .false.,
+   pres_levels             = 70000.,
+   /
+
+&ncepobs_nml
+   year = 2010,
+   month = 06,
+   day = 00,
+   tot_days = 1,
+   max_num = 1000000,
+   ObsBase = 'temp_obs.',
+   select_obs  = 0,
+   ADPUPA = .false.,
+   AIRCAR = .false.,
+   AIRCFT = .false.,
+   SATEMP = .false.,
+   SFCSHP = .false.,
+   ADPSFC = .false.,
+   SATWND = .true.,
+   obs_U  = .false.,
+   obs_V  = .false.,
+   obs_T  = .false.,
+   obs_PS = .false.,
+   obs_QV = .false.,
+   daily_file = .true.,
+   obs_time = .false.,
+   lat1 = 10.00,
+   lat2 = 60.00,
+   lon1 = 210.0,
+   lon2 = 300.0
+   /
+
+&prep_bufr_nml
+   obs_window_upa = 1.0,
+   obs_window_air = 1.0,
+   obs_window_cw = 1.0,
+   otype_use      = 242.0, 243.0, 245.0, 246.0, 251.0, 252.0, 253.0, 257.0, 259.0
+   qctype_use     = 0, 1, 2, 3, 4, 9, 15
+   /
+
+&convert_cosmic_gps_nml
+   gpsro_netcdf_file     = '',
+   gpsro_netcdf_filelist = 'flist',
+   gpsro_out_file        = 'obs_seq.gpsro',
+   local_operator        = .true.,
+   obs_levels            = 0.22, 0.55, 1.1, 1.8, 2.7, 3.7, 4.9,
+                           6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 12.0, 13.0,
+   ray_ds                = 5000.0,
+   ray_htop              = 13000.1,
+   /
+
+&wrf_obs_preproc_nml
+
+   file_name_input          = 'obs_seq20110901'
+   file_name_output         = 'obs_seq.europe.prev'
+  
+   overwrite_obs_time       = .false.  
+  
+   obs_boundary             = 0.0   
+   increase_bdy_error       = .false.  
+   maxobsfac                = 2.5   
+   obsdistbdy               = 1.0  
+  
+   sfc_elevation_check      = .false.  
+   sfc_elevation_tol        = 3000.0  
+   obs_pressure_top         = 0.0  
+   obs_height_top           = 2.0e10  
+  
+   include_sig_data         = .true.   
+   tc_sonde_radii           = -1.0  
+  
+   superob_aircraft         = .true.  
+   aircraft_horiz_int       = 800.0  
+   aircraft_pres_int        = 25000.0  
+  
+   superob_sat_winds        = .true.    
+   sat_wind_horiz_int       = 800.0   
+   sat_wind_pres_int        = 25000.0  
+  
+   overwrite_ncep_satwnd_qc = .false.    
+   overwrite_ncep_sfc_qc    = .false.  
+   /
+
+!  sonde_extra              = 'obs_seq.rawin'
+!  land_sfc_extra           = 'obs_seq.land_sfc'
+!  metar_extra              = 'obs_seq.metar'
+!  marine_sfc_extra         = 'obs_seq.marine'
+!  sat_wind_extra           = 'obs_seq.satwnd'
+!  profiler_extra           = 'obs_seq.profiler'
+!  gpsro_extra              = 'obs_seq.gpsro'
+!  acars_extra              = 'obs_seq.acars'
+!  trop_cyclone_extra       = 'obs_seq.tc'
+
+&state_vector_io_nml
+   single_precision_output    = .true.,
+   /
+
+&compare_states_nml
+   /
+
+&closest_member_tool_nml 
+   input_restart_file_list   = 'input_file_list_d01.txt',
+   output_file_name          = 'closest_results.txt'
+   ens_size                  = 3,
+   single_restart_file_in    = .false.,
+   difference_method         = 4,
+   use_only_qtys             = 'QTY_U_WIND_COMPONENT'
+   /
+
+# To test both domains, you must change 'model_nml:num_domains = 2'
+
+&model_mod_check_nml
+   input_state_files     = 'wrfinput_d01', 'wrfinput_d02'
+   output_state_files    = 'mmc_output1.nc', 'mmc_output2.nc'
+   test1thru             = 0
+   run_tests             = 1,2,3,4,5
+   x_ind                 = 87370
+   loc_of_interest       = 231.0, 40.0, 10.0
+   quantity_of_interest  = 'QTY_U_WIND_COMPONENT'
+   interp_test_dlon      = 0.1
+   interp_test_dlat      = 0.1
+   interp_test_dvert     = 1000.0
+   interp_test_lonrange  = 250.0,  260.0
+   interp_test_latrange  =  30.0,   45.0
+   interp_test_vertrange = 2000.0, 4000.0
+   interp_test_vertcoord = 'VERTISHEIGHT'
+   verbose               = .false.
+   /
+
diff --git a/tests/test_inputnml.py b/tests/test_inputnml.py
new file mode 100644
index 0000000000000000000000000000000000000000..26466033dd02a2a1fca25dbf326359e26307fbc4
--- /dev/null
+++ b/tests/test_inputnml.py
@@ -0,0 +1,47 @@
+import os, shutil
+import datetime as dt
+
+from dartwrf import dart_nml
+
+
+
+def test_input_nml():
+    test_input = './input.nml.original'
+    test_output = './input.nml.output'
+    desired_output = './input.nml.desired_output'
+
+    # read an existing input.nml
+    nml = dart_nml.read_namelist(test_input)
+
+    # modify one parameter
+    nml['&filter_nml']['ens_size'] = [[str(999)]]
+    nml['&filter_nml']['num_output_state_members'] = [[str(999)]]
+    nml['&filter_nml']['num_output_obs_members'] = [[str(999)]]
+
+    # save the configuration as input.nml
+    dart_nml.write_namelist_from_dict(nml, test_output)
+
+    # compare the saved input.nml to the true input.nml
+    # by reading both and comparing the dictionaries
+    nml_desired = dart_nml.read_namelist(desired_output)
+    nml_test = dart_nml.read_namelist(test_output)
+
+    for section, _ in nml_desired.items():
+
+        for param, value in nml_desired[section].items():
+
+            should_have = nml_desired[section][param]
+            should_have = [v.strip() for line in should_have for v in line]
+
+            have = nml_test[section][param]
+            have = [v.strip() for line in have for v in line]
+            
+            if should_have != have:
+
+                raise ValueError(section, param, 'should be', should_have, 'but is', have)
+
+    
+    os.remove(test_output)
+
+if __name__ == '__main__':
+    test_input_nml()