diff --git a/examples/EAGLE_ICs/EAGLE_12/eagle_12.yml b/examples/EAGLE_ICs/EAGLE_12/eagle_12.yml index 3e55ec9274a23d39818c19a1e5e3c292806c4682..cf4d711c5cb3bff4e355587343a33282f03a84b9 100644 --- a/examples/EAGLE_ICs/EAGLE_12/eagle_12.yml +++ b/examples/EAGLE_ICs/EAGLE_12/eagle_12.yml @@ -164,7 +164,7 @@ EAGLEFeedback: SNII_yield_factor_Nitrogen: 1.0 # (Optional) Correction factor to apply to the Nitrogen yield from the SNII channel. SNII_yield_factor_Oxygen: 1.0 # (Optional) Correction factor to apply to the Oxygen yield from the SNII channel. SNII_yield_factor_Neon: 1.0 # (Optional) Correction factor to apply to the Neon yield from the SNII channel. - SNII_yield_factor_Magnesium: 2.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. + SNII_yield_factor_Magnesium: 4.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. SNII_yield_factor_Silicon: 1.0 # (Optional) Correction factor to apply to the Silicon yield from the SNII channel. SNII_yield_factor_Iron: 0.5 # (Optional) Correction factor to apply to the Iron yield from the SNII channel. diff --git a/examples/EAGLE_ICs/EAGLE_25/eagle_25.yml b/examples/EAGLE_ICs/EAGLE_25/eagle_25.yml index 9d3f466fd5031ef6cdb8d74836ab0fe274f58c93..ddd0470c2af2d547b5a9e642e0587cb9d8306ae9 100644 --- a/examples/EAGLE_ICs/EAGLE_25/eagle_25.yml +++ b/examples/EAGLE_ICs/EAGLE_25/eagle_25.yml @@ -165,7 +165,7 @@ EAGLEFeedback: SNII_yield_factor_Nitrogen: 1.0 # (Optional) Correction factor to apply to the Nitrogen yield from the SNII channel. SNII_yield_factor_Oxygen: 1.0 # (Optional) Correction factor to apply to the Oxygen yield from the SNII channel. SNII_yield_factor_Neon: 1.0 # (Optional) Correction factor to apply to the Neon yield from the SNII channel. - SNII_yield_factor_Magnesium: 2.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. + SNII_yield_factor_Magnesium: 4.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. SNII_yield_factor_Silicon: 1.0 # (Optional) Correction factor to apply to the Silicon yield from the SNII channel. SNII_yield_factor_Iron: 0.5 # (Optional) Correction factor to apply to the Iron yield from the SNII channel. diff --git a/examples/EAGLE_ICs/EAGLE_50/eagle_50.yml b/examples/EAGLE_ICs/EAGLE_50/eagle_50.yml index e7af43e7bb9fb3f189f3f528afdb04da84633648..c12e8b33b4dac82cd03eb7fc7a1a737271f0b78a 100644 --- a/examples/EAGLE_ICs/EAGLE_50/eagle_50.yml +++ b/examples/EAGLE_ICs/EAGLE_50/eagle_50.yml @@ -165,7 +165,7 @@ EAGLEFeedback: SNII_yield_factor_Nitrogen: 1.0 # (Optional) Correction factor to apply to the Nitrogen yield from the SNII channel. SNII_yield_factor_Oxygen: 1.0 # (Optional) Correction factor to apply to the Oxygen yield from the SNII channel. SNII_yield_factor_Neon: 1.0 # (Optional) Correction factor to apply to the Neon yield from the SNII channel. - SNII_yield_factor_Magnesium: 2.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. + SNII_yield_factor_Magnesium: 4.0 # (Optional) Correction factor to apply to the Magnesium yield from the SNII channel. SNII_yield_factor_Silicon: 1.0 # (Optional) Correction factor to apply to the Silicon yield from the SNII channel. SNII_yield_factor_Iron: 0.5 # (Optional) Correction factor to apply to the Iron yield from the SNII channel. diff --git a/examples/EAGLE_ICs/README b/examples/EAGLE_ICs/README index ac186af26f1ed6585c79d96b6a7d6ab7dc3339bf..7a9cdae549f5d74145009739add71e8555d0df41 100644 --- a/examples/EAGLE_ICs/README +++ b/examples/EAGLE_ICs/README @@ -3,6 +3,13 @@ the EAGLE suite of simulations. The cosmology, resolution and phases are the same as used in the original suite. The only difference is the file format, adapted for SWIFT. +Compared to the original EAGLE runs, the following changes have been +made: + + - The redshift of reionization has been lowered to 7.5 (from 11.5) + - The Magnesium yields from SNII stars have been boosted by a + factor of 2. + The scripts in this directory download the tables required to run the EAGLE model. Plotting scripts are also provided for basic quantities. diff --git a/src/engine.c b/src/engine.c index 131f1bfcca6cca9699cc75614bafdb07d7280928..bcc07e3e39b742e0bab288bce6020cbe64f8e01c 100644 --- a/src/engine.c +++ b/src/engine.c @@ -1834,7 +1834,7 @@ void engine_skip_drift(struct engine *e) { /* Skip everything that moves the particles */ if (t->type == task_type_drift_part || t->type == task_type_drift_gpart || - t->type == task_type_drift_spart) + t->type == task_type_drift_spart || t->type == task_type_drift_bpart) t->skip = 1; } diff --git a/src/engine_maketasks.c b/src/engine_maketasks.c index 637af45f51167534d1dd296bb8fb984a50b9ba03..d18990fa2e0b0622f50d4b53dbc049e21a6907e1 100644 --- a/src/engine_maketasks.c +++ b/src/engine_maketasks.c @@ -1125,8 +1125,7 @@ void engine_make_hierarchical_tasks_hydro(struct engine *e, struct cell *c, c->hydro.cooling = scheduler_addtask(s, task_type_cooling, task_subtype_none, 0, 0, c, NULL); - scheduler_addunlock(s, c->hydro.end_force, c->hydro.cooling); - scheduler_addunlock(s, c->hydro.cooling, c->super->kick2); + task_order_addunlock_cooling(s, c); } else { scheduler_addunlock(s, c->hydro.end_force, c->super->kick2); diff --git a/src/fof.c b/src/fof.c index 7d8af4ca33d8dde18c70d46ecbce14611171abfb..cff567d7dfdb548be6dd678c630ddf20405741a9 100644 --- a/src/fof.c +++ b/src/fof.c @@ -1968,6 +1968,9 @@ void fof_seed_black_holes(const struct fof_props *props, /* Set a smoothing length */ bp->h = p->h; + /* Save the ID */ + bp->id = p->id; + #ifdef SWIFT_DEBUG_CHECKS bp->ti_kick = p->ti_kick; bp->ti_drift = p->ti_drift; diff --git a/src/parallel_io.c b/src/parallel_io.c index 9eb4ec3dd36949d45264f7306d0cdd26d6859ebd..804013f1dd762491142c6e0aa472435c387bced5 100644 --- a/src/parallel_io.c +++ b/src/parallel_io.c @@ -1795,9 +1795,10 @@ void write_output_parallel(struct engine* e, const char* baseName, /* Select the fields to write */ stars_write_particles(sparts_written, list, &num_fields, with_cosmology); - num_fields += chemistry_write_sparticles(sparts, list + num_fields); - num_fields += tracers_write_sparticles(sparts, list + num_fields, - with_cosmology); + num_fields += + chemistry_write_sparticles(sparts_written, list + num_fields); + num_fields += tracers_write_sparticles( + sparts_written, list + num_fields, with_cosmology); if (with_fof) { num_fields += fof_write_sparts(sparts_written, list + num_fields); } diff --git a/src/space.c b/src/space.c index 417eb57b6a2ed907bc9fab45d7a325be98ad2fab..8f151b1ff372fb424dda6c5deda569bdd9a24c71 100644 --- a/src/space.c +++ b/src/space.c @@ -724,6 +724,20 @@ void space_allocate_extras(struct space *s, int verbose) { 0.5 * cells[0].width[1], 0.5 * cells[0].width[2]}; + /* The dithering vector + * Note that we use the old dithering vector here since + * (new - old) will be added to all positions further down */ + const double pos_dithering[3] = {s->pos_dithering_old[0], + s->pos_dithering_old[1], + s->pos_dithering_old[2]}; +#ifdef SWIFT_DEBUG_CHECKS + if (!s->e->gravity_properties->with_dithering) { + if (s->pos_dithering[0] != 0. || s->pos_dithering[1] != 0. || + s->pos_dithering[2] != 0.) + error("Non-zero dithering vector when dithering is off!"); + } +#endif + /* The current number of particles (including spare ones) */ size_t nr_parts = s->nr_parts; size_t nr_gparts = s->nr_gparts; @@ -844,9 +858,12 @@ void space_allocate_extras(struct space *s, int verbose) { if (s->gparts[i].time_bin == time_bin_not_created) { /* We want the extra particles to be at the centre of their cell */ - s->gparts[i].x[0] = cells[current_cell].loc[0] + half_cell_width[0]; - s->gparts[i].x[1] = cells[current_cell].loc[1] + half_cell_width[1]; - s->gparts[i].x[2] = cells[current_cell].loc[2] + half_cell_width[2]; + s->gparts[i].x[0] = + cells[current_cell].loc[0] + half_cell_width[0] - pos_dithering[0]; + s->gparts[i].x[1] = + cells[current_cell].loc[1] + half_cell_width[1] - pos_dithering[1]; + s->gparts[i].x[2] = + cells[current_cell].loc[2] + half_cell_width[2] - pos_dithering[2]; ++count_in_cell; count_extra_gparts++; } @@ -876,7 +893,7 @@ void space_allocate_extras(struct space *s, int verbose) { /* Do we have enough space for the extra parts (i.e. we haven't used up any) ? */ - if (expected_num_extra_parts > s->nr_extra_parts) { + if (nr_actual_parts + expected_num_extra_parts > nr_parts) { /* Ok... need to put some more in the game */ @@ -918,7 +935,7 @@ void space_allocate_extras(struct space *s, int verbose) { bzero(&s->parts[i], sizeof(struct part)); bzero(&s->xparts[i], sizeof(struct xpart)); s->parts[i].time_bin = time_bin_not_created; - s->parts[i].id = -1; + s->parts[i].id = -42; } /* Put the spare particles in their correct cell */ @@ -936,9 +953,12 @@ void space_allocate_extras(struct space *s, int verbose) { if (s->parts[i].time_bin == time_bin_not_created) { /* We want the extra particles to be at the centre of their cell */ - s->parts[i].x[0] = cells[current_cell].loc[0] + half_cell_width[0]; - s->parts[i].x[1] = cells[current_cell].loc[1] + half_cell_width[1]; - s->parts[i].x[2] = cells[current_cell].loc[2] + half_cell_width[2]; + s->parts[i].x[0] = + cells[current_cell].loc[0] + half_cell_width[0] - pos_dithering[0]; + s->parts[i].x[1] = + cells[current_cell].loc[1] + half_cell_width[1] - pos_dithering[1]; + s->parts[i].x[2] = + cells[current_cell].loc[2] + half_cell_width[2] - pos_dithering[2]; ++count_in_cell; count_extra_parts++; } @@ -1018,9 +1038,12 @@ void space_allocate_extras(struct space *s, int verbose) { if (s->sparts[i].time_bin == time_bin_not_created) { /* We want the extra particles to be at the centre of their cell */ - s->sparts[i].x[0] = cells[current_cell].loc[0] + half_cell_width[0]; - s->sparts[i].x[1] = cells[current_cell].loc[1] + half_cell_width[1]; - s->sparts[i].x[2] = cells[current_cell].loc[2] + half_cell_width[2]; + s->sparts[i].x[0] = + cells[current_cell].loc[0] + half_cell_width[0] - pos_dithering[0]; + s->sparts[i].x[1] = + cells[current_cell].loc[1] + half_cell_width[1] - pos_dithering[1]; + s->sparts[i].x[2] = + cells[current_cell].loc[2] + half_cell_width[2] - pos_dithering[2]; ++count_in_cell; count_extra_sparts++; } @@ -1100,9 +1123,12 @@ void space_allocate_extras(struct space *s, int verbose) { if (s->bparts[i].time_bin == time_bin_not_created) { /* We want the extra particles to be at the centre of their cell */ - s->bparts[i].x[0] = cells[current_cell].loc[0] + half_cell_width[0]; - s->bparts[i].x[1] = cells[current_cell].loc[1] + half_cell_width[1]; - s->bparts[i].x[2] = cells[current_cell].loc[2] + half_cell_width[2]; + s->bparts[i].x[0] = + cells[current_cell].loc[0] + half_cell_width[0] - pos_dithering[0]; + s->bparts[i].x[1] = + cells[current_cell].loc[1] + half_cell_width[1] - pos_dithering[1]; + s->bparts[i].x[2] = + cells[current_cell].loc[2] + half_cell_width[2] - pos_dithering[2]; ++count_in_cell; count_extra_bparts++; } @@ -1203,13 +1229,13 @@ void space_rebuild(struct space *s, int repartitioned, int verbose) { /* Re-grid if necessary, or just re-set the cell data. */ space_regrid(s, verbose); - /* Allocate extra space for particles that will be created */ - if (s->with_star_formation) space_allocate_extras(s, verbose); - /* Are we dithering the particles? */ const int with_dithering = s->e->gravity_properties->with_dithering; if (s->with_self_gravity && with_dithering) space_dither(s, verbose); + /* Allocate extra space for particles that will be created */ + if (s->with_star_formation) space_allocate_extras(s, verbose); + struct cell *cells_top = s->cells_top; const integertime_t ti_current = (s->e != NULL) ? s->e->ti_current : 0; const int local_nodeID = s->e->nodeID; @@ -2211,6 +2237,12 @@ void space_parts_get_cell_index_mapper(void *map_data, int nr_parts, ind[k] = index; cell_counts[index]++; ++count_extra_part; + + /* Update the position (since we may have dithered) */ + p->x[0] = pos_x; + p->x[1] = pos_y; + p->x[2] = pos_z; + } else { /* Normal case: list its top-level cell index */ ind[k] = index; @@ -2343,6 +2375,12 @@ void space_gparts_get_cell_index_mapper(void *map_data, int nr_gparts, ind[k] = index; cell_counts[index]++; ++count_extra_gpart; + + /* Update the position (since we may have dithered) */ + gp->x[0] = pos_x; + gp->x[1] = pos_y; + gp->x[2] = pos_z; + } else { /* List its top-level cell index */ ind[k] = index; @@ -2481,6 +2519,12 @@ void space_sparts_get_cell_index_mapper(void *map_data, int nr_sparts, ind[k] = index; cell_counts[index]++; ++count_extra_spart; + + /* Update the position (since we may have dithered) */ + sp->x[0] = pos_x; + sp->x[1] = pos_y; + sp->x[2] = pos_z; + } else { /* List its top-level cell index */ ind[k] = index; @@ -2615,6 +2659,12 @@ void space_bparts_get_cell_index_mapper(void *map_data, int nr_bparts, ind[k] = index; cell_counts[index]++; ++count_extra_bpart; + + /* Update the position (since we may have dithered) */ + bp->x[0] = pos_x; + bp->x[1] = pos_y; + bp->x[2] = pos_z; + } else { /* List its top-level cell index */ ind[k] = index; diff --git a/src/task_order/EAGLE/task_order.h b/src/task_order/EAGLE/task_order.h index 9d3cf5a981fd1382bfa0e0256e057b1c608edac4..e6dff8610e07954fcb5ab3b0aea604eb01c100d9 100644 --- a/src/task_order/EAGLE/task_order.h +++ b/src/task_order/EAGLE/task_order.h @@ -40,4 +40,22 @@ INLINE static void task_order_addunlock_star_formation_feedback( c->stars.stars_in); } +/** + * @brief Place the cooling cell at the right place in the dependency + * graph. + * + * The default model follows EAGLE. + * + * In EAGLE, the cooling takes place between the hydro and the kick2. + * + * @param s The #scheduler. + * @param c The #cell on which to act. + */ +INLINE static void task_order_addunlock_cooling(struct scheduler *s, + struct cell *c) { + + scheduler_addunlock(s, c->hydro.end_force, c->hydro.cooling); + scheduler_addunlock(s, c->hydro.cooling, c->super->kick2); +} + #endif /* SWIFT_TASK_ORDER_EAGLE_H */ diff --git a/src/task_order/GEAR/task_order.h b/src/task_order/GEAR/task_order.h index f527453fda7845df8325dc0e60ab4f9c84351403..3708881db68d226e44a493451fbd147329e2bfee 100644 --- a/src/task_order/GEAR/task_order.h +++ b/src/task_order/GEAR/task_order.h @@ -39,4 +39,20 @@ INLINE static void task_order_addunlock_star_formation_feedback( scheduler_addunlock(s, c->stars.stars_out, c->top->hydro.star_formation); } +/** + * @brief Place the cooling cell at the right place in the dependency + * graph. + * + * In GEAR, the cooling takes place after the kick1. + * + * @param s The #scheduler. + * @param c The #cell on which to act. + */ +INLINE static void task_order_addunlock_cooling(struct scheduler *s, + struct cell *c) { + + scheduler_addunlock(s, c->super->kick1, c->hydro.cooling); + scheduler_addunlock(s, c->hydro.end_force, c->super->kick2); +} + #endif /* SWIFT_TASK_ORDER_GEAR_H */ diff --git a/src/task_order/none/task_order.h b/src/task_order/none/task_order.h index 6ee1a99de18f00d7d9caf92279d2aa16eb03f158..3bb7975f4331b93d1a28caa93a199ba2274cfcc1 100644 --- a/src/task_order/none/task_order.h +++ b/src/task_order/none/task_order.h @@ -42,4 +42,22 @@ INLINE static void task_order_addunlock_star_formation_feedback( c->stars.stars_in); } +/** + * @brief Place the cooling cell at the right place in the dependency + * graph. + * + * The default model follows EAGLE. + * + * In EAGLE, the cooling takes place between the hydro and the kick2. + * + * @param s The #scheduler. + * @param c The #cell on which to act. + */ +INLINE static void task_order_addunlock_cooling(struct scheduler *s, + struct cell *c) { + + scheduler_addunlock(s, c->hydro.end_force, c->hydro.cooling); + scheduler_addunlock(s, c->hydro.cooling, c->super->kick2); +} + #endif /* SWIFT_TASK_ORDER_NONE_H */