aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authortradke <tradke@94b1c47f-dcfd-45ef-a468-0854c0e9e350>2002-04-15 13:07:16 +0000
committertradke <tradke@94b1c47f-dcfd-45ef-a468-0854c0e9e350>2002-04-15 13:07:16 +0000
commit8c87ce629147b4040461ed28048fb15ca1f4a2c4 (patch)
treeb51c883c8449c2e60f9ff66f5962ca1400e6fc36
parent88a045f23bf33bbe1e309f046b81508260ea723a (diff)
Switch to the new Hyperslab API. You need to update CactusPUGH/PUGHSlab if
you haven't done so yet. git-svn-id: http://svn.cactuscode.org/arrangements/CactusBase/IOASCII/trunk@105 94b1c47f-dcfd-45ef-a468-0854c0e9e350
-rw-r--r--src/Output1D.c77
-rw-r--r--src/Output2D.c79
-rw-r--r--src/Output3D.c81
-rw-r--r--src/Startup.c31
-rw-r--r--src/Write1D.c476
-rw-r--r--src/Write2D.c830
-rw-r--r--src/Write3D.c670
-rw-r--r--src/ioASCIIGH.h27
8 files changed, 1162 insertions, 1109 deletions
diff --git a/src/Output1D.c b/src/Output1D.c
index 8c18aed..4610b02 100644
--- a/src/Output1D.c
+++ b/src/Output1D.c
@@ -67,12 +67,6 @@ int IOASCII_Output1DGH (const cGH *GH)
CheckSteerableParameters (myGH);
- /* Return if no output is required */
- if (myGH->out1D_every <= 0)
- {
- return (0);
- }
-
/* Loop over all variables */
for (vindex = retval = 0; vindex < CCTK_NumVars (); vindex++)
{
@@ -204,15 +198,9 @@ int IOASCII_TimeFor1D (const cGH *GH, int vindex)
CheckSteerableParameters (myGH);
- /* return if no output requested */
- if (myGH->out1D_every <= 0)
- {
- return (0);
- }
-
/* Check if this variable should be output */
- if (myGH->do_out1D[vindex] &&
- GH->cctk_iteration % myGH->out1D_every == 0)
+ if (myGH->out1D_every[vindex] > 0 &&
+ GH->cctk_iteration % myGH->out1D_every[vindex] == 0)
{
/* Check if this variable wasn't already output this iteration */
if (myGH->out1D_last[vindex] == GH->cctk_iteration)
@@ -293,28 +281,22 @@ int IOASCII_TriggerOutput1D (const cGH *GH, int vindex)
/* check if steerable parameters have changed */
static void CheckSteerableParameters (asciiioGH *myGH)
{
- int i, num_vars, out_old, times_set;
+ int i, num_vars;
char *fullname, *msg;
- static int out1D_vars_lastset = -1;
DECLARE_CCTK_PARAMETERS
- out_old = myGH->out1D_every;
-
/* How often to output */
- myGH->out1D_every = out_every > 0 ? out_every : -1;
- if (out1D_every > 0)
- {
- myGH->out1D_every = out1D_every;
- }
+ i = myGH->out1D_every_default;
+ myGH->out1D_every_default = out1D_every > 0 ? out1D_every : out_every;
/* Report if frequency changed */
- if (myGH->out1D_every != out_old && ! CCTK_Equals (newverbose, "none"))
+ if (myGH->out1D_every_default != i && ! CCTK_Equals (newverbose, "none"))
{
- if (myGH->out1D_every > 0)
+ if (myGH->out1D_every_default > 0)
{
CCTK_VInfo (CCTK_THORNSTRING, "IOASCII_1D: Periodic output every %d "
- "iterations", myGH->out1D_every);
+ "iterations", myGH->out1D_every_default);
}
else
{
@@ -323,20 +305,18 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* re-parse the 'out1D_vars' parameter if it was changed */
- times_set = CCTK_ParameterQueryTimesSet ("out1D_vars", CCTK_THORNSTRING);
- if (times_set != out1D_vars_lastset)
+ if (strcmp (out1D_vars, myGH->out1D_vars) || myGH->out1D_every_default != i)
{
num_vars = CCTK_NumVars ();
- memset (myGH->do_out1D, 0, num_vars);
- CCTK_TraverseString (out1D_vars, SetOutputFlag, myGH->do_out1D,
- CCTK_GROUP_OR_VAR);
+ memset (myGH->out1D_every, 0, num_vars * sizeof (int));
+ CCTK_TraverseString (out1D_vars, SetOutputFlag, myGH, CCTK_GROUP_OR_VAR);
- if (! CCTK_Equals (newverbose, "none"))
+ if (myGH->out1D_every_default == i || ! CCTK_Equals (newverbose, "none"))
{
msg = NULL;
for (i = 0; i < num_vars; i++)
{
- if (myGH->do_out1D[i])
+ if (myGH->out1D_every[i] > 0)
{
fullname = CCTK_FullName (i);
if (! msg)
@@ -359,9 +339,9 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* Save the last setting of 'out1D_vars' parameter */
- out1D_vars_lastset = times_set;
+ free (myGH->out1D_vars);
+ myGH->out1D_vars = strdup (out1D_vars);
}
-
}
@@ -393,18 +373,27 @@ static int CheckOutputVar (int vindex)
for the given variable */
static void SetOutputFlag (int vindex, const char *optstring, void *arg)
{
- char *flags = (char *) arg;
+ char *endptr;
+ asciiioGH *myGH = (asciiioGH *) arg;
if (CheckOutputVar (vindex) == 0)
{
- flags[vindex] = 1;
- }
-
- if (optstring)
- {
- CCTK_VWarn (5, __LINE__, __FILE__, CCTK_THORNSTRING,
- "SetOutputFlag: Optional string '%s' in variable name ignored",
- optstring);
+ myGH->out1D_every[vindex] = myGH->out1D_every_default;
+ if (optstring)
+ {
+ endptr = "error";
+ if (strncmp ("out_every=", optstring, 10) == 0)
+ {
+ myGH->out1D_every[vindex] = strtol (optstring + 10, &endptr, 10);
+ }
+ if (endptr && *endptr)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "SetOutputFlag: Optional string '%s' could not be parsed",
+ optstring);
+ myGH->out1D_every[vindex] = 0;
+ }
+ }
}
}
diff --git a/src/Output2D.c b/src/Output2D.c
index 721a067..0ccb68d 100644
--- a/src/Output2D.c
+++ b/src/Output2D.c
@@ -67,20 +67,13 @@ int IOASCII_Output2DGH (const cGH *GH)
CheckSteerableParameters (myGH);
- /* Return if no output is required */
- if (myGH->out2D_every <= 0)
- {
- return (0);
- }
-
/* Loop over all variables */
for (vindex = retval = 0; vindex < CCTK_NumVars (); vindex++)
{
-
/* Check if this variable should be output */
if (! IOASCII_TimeFor2D (GH, vindex))
{
- continue;
+ continue;
}
/* Get the variable name for this index (for filename) */
@@ -205,14 +198,9 @@ int IOASCII_TimeFor2D (const cGH *GH, int vindex)
CheckSteerableParameters (myGH);
- /* return if no output requested */
- if (myGH->out2D_every <= 0)
- {
- return (0);
- }
-
/* Check if this variable should be output */
- if (myGH->do_out2D[vindex] && (GH->cctk_iteration % myGH->out2D_every == 0))
+ if (myGH->out2D_every[vindex] > 0 &&
+ GH->cctk_iteration % myGH->out2D_every[vindex] == 0)
{
/* Check if variable wasn't already output this iteration */
if (myGH->out2D_last[vindex] == GH->cctk_iteration)
@@ -294,29 +282,22 @@ int IOASCII_TriggerOutput2D (const cGH *GH, int vindex)
/* check if steerable parameters have changed */
static void CheckSteerableParameters (asciiioGH *myGH)
{
- int i, out_old, times_set, num_vars;
+ int i, num_vars;
char *fullname, *msg;
- static int out2D_vars_lastset = -1;
DECLARE_CCTK_PARAMETERS
- out_old = myGH->out2D_every;
-
/* How often to output */
- myGH->out2D_every = out_every > 0 ? out_every : -1;
- if (out2D_every > 0)
- {
- myGH->out2D_every = out2D_every;
- }
+ i = myGH->out2D_every_default;
+ myGH->out2D_every_default = out2D_every > 0 ? out2D_every : out_every;
/* Report if frequency changed */
-
- if (myGH->out2D_every != out_old && ! CCTK_Equals (newverbose, "none"))
+ if (myGH->out2D_every_default != i && ! CCTK_Equals (newverbose, "none"))
{
- if (myGH->out2D_every >0)
+ if (myGH->out2D_every_default > 0)
{
CCTK_VInfo (CCTK_THORNSTRING, "IOASCII_2D: Periodic output every %d "
- "iterations", myGH->out2D_every);
+ "iterations", myGH->out2D_every_default);
}
else
{
@@ -325,20 +306,18 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* re-parse the 'out2D_vars' parameter if it was changed */
- times_set = CCTK_ParameterQueryTimesSet ("out2D_vars", CCTK_THORNSTRING);
- if (times_set != out2D_vars_lastset)
+ if (strcmp (out2D_vars, myGH->out2D_vars) || myGH->out2D_every_default != i)
{
num_vars = CCTK_NumVars ();
- memset (myGH->do_out2D, 0, num_vars);
- CCTK_TraverseString (out2D_vars, SetOutputFlag, myGH->do_out2D,
- CCTK_GROUP_OR_VAR);
+ memset (myGH->out2D_every, 0, num_vars * sizeof (int));
+ CCTK_TraverseString (out2D_vars, SetOutputFlag, myGH, CCTK_GROUP_OR_VAR);
- if (! CCTK_Equals (newverbose, "none"))
+ if (myGH->out2D_every_default == i || ! CCTK_Equals (newverbose, "none"))
{
msg = NULL;
for (i = 0; i < num_vars; i++)
{
- if (myGH->do_out2D[i])
+ if (myGH->out2D_every[i])
{
fullname = CCTK_FullName (i);
if (! msg)
@@ -361,7 +340,8 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* Save the last setting of 'out2D_vars' parameter */
- out2D_vars_lastset = times_set;
+ free (myGH->out2D_vars);
+ myGH->out2D_vars = strdup (out2D_vars);
}
}
@@ -405,18 +385,27 @@ static int CheckOutputVar (int vindex)
for the given variable */
static void SetOutputFlag (int vindex, const char *optstring, void *arg)
{
- char *flags = (char *) arg;
+ char *endptr;
+ asciiioGH *myGH = (asciiioGH *) arg;
- /* Check the variable type */
if (CheckOutputVar (vindex) == 0)
{
- flags[vindex] = 1;
- }
-
- if (optstring)
- {
- CCTK_VWarn (5, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Optional string '%s' in variable name ignored", optstring);
+ myGH->out2D_every[vindex] = myGH->out2D_every_default;
+ if (optstring)
+ {
+ endptr = "error";
+ if (strncmp ("out_every=", optstring, 10) == 0)
+ {
+ myGH->out2D_every[vindex] = strtol (optstring + 10, &endptr, 10);
+ }
+ if (endptr && *endptr)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "SetOutputFlag: Optional string '%s' could not be parsed",
+ optstring);
+ myGH->out2D_every[vindex] = 0;
+ }
+ }
}
}
diff --git a/src/Output3D.c b/src/Output3D.c
index 7bd3b55..78d8354 100644
--- a/src/Output3D.c
+++ b/src/Output3D.c
@@ -67,20 +67,13 @@ int IOASCII_Output3DGH (const cGH *GH)
CheckSteerableParameters (myGH);
- /* Return if no output is required */
- if (myGH->out3D_every <= 0)
- {
- return (0);
- }
-
/* Loop over all variables */
for (vindex = retval = 0; vindex < CCTK_NumVars (); vindex++)
{
-
/* Check if this variable should be output */
if (! IOASCII_TimeFor3D (GH, vindex))
{
- continue;
+ continue;
}
/* Get the variable name for this index (for filename) */
@@ -205,14 +198,9 @@ int IOASCII_TimeFor3D (const cGH *GH, int vindex)
CheckSteerableParameters (myGH);
- /* return if no output requested */
- if (myGH->out3D_every <= 0)
- {
- return (0);
- }
-
/* Check if this variable should be output */
- if (myGH->do_out3D[vindex] && (GH->cctk_iteration % myGH->out3D_every == 0))
+ if (myGH->out3D_every[vindex] > 0 &&
+ GH->cctk_iteration % myGH->out3D_every[vindex] == 0)
{
/* Check if variable wasn't already output this iteration */
if (myGH->out3D_last[vindex] == GH->cctk_iteration)
@@ -294,29 +282,22 @@ int IOASCII_TriggerOutput3D (const cGH *GH, int vindex)
/* check if steerable parameters have changed */
static void CheckSteerableParameters (asciiioGH *myGH)
{
- int i, out_old, times_set, num_vars;
+ int i, num_vars;
char *fullname, *msg;
- static int out3D_vars_lastset = -1;
DECLARE_CCTK_PARAMETERS
- out_old = myGH->out3D_every;
-
/* How often to output */
- myGH->out3D_every = out_every > 0 ? out_every : -1;
- if (out3D_every > 0)
- {
- myGH->out3D_every = out3D_every;
- }
+ i = myGH->out3D_every_default;
+ myGH->out3D_every_default = out3D_every > 0 ? out3D_every : out_every;
/* Report if frequency changed */
-
- if (myGH->out3D_every != out_old && ! CCTK_Equals (newverbose, "none"))
+ if (myGH->out3D_every_default != i && ! CCTK_Equals (newverbose, "none"))
{
- if (myGH->out3D_every > 0)
+ if (myGH->out3D_every_default > 0)
{
CCTK_VInfo (CCTK_THORNSTRING, "IOASCII_3D: Periodic output every %d "
- "iterations", myGH->out3D_every);
+ "iterations", myGH->out3D_every_default);
}
else
{
@@ -325,21 +306,18 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* re-parse the 'out3D_vars' parameter if it was changed */
- times_set = CCTK_ParameterQueryTimesSet ("out3D_vars", CCTK_THORNSTRING);
- if (times_set != out3D_vars_lastset)
+ if (strcmp (out3D_vars, myGH->out3D_vars) || myGH->out3D_every_default != i)
{
num_vars = CCTK_NumVars ();
- memset (myGH->do_out3D, 0, num_vars);
- CCTK_TraverseString (out3D_vars, SetOutputFlag, myGH->do_out3D,
- CCTK_GROUP_OR_VAR);
+ memset (myGH->out3D_every, 0, num_vars * sizeof (int));
+ CCTK_TraverseString (out3D_vars, SetOutputFlag, myGH, CCTK_GROUP_OR_VAR);
- if (CCTK_Equals (newverbose, "standard") ||
- CCTK_Equals (newverbose, "full"))
+ if (myGH->out3D_every_default == i || ! CCTK_Equals (newverbose, "none"))
{
msg = NULL;
for (i = 0; i < num_vars; i++)
{
- if (myGH->do_out3D[i])
+ if (myGH->out3D_every[i] > 0)
{
fullname = CCTK_FullName (i);
if (! msg)
@@ -362,9 +340,9 @@ static void CheckSteerableParameters (asciiioGH *myGH)
}
/* Save the last setting of 'out3D_vars' parameter */
- out3D_vars_lastset = times_set;
+ free (myGH->out3D_vars);
+ myGH->out3D_vars = strdup (out3D_vars);
}
-
}
@@ -407,18 +385,27 @@ static int CheckOutputVar (int vindex)
for the given variable */
static void SetOutputFlag (int vindex, const char *optstring, void *arg)
{
- char *flags = (char *) arg;
+ char *endptr;
+ asciiioGH *myGH = (asciiioGH *) arg;
- /* Check the variable type */
if (CheckOutputVar (vindex) == 0)
{
- flags[vindex] = 1;
- }
-
- if (optstring)
- {
- CCTK_VWarn (5, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Optional string '%s' in variable name ignored", optstring);
+ myGH->out3D_every[vindex] = myGH->out3D_every_default;
+ if (optstring)
+ {
+ endptr = "error";
+ if (strncmp ("out_every=", optstring, 10) == 0)
+ {
+ myGH->out3D_every[vindex] = strtol (optstring + 10, &endptr, 10);
+ }
+ if (endptr && *endptr)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "SetOutputFlag: Optional string '%s' could not be parsed",
+ optstring);
+ myGH->out3D_every[vindex] = 0;
+ }
+ }
}
}
diff --git a/src/Startup.c b/src/Startup.c
index de7dfb4..8d3494c 100644
--- a/src/Startup.c
+++ b/src/Startup.c
@@ -44,16 +44,16 @@ static void *IOASCII_SetupGH (tFleshConfig *config,
void IOASCII_Startup (void)
{
/* check that thorn IOUtil was activated */
- if (CCTK_GHExtensionHandle ("IO") < 0)
+ if (CCTK_GHExtensionHandle ("IO") >= 0)
+ {
+ CCTK_RegisterGHExtensionSetupGH (CCTK_RegisterGHExtension ("IOASCII"),
+ IOASCII_SetupGH);
+ }
+ else
{
CCTK_WARN (1, "IOASCII_Startup: Thorn IOUtil was not activated. "
"No IOASCII IO methods will be enabled.");
- return;
}
-
- CCTK_RegisterGHExtensionSetupGH (CCTK_RegisterGHExtension ("IOASCII"),
- IOASCII_SetupGH);
-
}
@@ -128,8 +128,7 @@ static void *IOASCII_SetupGH (tFleshConfig *config,
CCTK_RegisterIOMethodTimeToOutput (i, IOASCII_TimeFor3D);
CCTK_RegisterIOMethodTriggerOutput (i, IOASCII_TriggerOutput3D);
- if (CCTK_Equals (newverbose, "standard") ||
- CCTK_Equals( newverbose, "full"))
+ if (! CCTK_Equals (newverbose, "none"))
{
CCTK_INFO ("I/O Method 'IOASCII_1D' registered");
CCTK_INFO ("IOASCII_1D: Output of 1D lines of grid functions/arrays "
@@ -145,12 +144,12 @@ static void *IOASCII_SetupGH (tFleshConfig *config,
/* allocate the GH extension and its components */
newGH = (asciiioGH *) malloc (sizeof (asciiioGH));
- if(newGH)
+ if (newGH)
{
numvars = CCTK_NumVars ();
- newGH->do_out1D = (char *) malloc (numvars * sizeof (char));
- newGH->do_out2D = (char *) malloc (numvars * sizeof (char));
- newGH->do_out3D = (char *) malloc (numvars * sizeof (char));
+ newGH->out1D_every = (int *) malloc (numvars * sizeof (int));
+ newGH->out2D_every = (int *) malloc (numvars * sizeof (int));
+ newGH->out3D_every = (int *) malloc (numvars * sizeof (int));
newGH->out1D_last = (int *) malloc (numvars * sizeof (int));
newGH->out2D_last = (int *) malloc (numvars * sizeof (int));
newGH->out3D_last = (int *) malloc (numvars * sizeof (int));
@@ -162,6 +161,13 @@ static void *IOASCII_SetupGH (tFleshConfig *config,
newGH->out3D_last[i] = -1;
}
+ newGH->out1D_vars = strdup ("");
+ newGH->out2D_vars = strdup ("");
+ newGH->out3D_vars = strdup ("");
+ newGH->out1D_every_default = 0;
+ newGH->out2D_every_default = 0;
+ newGH->out3D_every_default = 0;
+
newGH->filenameList1D = NULL;
newGH->fileList_2D = NULL;
newGH->fileList_3D = NULL;
@@ -236,7 +242,6 @@ static void *IOASCII_SetupGH (tFleshConfig *config,
CCTK_VInfo (CCTK_THORNSTRING, "IOASCII_3D: Output to directory '%s'",
newGH->outdir3D);
}
-
}
else
{
diff --git a/src/Write1D.c b/src/Write1D.c
index f8ad0f3..b497d89 100644
--- a/src/Write1D.c
+++ b/src/Write1D.c
@@ -16,17 +16,15 @@
@version $Id$
@@*/
-#include <stdlib.h>
#include <math.h> /* sqrt(3) */
+#include <stdlib.h>
#include <string.h>
-#include <sys/types.h>
-#include <sys/stat.h> /* stat(2) */
#include "cctk.h"
#include "cctk_Parameters.h"
#include "Hyperslab.h"
+#include "CactusBase/IOUtil/src/ioGH.h"
#include "CactusBase/IOUtil/src/ioutil_AdvertisedFiles.h"
-#include "CactusBase/IOUtil/src/ioutil_CheckpointRecovery.h"
#include "ioASCIIGH.h"
/* the rcs ID and its dummy function to use it */
@@ -43,29 +41,28 @@ CCTK_FILEVERSION(CactusBase_IOASCII_Write1D_c)
/* Macro to output a 1D line (with coordinates if available) as typed data
For readability, the macro definition implicitely uses the following
variables (which are defined in the calling routine):
- hdata, hstride, hsize, complex_fmt_string */
-#define WRITE_DATA(hstart, cctk_type, c_type, is_complex, format, file) \
+ hdata, hstride, hsize, format[2] */
+#define WRITE_DATA(hstart, cctk_type, c_type, is_complex, fmt, file) \
{ \
int _h; \
- const cctk_type *_typed_data = (const cctk_type *) hdata[0]; \
- const CCTK_REAL *_coord_data = (const CCTK_REAL *) hdata[1]; \
+ const cctk_type *_hdata = (const cctk_type *) hdata[0]; \
+ const CCTK_REAL *_coord = (const CCTK_REAL *) hdata[1]; \
\
\
for (_h = hstart; _h < hstride * hsize; _h += hstride) \
{ \
- if (_coord_data) \
+ if (_coord) \
{ \
- fprintf (file, format, \
- (double) _coord_data[_h], (c_type) _typed_data[_h]); \
+ fprintf (file, fmt, (double) _coord[_h], (c_type) _hdata[_h]); \
} \
else \
{ \
- fprintf (file, format, _h, (c_type) _typed_data[_h]); \
+ fprintf (file, fmt, _h, (c_type) _hdata[_h]); \
} \
\
if (is_complex && hstride == 1) \
{ \
- fprintf (file, complex_fmt_string, (c_type) _typed_data[_h+1]); \
+ fprintf (file, format[2], (c_type) _hdata[_h+1]); \
} \
fputc ('\n', file); \
} \
@@ -79,16 +76,14 @@ static void OpenFile (const cGH *GH,
const char *fullname,
const char *alias,
const cGroup *gdata,
- const int *Do_it,
+ const int *do_dir,
const CCTK_REAL *coord_lower,
int num_files,
FILE *file[]);
static void WriteData (int vtype,
const char *header,
- const char *data_fmt_int,
- const char *data_fmt_real,
- int hsize,
- int hstride,
+ char format[3][30],
+ int hsize, int hstride,
void *const *const hdata,
FILE *const file[]);
@@ -104,9 +99,11 @@ static void WriteData (int vtype,
It writes to ASCII files suitable for gnuplot and xgraph.
A header telling the physical time prefixes the output data.
@enddesc
- @calls IOUtil_RestartFromRecovery
- IOUtil_AdvertiseFile
- Hyperslab_GetHyperslab
+ @calls Hyperslab_DefineGlobalMappingByIndex
+ Hyperslab_FreeMapping
+ Hyperslab_GetList
+ OpenFile
+ WriteData
@var GH
@vdesc Pointer to CCTK GH
@@ -132,24 +129,25 @@ static void WriteData (int vtype,
@@*/
int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
{
- asciiioGH *myGH; /* IOASCII extension handle */
- int Do_it[4]; /* flags indicating actual work */
- int coord_index[3]; /* x,y,z coordinate variable indices */
- int myproc; /* identify processor */
- int i, dir; /* Loopers */
- int groupindex; /* variable's group index */
- int have_coords; /* boolean for existance of coordinates */
- char coord_system[20]; /* name of the coordinate system */
- cGroup group_static_data; /* variable's group static data */
- cGroupDynamicData group_dynamic_data;/* variable's group dynamic data */
- char *fullname; /* variable's full name */
- char header[30]; /* header string preceding a dataset */
- char time_fmt_string[30]; /* time format string */
- char data_fmt_string_int[30]; /* data format string for int types */
- char data_fmt_string_real[30]; /* data format string for float types */
- FILE *file[8]; /* fds for x,y,z,d output (also COMPLEX)*/
- CCTK_REAL coord_lower[3], offset;
- int hstride, hsize, num_files;
+ asciiioGH *myGH;
+ int do_dir[4], coord_index[3];
+ int i, dir, myproc, groupindex, have_coords;
+#if 0
+ int lower, upper;
+#endif
+ int hstride, num_files, num_requested_hslabs, num_returned_hslabs;
+ int *extent_int;
+ cGroup gdata;
+ char *fullname;
+ char coord_system[20], header[30], buffer[30];
+ char format[3][30];
+ FILE *file[8];
+ CCTK_REAL offset;
+ CCTK_REAL coord_lower[3];
+ CCTK_INT *origin, *direction, *extent;
+ CCTK_INT mapping, hsize;
+ CCTK_INT vindices[2];
+ void *hdata[2];
DECLARE_CCTK_PARAMETERS
@@ -178,18 +176,15 @@ int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
/* get the variable's group information */
- CCTK_GroupData (groupindex, &group_static_data);
- CCTK_GroupDynamicData (GH, groupindex, &group_dynamic_data);
+ CCTK_GroupData (groupindex, &gdata);
/* see what slices should be output */
- Do_it[0] = out1D_x && group_static_data.dim >= 1;
- Do_it[1] = out1D_y && group_static_data.dim >= 2;
- Do_it[2] = out1D_z && group_static_data.dim >= 3;
+ do_dir[0] = out1D_x && gdata.dim >= 1;
+ do_dir[1] = out1D_y && gdata.dim >= 2;
+ do_dir[2] = out1D_z && gdata.dim >= 3;
/* diagonal slice is done only if variable is non-staggered and 3D */
- Do_it[3] = out1D_d &&
- group_static_data.dim == 3 &&
- group_static_data.stagtype == 0;
- if (out1D_d && ! Do_it[3] && myGH->out1D_last[vindex] < 0)
+ do_dir[3] = out1D_d && gdata.dim == 3 && gdata.stagtype == 0;
+ if (out1D_d && ! do_dir[3] && myGH->out1D_last[vindex] < 0)
{
CCTK_VWarn (3, __LINE__, __FILE__, CCTK_THORNSTRING,
"IOASCII_Write1D: No IOASCII_1D diagonal output for '%s' "
@@ -198,7 +193,7 @@ int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
}
/* return if nothing to do */
- if (! (Do_it[0] || Do_it[1] || Do_it[2] || Do_it[3]))
+ if (! (do_dir[0] || do_dir[1] || do_dir[2] || do_dir[3]))
{
free (fullname);
return (0);
@@ -206,12 +201,12 @@ int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
/* get the coordinate indices for CCTK_GF variables
(CCTK_ARRAY variables never have coordinates associated) */
- have_coords = group_static_data.grouptype == CCTK_GF;
+ have_coords = gdata.grouptype == CCTK_GF;
if (have_coords)
{
/* FIXME: this assumes a cartesian coordinate system */
- sprintf (coord_system, "cart%dd", group_static_data.dim);
- for (i = 0; i < group_static_data.dim && i < 3; i++)
+ sprintf (coord_system, "cart%dd", gdata.dim);
+ for (i = 0; i < gdata.dim && i < 3; i++)
{
CCTK_CoordRange (GH, &coord_lower[i], &offset, i + 1, NULL, coord_system);
coord_index[i] = CCTK_CoordIndex (i + 1, NULL, coord_system);
@@ -247,187 +242,201 @@ int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
/* set header format string */
if (CCTK_Equals (out1D_style, "xgraph"))
{
- sprintf (time_fmt_string, "\n\n\"Time = %%%s\n", out_format);
+ sprintf (buffer, "\n\n\"Time = %%%s\n", out_format);
}
else
{
- sprintf (time_fmt_string, "\n#Time = %%%s\n", out_format);
+ sprintf (buffer, "\n#Time = %%%s\n", out_format);
}
- sprintf (header, time_fmt_string, GH->cctk_time);
+ sprintf (header, buffer, (double) GH->cctk_time);
/* check whether to include physical time as separate column in the output */
i = 0;
if (CCTK_Equals (out1D_style, "gnuplot f(t,x)"))
{
- sprintf (time_fmt_string, "%%%s\t\t", out_format);
- sprintf (data_fmt_string_int, time_fmt_string, (double) GH->cctk_time);
- sprintf (data_fmt_string_real, time_fmt_string, (double) GH->cctk_time);
- i = strlen (data_fmt_string_int);
+ sprintf (buffer, "%%%s\t\t", out_format);
+ sprintf (format[0], buffer, (double) GH->cctk_time);
+ sprintf (format[1], buffer, (double) GH->cctk_time);
+ i = strlen (format[0]);
}
if (have_coords)
{
- sprintf (data_fmt_string_int + i, "%%%s\t\t%%d", out_format);
- sprintf (data_fmt_string_real + i, "%%%s\t\t%%%s", out_format, out_format);
+ sprintf (format[0] + i, "%%%s\t\t%%d", out_format);
+ sprintf (format[1] + i, "%%%s\t\t%%%s", out_format, out_format);
}
else
{
- sprintf (data_fmt_string_int + i, "%%d\t\t%%d");
- sprintf (data_fmt_string_real + i, "%%d\t\t%%%s", out_format);
+ sprintf (format[0] + i, "%%d\t\t%%d");
+ sprintf (format[1] + i, "%%d\t\t%%%s", out_format);
}
+ sprintf (format[2], "\t\t%%%s", out_format);
/* get the stride into the data and the (maximum) number of files to write */
- hstride = group_static_data.vartype == CCTK_VARIABLE_COMPLEX &&
+ hstride = gdata.vartype == CCTK_VARIABLE_COMPLEX &&
CCTK_Equals (out1D_style, "xgraph") ? 2 : 1;
num_files = hstride * 4;
- /* Processor 0 opens the files with the appropriate name */
+ /* processor 0 opens the files with the appropriate name */
myproc = CCTK_MyProc (GH);
if (myproc == 0)
{
- OpenFile (GH, fullname, alias, &group_static_data, Do_it,
+ OpenFile (GH, fullname, alias, &gdata, do_dir,
have_coords ? coord_lower : NULL, num_files, file);
}
- /* OK so actually do the I/O in each direction */
- for (dir = 0; dir < 4; dir++)
- {
- int length = -1;
- int gsh[3];
- const int downsample = 1;
- const int *origin;
- const int zero_point[3] = {0, 0, 0};
- int directions[3];
- void *hdata[2];
+ origin = (CCTK_INT *) calloc (3*gdata.dim, sizeof (CCTK_INT));
+ direction = origin + 1*gdata.dim;
+ extent = origin + 2*gdata.dim;
+ extent_int = (int *) malloc (gdata.dim * sizeof (int));
+ CCTK_GroupgshVI (GH, gdata.dim, extent_int, vindex);
+ /* now do the actual I/O looping over all directions */
+ for (dir = 0; dir < 4; dir++)
+ {
/* skip empty slices */
- if (! Do_it[dir])
+ if (! do_dir[dir])
{
continue;
}
- /* need to pass the extent for diagonals */
- if (dir < 3)
+ /* get the number of hyperslabs to extract
+ (ie. whether to get a coordinate hyperslab too or not) */
+ num_requested_hslabs = have_coords && dir < 3 ? 2 : 1;
+
+ /* set the direction vector */
+ for (i = 0; i < gdata.dim; i++)
{
- length = -1;
+ direction[i] = (dir == i || dir == 3) ? 1 : 0;
}
- else
+
+ /* set the extent vector */
+ for (i = 0; i < gdata.dim; i++)
{
- CCTK_GroupgshVI (GH, 3, gsh, vindex);
- length = group_dynamic_data.gsh[0];
- if (length > group_dynamic_data.gsh[1])
- {
- length = group_dynamic_data.gsh[1];
- }
- if (length > group_dynamic_data.gsh[2])
- {
- length = group_dynamic_data.gsh[2];
- }
+ extent[i] = extent_int[i];
}
- if (group_static_data.grouptype == CCTK_GF)
+ /* set the origin of the line */
+ if (gdata.grouptype == CCTK_GF && dir < 3)
{
- /* for GFs: get the coordinate's 1D data (in xyz direction only) */
- if (dir < 3)
+ for (i = 0; i < gdata.dim; i++)
{
- /* set the origin of the line */
- origin = myGH->spxyz[group_static_data.dim-1][dir];
-
- /* set the direction vector for the 1D line */
- memset (directions, 0, sizeof (directions));
- directions[dir] = 1;
-
- if (have_coords)
- {
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[dir], 0, 1,
- origin, directions, &length, &downsample,
- &hdata[1], &hsize) < 0)
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "IOASCII_Write1D: Failed to extract hyperslab for"
- "%c-coordinate", 'x' + dir);
- }
- }
- else
- {
- hdata[1] = NULL;
- }
+ origin[i] = myGH->spxyz[gdata.dim-1][dir][i];
+ extent[i] -= origin[i];
+ }
+#if 0
+ if (CCTK_CoordRangePhysIndex (GH, &lower, &upper, dir + 1, NULL,
+ coord_system) >= 0)
+ {
+fprintf (stderr, "CCTK_CoordRangePhysIndex() resets origin/extent in dir %d from %d/%d to ", dir, origin[dir], extent[dir]);
+ origin[dir] = lower; extent[dir] = upper - lower + 1;
+fprintf (stderr, "%d/%d\n", origin[dir], extent[dir]);
}
else
{
- /* set the origin of the line */
- origin = zero_point;
-
- /* set the direction vector for the diagonal 1D line */
- for (i = 0; i < 3; i++)
- {
- directions[i] = 1;
- }
-
- /* coordinates are calculated by output processor */
- hdata[1] = NULL;
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write1D: failed to get physical coordinate ranges "
+ "for variable '%s'", fullname);
}
+#endif
}
- else
+ else /* origin for CCTK_ARRAYS and diagonals is always (0, 0, 0) */
{
- /* set the origin of the line */
- /* FIXME: Should we define some slice center for arrays too ? */
- origin = zero_point;
+ memset (origin, 0, gdata.dim * sizeof (CCTK_INT));
- /* set the direction vector for the 1D line */
- for (i = 0; i < 3; i++)
+ /* for diagonals: get the extent as the minimum of points
+ in all direction */
+ if (dir == 3)
{
- directions[i] = (dir == i || dir == 3) ? 1 : 0;
+ if (extent[0] > extent[1])
+ {
+ extent[0] = extent[1];
+ }
+ if (extent[0] > extent[2])
+ {
+ extent[0] = extent[2];
+ }
}
-
- /* no coordinates are needed for arrays */
- hdata[1] = NULL;
}
- /* get the variable's 1D data */
- if (Hyperslab_GetHyperslab (GH, 0, vindex, 0, 1, origin,
- directions, &length, &downsample,
- &hdata[0], &hsize) < 0)
+ mapping = Hyperslab_DefineGlobalMappingByIndex (GH, vindex, 1,
+ direction,
+ origin,
+ extent,
+ NULL, /* downsample */
+ -1, /* table handle */
+ NULL /* conversion fn */,
+ &hsize);
+ if (mapping < 0)
{
CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "IOASCII_Write1D: Failed to extract hyperslab for "
+ "IOASCII_Write1D: Failed to define hyperslab mapping for "
"variable '%s'", fullname);
- if (hdata[1])
- {
- free (hdata[1]);
- }
continue;
}
+ if (hsize <= 0)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write1D: selected hyperslab has zero size for "
+ "variable '%s' direction %d", fullname, dir);
+ Hyperslab_FreeMapping (mapping);
+ continue;
+ }
+
+ if (myproc == 0)
+ {
+ /* allocate hyperslab buffers */
+ hdata[0] = malloc (hsize * CCTK_VarTypeSize (gdata.vartype));
+ hdata[1] = have_coords ? malloc (hsize * sizeof (CCTK_REAL)) : NULL;
+ }
+
+ /* get the hyperslabs */
+ vindices[0] = vindex;
+ vindices[1] = coord_index[dir];
+ num_returned_hslabs = Hyperslab_GetList (GH, mapping, num_requested_hslabs,
+ NULL, vindices, NULL, NULL, hdata,
+ NULL);
+
+ /* release the mapping structure */
+ Hyperslab_FreeMapping (mapping);
- /* And write it out on processor 0 */
+ /* And dump the data to file */
if (myproc == 0 && file[dir] != NULL)
{
- if (have_coords)
+ if (num_returned_hslabs != num_requested_hslabs)
{
- if (dir < 3)
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write1D: Failed to extract hyperslab for "
+ "variable '%s'", fullname);
+ }
+ else
+ {
+ if (have_coords)
{
- /* get the staggering offset for the xyz coordinates */
- offset = 0.5 * GH->cctk_delta_space[dir] *
- CCTK_StaggerDirIndex (dir, group_static_data.stagtype);
- for (i = 0; i < hsize; i++)
+ if (dir < 3)
{
- ((CCTK_REAL *) hdata[1])[i] += offset;
+ /* get the staggering offset for the xyz coordinates */
+ offset = 0.5 * GH->cctk_delta_space[dir] *
+ CCTK_StaggerDirIndex (dir, gdata.stagtype);
+ for (i = 0; i < hsize; i++)
+ {
+ ((CCTK_REAL *) hdata[1])[i] += offset;
+ }
}
- }
- else
- {
- /* calculate the diagonal coordinates */
- offset = GH->cctk_delta_space[0] * sqrt (3);
- hdata[1] = malloc (hsize * sizeof (CCTK_REAL));
- for (i = 0; i < hsize; i++)
+ else
{
- ((CCTK_REAL *) hdata[1])[i] = coord_lower[0]*sqrt (3) + i*offset;
+ /* calculate the diagonal coordinates */
+ offset = GH->cctk_delta_space[0] * sqrt (3);
+ for (i = 0; i < hsize; i++)
+ {
+ ((CCTK_REAL *) hdata[1])[i] = coord_lower[0]*sqrt (3) + i*offset;
+ }
}
}
- }
- WriteData (group_static_data.vartype, header, data_fmt_string_int,
- data_fmt_string_real, hsize, hstride, hdata, file + dir);
+ WriteData (gdata.vartype, header, format, hsize, hstride, hdata,
+ file + dir);
+ }
/* close the output file(s) */
fclose (file[dir]);
@@ -435,51 +444,66 @@ int IOASCII_Write1D (const cGH *GH, int vindex, const char *alias)
{
fclose (file[dir + 4]);
}
+ }
- /* clean up */
+ /* clean up */
+ if (myproc == 0)
+ {
free (hdata[0]);
if (hdata[1])
{
free (hdata[1]);
}
}
-
} /* end of loop through all directions */
/* free allocated resources */
+ free (origin);
free (fullname);
+ free (extent_int);
return (0);
}
+/********************************************************************
+ ******************** Internal Routines ************************
+ ********************************************************************/
+/*@@
+ @routine OpenFile
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Opens a set of ASCII files for a given alias name.
+ If this is the first time through, it will create the files,
+ write some header information, and advertise them to IOUtil.
+ @enddesc
+ @@*/
static void OpenFile (const cGH *GH,
const char *fullname,
const char *alias,
const cGroup *gdata,
- const int *Do_it,
+ const int *do_dir,
const CCTK_REAL *coord_lower,
int num_files,
FILE *file[])
{
- int i, dir;
+ int i, dir, upper, lower, first_time_through;
asciiioGH *myGH;
- struct stat fileinfo;
- const char *openmode;
- static char *extensions[] = {"xl", "yl", "zl", "dl"};
- char *filename, *type_extension, buffer[128];
+ const ioGH *ioUtilGH;
+ char comment_char;
+ char *filename, *type_extension;
+ const char *file_extension;
+ char slicename[20], buffer[128];
+ char ylabel1_fmt_string[13], ylabel2_fmt_string[13];
ioAdvertisedFileDesc advertised_file;
- char slicename[20]; /* name of current output slice */
- int upper, lower;
- char comment_char; /* character starting a comment */
- const char *file_extension; /* filename extension */
- char ylabel1_fmt_string[13]; /* y-label format string */
- char ylabel2_fmt_string[13]; /* y-label format string */
+ const char *extensions[] = {"xl", "yl", "zl", "dl"};
DECLARE_CCTK_PARAMETERS
- /* get the handle for IOASCII extensions */
+ /* get handles for IOUtil and IOASCII extensions */
myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
+ ioUtilGH = (const ioGH *) CCTK_GHExtension (GH, "IO");
/* set comment character and file extension */
if (CCTK_Equals (out1D_style, "xgraph"))
@@ -506,7 +530,7 @@ static void OpenFile (const cGH *GH,
dir = i % 4;
/* skip empty slices */
- if (! Do_it[dir])
+ if (! do_dir[dir])
{
continue;
}
@@ -590,34 +614,17 @@ static void OpenFile (const cGH *GH,
}
}
- /* see if output file was already created */
- if (GetNamedData (myGH->filenameList1D, filename) == NULL)
- {
- /* if restart from recovery, existing files are opened in append mode */
- if (IOUtil_RestartFromRecovery (GH))
- {
- openmode = stat (filename, &fileinfo) == 0 ? "a" : "w";
- }
- else
- {
- openmode = "w";
- }
-
- /* just store a non-NULL pointer in database */
- StoreNamedData (&myGH->filenameList1D, filename, (void *) 1);
- }
- else
- {
- openmode = "a";
- }
-
- if (! (file[i] = fopen (filename, openmode)))
+ /* create the output file the first time through
+ If restart from recovery, existing files are opened in append mode. */
+ first_time_through = GetNamedData (myGH->filenameList1D, filename) == NULL;
+ file[i] = fopen (filename,
+ ioUtilGH->recovered || ! first_time_through ? "a" : "w");
+ if (! file[i])
{
CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "IOASCII_Write1D: Cannot open 1D output file '%s'",
- filename);
+ "IOASCII_Write1D: Cannot open 1D output file '%s'", filename);
}
- else if (*openmode == 'w')
+ else if (first_time_through)
{
/* advertise new files for downloading and add file info */
/* FIXME: this can go after the old filename scheme has gone */
@@ -689,86 +696,89 @@ static void OpenFile (const cGH *GH,
}
}
}
+
+ StoreNamedData (&myGH->filenameList1D, filename, file[i]);
}
}
+
free (filename);
}
+/*@@
+ @routine WriteData
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Writes the given hyperslabs into the appropriate output files.
+ @enddesc
+ @@*/
static void WriteData (int vtype,
const char *header,
- const char *data_fmt_string_int,
- const char *data_fmt_string_real,
- int hsize,
- int hstride,
+ char format[3][30],
+ int hsize, int hstride,
void *const *const hdata,
FILE *const file[])
{
- char complex_fmt_string[30];
- DECLARE_CCTK_PARAMETERS
-
-
- sprintf (complex_fmt_string, "\t\t%%%s", out_format);
-
/* print out header */
fputs (header, file[0]);
if (vtype == CCTK_VARIABLE_CHAR)
{
- WRITE_DATA (0, CCTK_BYTE, int, 0, data_fmt_string_int, file[0]);
+ WRITE_DATA (0, CCTK_BYTE, int, 0, format[0], file[0]);
}
else if (vtype == CCTK_VARIABLE_INT)
{
- WRITE_DATA (0, CCTK_INT, int, 0, data_fmt_string_int, file[0]);
+ WRITE_DATA (0, CCTK_INT, int, 0, format[0], file[0]);
}
else if (vtype == CCTK_VARIABLE_REAL)
{
- WRITE_DATA (0, CCTK_REAL, double, 0, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL, double, 0, format[1], file[0]);
}
else if (vtype == CCTK_VARIABLE_COMPLEX)
{
- WRITE_DATA (0, CCTK_REAL, double, 1, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL, double, 1, format[1], file[0]);
if (hstride == 2)
{
/* print out header */
fputs (header, file[0 + 4]);
- WRITE_DATA (1, CCTK_REAL, double, 1, data_fmt_string_real, file[4]);
+ WRITE_DATA (1, CCTK_REAL, double, 1, format[1], file[4]);
}
}
#ifdef CCTK_INT2
else if (vtype == CCTK_VARIABLE_INT2)
{
- WRITE_DATA (0, CCTK_INT2, int, 0, data_fmt_string_int, file[0]);
+ WRITE_DATA (0, CCTK_INT2, int, 0, format[0], file[0]);
}
#endif
#ifdef CCTK_INT4
else if (vtype == CCTK_VARIABLE_INT4)
{
- WRITE_DATA (0, CCTK_INT4, int, 0, data_fmt_string_int, file[0]);
+ WRITE_DATA (0, CCTK_INT4, int, 0, format[0], file[0]);
}
#endif
#ifdef CCTK_INT8
else if (vtype == CCTK_VARIABLE_INT8)
{
- WRITE_DATA (0, CCTK_INT8, int, 0, data_fmt_string_int, file[0]);
+ WRITE_DATA (0, CCTK_INT8, int, 0, format[0], file[0]);
}
#endif
#ifdef CCTK_REAL4
else if (vtype == CCTK_VARIABLE_REAL4)
{
- WRITE_DATA (0, CCTK_REAL4, double, 0, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL4, double, 0, format[1], file[0]);
}
else if (vtype == CCTK_VARIABLE_COMPLEX8)
{
- WRITE_DATA (0, CCTK_REAL4, double, 1, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL4, double, 1, format[1], file[0]);
if (hstride == 2)
{
/* print out header */
fputs (header, file[0 + 4]);
- WRITE_DATA (1, CCTK_REAL4, double, 1, data_fmt_string_real, file[0 + 4]);
+ WRITE_DATA (1, CCTK_REAL4, double, 1, format[1], file[0 + 4]);
}
}
#endif
@@ -776,16 +786,16 @@ static void WriteData (int vtype,
#ifdef CCTK_REAL8
else if (vtype == CCTK_VARIABLE_REAL8)
{
- WRITE_DATA (0, CCTK_REAL8, double, 0, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL8, double, 0, format[1], file[0]);
}
else if (vtype == CCTK_VARIABLE_COMPLEX16)
{
- WRITE_DATA (0, CCTK_REAL8, double, 1, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL8, double, 1, format[1], file[0]);
if (hstride == 2)
{
/* print out header */
fputs (header, file[0 + 4]);
- WRITE_DATA (1, CCTK_REAL8, double, 1, data_fmt_string_real, file[0 + 4]);
+ WRITE_DATA (1, CCTK_REAL8, double, 1, format[1], file[0 + 4]);
}
}
#endif
@@ -793,16 +803,16 @@ static void WriteData (int vtype,
#ifdef CCTK_REAL16
else if (vtype == CCTK_VARIABLE_REAL16)
{
- WRITE_DATA (0, CCTK_REAL16, double, 0, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL16, double, 0, format[1], file[0]);
}
else if (vtype == CCTK_VARIABLE_COMPLEX32)
{
- WRITE_DATA (0, CCTK_REAL16, double, 1, data_fmt_string_real, file[0]);
+ WRITE_DATA (0, CCTK_REAL16, double, 1, format[1], file[0]);
if (hstride == 2)
{
/* print out header */
fputs (header, file[0 + 4]);
- WRITE_DATA (1, CCTK_REAL16, double, 1, data_fmt_string_real, file[0 + 4]);
+ WRITE_DATA (1, CCTK_REAL16, double, 1, format[1], file[0 + 4]);
}
}
#endif
diff --git a/src/Write2D.c b/src/Write2D.c
index 65fdebb..6442060 100644
--- a/src/Write2D.c
+++ b/src/Write2D.c
@@ -15,71 +15,76 @@
#include "cctk.h"
#include "cctk_Parameters.h"
#include "Hyperslab.h"
+#include "CactusBase/IOUtil/src/ioGH.h"
#include "CactusBase/IOUtil/src/ioutil_AdvertisedFiles.h"
-#include "CactusBase/IOUtil/src/ioutil_CheckpointRecovery.h"
#include "ioASCIIGH.h"
/* the rcs ID and its dummy function to use it */
static const char *rcsid = "$Id$";
CCTK_FILEVERSION(CactusBase_IOASCII_Write2D_c)
-/* enable debug output */
-/*#define IOASCII_DEBUG 1*/
+/********************************************************************
+ ******************** Macro Definitions ************************
+ ********************************************************************/
+/* uncomment this to enable debugging output */
+/* #define DEBUG_IOASCII 1 */
/* macro to output a time slice as typed data */
-#define OUTPUT_TYPED_DATA(coord_i, coord_j, stagger_offset_i,stagger_offset_j,\
- cctk_type, c_type, data, hsize, is_cmplx_type, \
- have_coords, fmt_string, file) \
- { \
- int i, j; \
- const cctk_type *typed_data = (const cctk_type *) (data); \
+/* Macro to output a 2D slice (with coordinates if available) as typed data
+ For readability, the macro definition implicitely uses the following
+ variables (which are defined in the calling routine):
+ hdata, hsize, is_complex, format[2], file */
+#define WRITE_DATA(cctk_type, c_type, fmt) \
+ { \
+ int _i, _j; \
+ const cctk_type *_hdata = (const cctk_type *) hdata[0]; \
+ const CCTK_REAL *_coord[2]; \
+ \
\
\
- /* output coordinates if available otherwise just the indices */ \
- if (have_coords) \
+ _coord[0] = (const CCTK_REAL *) hdata[1]; \
+ _coord[1] = (const CCTK_REAL *) hdata[2]; \
+ for (_j = 0; _j < hsize[1]; _j++) \
+ { \
+ for (_i = 0; _i < hsize[0]; _i++) \
{ \
- for (j = 0; j < hsize[1]; j++) \
+ if (_coord[0]) \
{ \
- for (i = 0; i < hsize[0]; i++) \
- { \
- fprintf (file, fmt_string, \
- (double) (*coord_i++ + stagger_offset_i), \
- (double) (*coord_j++ + stagger_offset_j), \
- (c_type) *typed_data++); \
- if (is_cmplx_type) \
- { \
- fprintf (file, "\t\t"); \
- fprintf (file, out_real_format, (double) *typed_data++); \
- } \
- fprintf (file, "\n"); \
- } \
- fprintf (file, "\n"); \
+ fprintf (file, fmt, (double) *_coord[0]++, \
+ (double) *_coord[1]++, (c_type) *_hdata++); \
} \
- coord_i -= hsize[0] * hsize[1]; \
- coord_j -= hsize[0] * hsize[1]; \
- } \
- else \
- { \
- for (j = 0; j < hsize[1]; j++) \
+ else \
+ { \
+ fprintf (file, fmt, _i, _j, (c_type) *_hdata++); \
+ } \
+ \
+ if (is_complex) \
{ \
- for (i = 0; i < hsize[0]; i++) \
- { \
- fprintf (file, fmt_string, \
- (double) i, \
- (double) j, \
- (c_type) *typed_data++); \
- if (is_cmplx_type) \
- { \
- fprintf (file, "\t\t"); \
- fprintf (file, out_real_format, (double) *typed_data++); \
- } \
- fprintf (file, "\n"); \
- } \
- fprintf (file, "\n"); \
+ fprintf (file, format[2], (c_type) *_hdata++); \
} \
+ fputc ('\n', file); \
} \
- }
+ fputc ('\n', file); \
+ } \
+ }
+
+
+/********************************************************************
+ ******************** Internal Routines ************************
+ ********************************************************************/
+static FILE **OpenFile (const cGH *GH,
+ const char *fullname,
+ const char *alias,
+ int dim,
+ const CCTK_REAL *coord_lower,
+ int maxdir);
+static void WriteData (int vtype,
+ const char *header,
+ char format[3][30],
+ const CCTK_INT hsize[2],
+ void *const *const hdata,
+ FILE *file);
/*@@
@@ -89,9 +94,11 @@ CCTK_FILEVERSION(CactusBase_IOASCII_Write2D_c)
@desc
Writes the 2D slices of a variable into separate ASCII files.
@enddesc
- @calls IOUtil_RestartFromRecovery
- IOUtil_AdvertiseFile
- Hyperslab_GetHyperslab
+ @calls Hyperslab_DefineGlobalMappingByIndex
+ Hyperslab_FreeMapping
+ Hyperslab_GetList
+ OpenFile
+ WriteData
@var GH
@vdesc Pointer to CCTK GH
@@ -120,44 +127,34 @@ CCTK_FILEVERSION(CactusBase_IOASCII_Write2D_c)
@@*/
int IOASCII_Write2D (const cGH *GH, int vindex, const char *alias)
{
- DECLARE_CCTK_PARAMETERS
- int myproc;
asciiioGH *myGH;
- char header_fmt_string[30]; /* header format string */
- char zlabel_fmt_string[30]; /* z-label format string */
- char out_real_format[30]; /* data format string for a real type */
- char time_fmt_string[30]; /* time format string */
- char data_fmt_string_int[30]; /* data format string for int types */
- char data_fmt_string_real[30]; /* data format string for real types */
- int dir, maxdir;
- int groupindex;
- int have_coords;
- cGroup groupinfo;
- FILE **fdset_2D; /* array of output file pointers */
- int coord_index[3]; /* variable indices for xyz coordinates */
- CCTK_REAL coord_lower[3]; /* coordinates' minima */
- char coord_system[20]; /* name of the coordinate system */
- int origin[3]; /* the slice origin */
- CCTK_REAL dummy;
- char *filename;
+ int i, total_hsize, num_requested_hslabs, num_returned_hslabs;
+ int dir, dir_i, dir_j, maxdir, myproc, groupindex, have_coords;
+ cGroup gdata;
+ int coord_index[3];
+ CCTK_REAL coord_lower[3];
+ char coord_system[20];
+ char format[3][30];
+ char header[30], buffer[30];
char *fullname;
- char slicename[20];
- ioAdvertisedFileDesc advertised_file;
- char buffer[128];
- static char *extensions[] = {"xy", "xz", "yz"};
-
+ int extent_int[3];
+ CCTK_INT mapping;
+ CCTK_REAL offset[2];
+ CCTK_INT vindices[3];
+ CCTK_INT origin[3], extent[3], direction[6], hsize[2];
+ void *hdata[3];
+ FILE **fileset;
+ DECLARE_CCTK_PARAMETERS
- /* to make the compiler happy */
- fdset_2D = NULL;
- /* get the variable group information */
+ /* get the variable name and group information */
+ fullname = CCTK_FullName (vindex);
groupindex = CCTK_GroupIndexFromVarI (vindex);
- CCTK_GroupData (groupindex, &groupinfo);
+ CCTK_GroupData (groupindex, &gdata);
/* check if variable has storage assigned */
if (! CCTK_QueryGroupStorageI (GH, groupindex))
{
- fullname = CCTK_FullName (vindex);
CCTK_VWarn (2, __LINE__, __FILE__, CCTK_THORNSTRING,
"No IOASCII 2D output for '%s' (no storage)", fullname);
free (fullname);
@@ -168,34 +165,18 @@ int IOASCII_Write2D (const cGH *GH, int vindex, const char *alias)
myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
/* get the number of slices to output */
- /* in general: maxdir = groupinfo.dim * (groupinfo.dim - 1) / 2; */
- maxdir = groupinfo.dim == 2 ? 1 : 3;
-
- /* set header and data format strings */
- sprintf (header_fmt_string, "\n\n#Time = %%%s\n", out_format);
- sprintf (zlabel_fmt_string, " (%%c = %%%s),", out_format);
- sprintf (out_real_format, "%%%s", out_format);
- dir = 0;
- if (CCTK_Equals (out2D_style, "gnuplot f(t,x,y)"))
- {
- sprintf (time_fmt_string, "%%%s\t\t", out_format);
- sprintf (data_fmt_string_int, time_fmt_string, (double) GH->cctk_time);
- sprintf (data_fmt_string_real, time_fmt_string, (double) GH->cctk_time);
- dir = strlen (data_fmt_string_int);
- }
- sprintf (data_fmt_string_int + dir, "%%%s\t\t%%%s\t\t%%d",
- out_format, out_format);
- sprintf (data_fmt_string_real + dir, "%%%s\t\t%%%s\t\t%%%s",
- out_format, out_format, out_format);
+ /* in general: maxdir = gdata.dim * (gdata.dim - 1) / 2; */
+ maxdir = gdata.dim == 2 ? 1 : 3;
- /* get the coordinate indices if we output a grid function */
- if (groupinfo.grouptype == CCTK_GF)
+ /* get the coordinate indices for CCTK_GF variables
+ (CCTK_ARRAY variables never have coordinates associated) */
+ have_coords = gdata.grouptype == CCTK_GF;
+ if (have_coords)
{
- sprintf (coord_system, "cart%dd", groupinfo.dim);
- have_coords = 1;
- for (dir = 0; dir < groupinfo.dim && dir < 3; dir++)
+ sprintf (coord_system, "cart%dd", gdata.dim);
+ for (dir = 0; dir < gdata.dim && dir < 3; dir++)
{
- CCTK_CoordRange (GH, &coord_lower[dir], &dummy, dir+1, NULL,coord_system);
+ CCTK_CoordRange (GH, &coord_lower[dir], offset, dir+1, NULL,coord_system);
coord_index[dir] = CCTK_CoordIndex (dir + 1, NULL, coord_system);
have_coords &= coord_index[dir] >= 0;
}
@@ -207,173 +188,49 @@ int IOASCII_Write2D (const cGH *GH, int vindex, const char *alias)
coord_system);
}
}
+ num_requested_hslabs = have_coords ? 3 : 1;
+
+ /* set header and data format strings */
+ sprintf (buffer, "\n\n#Time = %%%s\n", out_format);
+ sprintf (header, buffer, GH->cctk_time);
+ dir = 0;
+ if (CCTK_Equals (out2D_style, "gnuplot f(t,x,y)"))
+ {
+ sprintf (buffer, "%%%s\t\t", out_format);
+ sprintf (format[0], buffer, (double) GH->cctk_time);
+ sprintf (format[1], buffer, (double) GH->cctk_time);
+ dir = strlen (format[0]);
+ }
+ if (have_coords)
+ {
+ sprintf (format[0] + dir, "%%%s\t\t%%%s\t\t%%d",
+ out_format, out_format);
+ sprintf (format[1] + dir, "%%%s\t\t%%%s\t\t%%%s",
+ out_format, out_format, out_format);
+ }
else
{
- /* CCTK_ARRAY variables never have coordinates associated */
- have_coords = 0;
+ sprintf (format[0] + dir, "%%d\t\t%%d\t\t%%d");
+ sprintf (format[1] + dir, "%%d\t\t%%d\t\t%%%s", out_format);
}
- /* What processor are we on? */
+ /* processor 0 opens the files on the first trip through */
myproc = CCTK_MyProc (GH);
-
- /* Open the files on the first trip through if we are proc. 0 */
if (myproc == 0)
{
-
- /* see if output file for this alias name was already created */
- fdset_2D = (FILE **) GetNamedData (myGH->fileList_2D, alias);
- if (fdset_2D == NULL)
- {
- fdset_2D = (FILE **) malloc (3 * sizeof (FILE *));
- filename = (char *) malloc (strlen (myGH->outdir2D) + strlen (alias) +
- sizeof (slicename) + 20);
-
- /* get the variable's full name */
- fullname = CCTK_FullName (vindex);
-
- /* Open/Create files */
- for (dir = 0; dir < maxdir; dir++)
- {
- /* FIXME: this can go when we permanently switch the the
- new filename scheme */
- if (new_filename_scheme)
- {
- if (groupinfo.dim == 2)
- {
- strcpy (slicename, "2D");
- }
- else
- {
- /* give the slice origin as range [1 .. n] */
- sprintf (slicename, "%s_[%d]", extensions[dir],
- myGH->sp2xyz[groupinfo.dim - 1][dir]);
- }
-
- /* skip pathname if output goes into current directory */
- if (strcmp (myGH->outdir2D, "."))
- {
- sprintf (filename, "%s/%s_%s.asc", myGH->outdir2D, alias,slicename);
- }
- else
- {
- sprintf (filename, "%s_%s.asc", alias, slicename);
- }
- }
- else
- {
- /* skip pathname if output goes into current directory */
- if (strcmp (myGH->outdir2D, "."))
- {
- if (groupinfo.dim == 2)
- {
- sprintf (filename, "%s/%s_2D.gnuplot", myGH->outdir2D, alias);
- }
- else
- {
- sprintf (filename, "%s/%s_2d_%s.gnuplot", myGH->outdir2D, alias,
- extensions[dir]);
- }
- }
- else
- {
- if (groupinfo.dim == 2)
- {
- sprintf (filename, "%s_2D.gnuplot", alias);
- }
- else
- {
- sprintf (filename, "%s_2d_%s.gnuplot", alias, extensions[dir]);
- }
- }
- }
-
- /* if restart from recovery, try to open an existing file ... */
- fdset_2D[dir] = NULL;
- if (IOUtil_RestartFromRecovery (GH))
- {
- fdset_2D[dir] = fopen (filename, "a");
- }
-
- /* otherwise or if that failed, create a new one */
- if (! fdset_2D[dir])
- {
- fdset_2D[dir] = fopen (filename, "w");
- }
- if (! fdset_2D[dir])
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Cannot open 2D output file '%s'", filename);
- return (-2);
- }
-
- /* advertise the file for downloading and write file info */
- /* FIXME: this can go when we permanently switch the the
- new filename scheme */
- advertised_file.slice = new_filename_scheme ?
- slicename : extensions[dir];
- advertised_file.thorn = CCTK_THORNSTRING;
- advertised_file.varname = fullname;
- advertised_file.description = "Two-dimensional slice plots";
- advertised_file.mimetype = "application/gnuplot";
-
- IOUtil_AdvertiseFile (GH, filename, &advertised_file);
-
- if (CCTK_Equals (out_fileinfo, "parameter filename") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- buffer[0] = 0;
- CCTK_ParameterFilename (sizeof (buffer), buffer);
- fprintf (fdset_2D[dir], "#Parameter file %s\n", buffer);
- }
- if (CCTK_Equals (out_fileinfo, "creation date") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- buffer[0] = 0;
- Util_CurrentDate (sizeof (buffer), buffer);
- fprintf (fdset_2D[dir], "#Created %s ", buffer);
- Util_CurrentTime (sizeof (buffer), buffer);
- fprintf (fdset_2D[dir], "%s\n", buffer);
- }
- if (CCTK_Equals (out_fileinfo, "axis labels") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- fprintf (fdset_2D[dir], "#x-label %c\n", extensions[dir][0]);
- fprintf (fdset_2D[dir], "#y-label %c\n", extensions[dir][1]);
- fprintf (fdset_2D[dir], "#z-label %s", advertised_file.varname);
- if (groupinfo.dim != 2)
- {
- if (have_coords)
- {
- fprintf (fdset_2D[dir], zlabel_fmt_string, 'x' + (maxdir-dir-1),
- coord_lower[maxdir-dir-1] +
- GH->cctk_delta_space[maxdir-dir-1] *
- myGH->sp2xyz[groupinfo.dim-1][dir]);
- }
- fprintf (fdset_2D[dir], " (%ci = %d)",
- 'x' + (maxdir-dir-1), myGH->sp2xyz[groupinfo.dim-1][dir]);
- }
- fputc ('\n', fdset_2D[dir]);
- }
- }
-
- /* store file desriptors in database */
- StoreNamedData (&myGH->fileList_2D, alias, fdset_2D);
-
- free (filename);
- free (fullname);
- }
+ fileset = OpenFile (GH, fullname, alias, gdata.dim,
+ have_coords ? coord_lower : NULL, maxdir);
}
+ else
+ {
+ fileset = NULL;
+ }
+
+ CCTK_GroupgshVI (GH, 3, extent_int, vindex);
+ /* now do the actual I/O looping over all directions */
for (dir = 0; dir < maxdir; dir++)
{
- int dir_i, dir_j;
- int directions[3];
- const int lengths[2] = {-1, -1};
- const int downsamples[2] = {1, 1};
- int hsize[2];
- CCTK_REAL *coord_data_i, *coord_data_j;
- void *data;
-
/* get the directions to span the hyperslab */
if (dir == 0)
{
@@ -388,179 +245,372 @@ int IOASCII_Write2D (const cGH *GH, int vindex, const char *alias)
dir_i = 1; dir_j = 2; /* yz */
}
+ /* set the extent vector */
+ for (i = 0; i < 3; i++)
+ {
+ extent[i] = extent_int[i];
+ }
+
/* set the origin using the slice center from IOUtil */
- memset (origin, 0, GH->cctk_dim * sizeof (int));
- origin[maxdir-dir-1] = myGH->sp2xyz[groupinfo.dim - 1][dir];
+ memset (origin, 0, sizeof (origin));
+ if (have_coords)
+ {
+ origin[maxdir-dir-1] = myGH->sp2xyz[gdata.dim - 1][dir];
+ }
- /* set the directions vector */
- memset (directions, 0, sizeof (directions));
- directions[maxdir-dir-1] = 1;
+ /* set the direction vector */
+ memset (direction, 0, sizeof (direction));
+ direction[dir_i] = direction[gdata.dim + dir_j] = 1;
+
+ mapping = Hyperslab_DefineGlobalMappingByIndex (GH, vindex, 2,
+ direction,
+ origin,
+ extent,
+ NULL, /* downsample */
+ -1, /* table handle */
+ NULL /* conversion fn */,
+ hsize);
+ if (mapping < 0)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write2D: Failed to define hyperslab mapping for "
+ "variable '%s'", fullname);
+ continue;
+ }
+ total_hsize = hsize[0] * hsize[1];
+ if (total_hsize <= 0)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write2D: selected hyperslab has zero size for "
+ "variable '%s' direction %d", fullname, dir);
+ Hyperslab_FreeMapping (mapping);
+ continue;
+ }
- /* get the coordinates for grid function output */
- if (have_coords)
+ if (myproc == 0)
{
- /* get the i-coordinate slice */
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[dir_i], 0, 2,
- origin, directions, lengths, downsamples,
- (void **) &coord_data_i, hsize) < 0)
+ /* allocate hyperslab buffers */
+ hdata[0] = malloc (total_hsize * CCTK_VarTypeSize (gdata.vartype));
+ hdata[1] = have_coords ? malloc (2 * total_hsize * sizeof (CCTK_REAL)) :
+ NULL;
+ hdata[2] = (CCTK_REAL *) hdata[1] + total_hsize;
+ }
+
+ /* get the hyperslabs */
+ vindices[0] = vindex;
+ vindices[1] = coord_index[dir_i];
+ vindices[2] = coord_index[dir_j];
+ num_returned_hslabs = Hyperslab_GetList (GH, mapping, num_requested_hslabs,
+ NULL, vindices, NULL, NULL, hdata,
+ NULL);
+
+ /* release the mapping structure */
+ Hyperslab_FreeMapping (mapping);
+
+ /* And dump the data to file */
+ if (myproc == 0 && fileset)
+ {
+ if (num_returned_hslabs == num_requested_hslabs)
+ {
+ if (have_coords)
+ {
+ /* get the staggering offset for the coordinates */
+ offset[0] = 0.5 * GH->cctk_delta_space[dir_i] *
+ CCTK_StaggerDirIndex (dir_i, gdata.stagtype);
+ offset[1] = 0.5 * GH->cctk_delta_space[dir_j] *
+ CCTK_StaggerDirIndex (dir_j, gdata.stagtype);
+ for (i = 0; i < total_hsize; i++)
+ {
+ ((CCTK_REAL *) hdata[1])[i] += offset[0];
+ ((CCTK_REAL *) hdata[2])[i] += offset[1];
+ }
+ }
+
+ WriteData (gdata.vartype, header, format, hsize, hdata, fileset[dir]);
+ }
+ else
{
CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 2D hyperslab for %c-coordinate",
- 'x' + dir_i);
- return (-3);
+ "IOASCII_Write2D: Failed to extract hyperslab for "
+ "variable '%s'", fullname);
}
- /* get the j-coordinate slice */
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[dir_j], 0, 2,
- origin, directions, lengths, downsamples,
- (void **) &coord_data_j, hsize) < 0)
+ /* clean up */
+ free (hdata[0]);
+ if (hdata[1])
{
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 2D hyperslab for %c-coordinate",
- 'x' + dir_j);
- free (coord_data_i);
- return (-3);
+ free (hdata[1]);
+ }
+
+ } /* end of outputting the data by processor 0 */
+
+ } /* end of looping through xyz directions */
+
+ free (fullname);
+
+ return (0);
+}
+
+
+/********************************************************************
+ ******************** Internal Routines ************************
+ ********************************************************************/
+/*@@
+ @routine OpenFile
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Opens a set of ASCII files for a given alias name.
+ If this is the first time through, it will create the files,
+ write some header information, and advertise them to IOUtil.
+ @enddesc
+
+ @returntype FILE **
+ @returndesc
+ the set of open file descriptors,<BR>
+ or NULL if a file couldn't be created
+ @endreturndesc
+ @@*/
+static FILE **OpenFile (const cGH *GH,
+ const char *fullname,
+ const char *alias,
+ int dim,
+ const CCTK_REAL *coord_lower,
+ int maxdir)
+{
+ int dir;
+ FILE **fileset;
+ char *filename;
+ asciiioGH *myGH;
+ const ioGH *ioUtilGH;
+ ioAdvertisedFileDesc advertised_file;
+ char slicename[30], zlabel_fmt_string[30], buffer[128];
+ const char *extensions[] = {"xy", "xz", "yz"};
+ DECLARE_CCTK_PARAMETERS
+
+
+ /* get handles for IOUtil and IOASCII extensions */
+ myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
+ ioUtilGH = (const ioGH *) CCTK_GHExtension (GH, "IO");
+
+ /* see if we are the first time through */
+ fileset = (FILE **) GetNamedData (myGH->fileList_2D, alias);
+ if (fileset)
+ {
+ return (fileset);
+ }
+
+ sprintf (zlabel_fmt_string, " (%%c = %%%s),", out_format);
+ fileset = (FILE **) malloc (3 * sizeof (FILE *));
+ filename = (char *) malloc (strlen (myGH->outdir2D) + strlen (alias) +
+ sizeof (slicename) + 20);
+
+ /* open/create files for each slice */
+ for (dir = 0; dir < maxdir; dir++)
+ {
+ if (new_filename_scheme)
+ {
+ if (dim == 2)
+ {
+ strcpy (slicename, "2D");
+ }
+ else
+ {
+ /* give the slice origin as range [1 .. n] */
+ sprintf (slicename, "%s_[%d]", extensions[dir],
+ myGH->sp2xyz[dim - 1][dir]);
+ }
+
+ /* skip pathname if output goes into current directory */
+ if (strcmp (myGH->outdir2D, "."))
+ {
+ sprintf (filename, "%s/%s_%s.asc", myGH->outdir2D, alias, slicename);
+ }
+ else
+ {
+ sprintf (filename, "%s_%s.asc", alias, slicename);
}
}
else
{
- /* grid arrays don't have coordinates assigned */
- coord_data_i = NULL;
- coord_data_j = NULL;
+ /* skip pathname if output goes into current directory */
+ if (strcmp (myGH->outdir2D, "."))
+ {
+ if (dim == 2)
+ {
+ sprintf (filename, "%s/%s_2D.gnuplot", myGH->outdir2D, alias);
+ }
+ else
+ {
+ sprintf (filename, "%s/%s_2d_%s.gnuplot", myGH->outdir2D, alias,
+ extensions[dir]);
+ }
+ }
+ else
+ {
+ if (dim == 2)
+ {
+ sprintf (filename, "%s_2D.gnuplot", alias);
+ }
+ else
+ {
+ sprintf (filename, "%s_2d_%s.gnuplot", alias, extensions[dir]);
+ }
+ }
}
- /* get the variable slice */
- if (Hyperslab_GetHyperslab (GH, 0, vindex, 0, 2, origin, directions,
- lengths, downsamples, &data, hsize) < 0)
+ /* if restart from recovery, try to open an existing file ... */
+ fileset[dir] = fopen (filename, ioUtilGH->recovered ? "a" : "w");
+ if (! fileset[dir])
{
- fullname = CCTK_FullName (vindex);
CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 2D hyperslab for variable '%s'", fullname);
- free (fullname);
- if (coord_data_i)
- {
- free (coord_data_i);
- }
- if (coord_data_j)
+ "Cannot open 2D output file '%s'", filename);
+ free (fileset);
+ free (filename);
+ return (NULL);
+ }
+
+ /* advertise the file for downloading and write file info */
+ advertised_file.slice = new_filename_scheme ? slicename : extensions[dir];
+ advertised_file.thorn = CCTK_THORNSTRING;
+ advertised_file.varname = fullname;
+ advertised_file.description = "Two-dimensional slice plots";
+ advertised_file.mimetype = "application/gnuplot";
+
+ IOUtil_AdvertiseFile (GH, filename, &advertised_file);
+
+ if (CCTK_Equals (out_fileinfo, "parameter filename") ||
+ CCTK_Equals (out_fileinfo, "all"))
+ {
+ buffer[0] = 0;
+ CCTK_ParameterFilename (sizeof (buffer), buffer);
+ fprintf (fileset[dir], "#Parameter file %s\n", buffer);
+ }
+ if (CCTK_Equals (out_fileinfo, "creation date") ||
+ CCTK_Equals (out_fileinfo, "all"))
+ {
+ buffer[0] = 0;
+ Util_CurrentDate (sizeof (buffer), buffer);
+ fprintf (fileset[dir], "#Created %s ", buffer);
+ Util_CurrentTime (sizeof (buffer), buffer);
+ fprintf (fileset[dir], "%s\n", buffer);
+ }
+ if (CCTK_Equals (out_fileinfo, "axis labels") ||
+ CCTK_Equals (out_fileinfo, "all"))
+ {
+ fprintf (fileset[dir], "#x-label %c\n", extensions[dir][0]);
+ fprintf (fileset[dir], "#y-label %c\n", extensions[dir][1]);
+ fprintf (fileset[dir], "#z-label %s", advertised_file.varname);
+ if (dim != 2)
{
- free (coord_data_j);
+ if (coord_lower)
+ {
+ fprintf (fileset[dir], zlabel_fmt_string, 'x' + (maxdir-dir-1),
+ coord_lower[maxdir-dir-1] +
+ GH->cctk_delta_space[maxdir-dir-1] *
+ myGH->sp2xyz[dim-1][dir]);
+ }
+ fprintf (fileset[dir], " (%ci = %d)",
+ 'x' + (maxdir-dir-1), myGH->sp2xyz[dim-1][dir]);
}
- return (-3);
+ fputc ('\n', fileset[dir]);
}
+ }
- /* proc 0 writes */
- if (myproc == 0)
- {
- CCTK_REAL stagger_offset_i, stagger_offset_j;
+ /* store file desriptors in database */
+ StoreNamedData (&myGH->fileList_2D, alias, fileset);
+ free (filename);
- /* get the staggering offset for the coordinates */
- stagger_offset_i = CCTK_StaggerDirIndex (dir_i, groupinfo.stagtype) *
- 0.5 * GH->cctk_delta_space[dir_i];
- stagger_offset_j = CCTK_StaggerDirIndex (dir_j, groupinfo.stagtype) *
- 0.5 * GH->cctk_delta_space[dir_j];
+ return (fileset);
+}
- /* print out header */
- fprintf (fdset_2D[dir], header_fmt_string, GH->cctk_time);
- switch (groupinfo.vartype)
- {
- case CCTK_VARIABLE_CHAR:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_BYTE, int, data, hsize,
- 0, have_coords, data_fmt_string_int,fdset_2D[dir]);
- break;
-
- case CCTK_VARIABLE_INT:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_INT, int, data, hsize,
- 0, have_coords, data_fmt_string_int,fdset_2D[dir]);
- break;
-
- case CCTK_VARIABLE_REAL:
- case CCTK_VARIABLE_COMPLEX:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_REAL, double, data, hsize,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX,
- have_coords, data_fmt_string_real, fdset_2D[dir]);
- break;
+/*@@
+ @routine WriteData
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Writes the given hyperslabs into the appropriate output files.
+ @enddesc
+ @@*/
+static void WriteData (int vtype,
+ const char *header,
+ char format[3][30],
+ const CCTK_INT hsize[2],
+ void *const *const hdata,
+ FILE *file)
+{
+ int is_complex;
+ char complex_fmt_string[30];
+ DECLARE_CCTK_PARAMETERS
+
+ is_complex = strncmp (CCTK_VarTypeName (vtype), "CCTK_COMPLEX", 12) == 0;
+ sprintf (complex_fmt_string, "\t\t%%%s", out_format);
+
+ /* print out header */
+ fputs (header, file);
+
+ if (vtype == CCTK_VARIABLE_CHAR)
+ {
+ WRITE_DATA (CCTK_BYTE, int, format[0]);
+ }
+ else if (vtype == CCTK_VARIABLE_INT)
+ {
+ WRITE_DATA (CCTK_INT, int, format[0]);
+ }
+ else if (vtype == CCTK_VARIABLE_REAL || vtype == CCTK_VARIABLE_COMPLEX)
+ {
+ WRITE_DATA (CCTK_REAL, double, format[1]);
+ }
#ifdef CCTK_INT2
- case CCTK_VARIABLE_INT2:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_INT2, int, data, hsize,
- 0, have_coords, data_fmt_string_int,fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_INT2)
+ {
+ WRITE_DATA (CCTK_INT2, int, format[0]);
+ }
#endif
#ifdef CCTK_INT4
- case CCTK_VARIABLE_INT4:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_INT4, int, data, hsize,
- 0, have_coords, data_fmt_string_int,fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_INT4)
+ {
+ WRITE_DATA (CCTK_INT4, int, format[0]);
+ }
#endif
#ifdef CCTK_INT8
- case CCTK_VARIABLE_INT8:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_INT8, int, data, hsize,
- 0, have_coords, data_fmt_string_int,fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_INT8)
+ {
+ WRITE_DATA (CCTK_INT8, int, format[0]);
+ }
#endif
#ifdef CCTK_REAL4
- case CCTK_VARIABLE_REAL4:
- case CCTK_VARIABLE_COMPLEX8:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_REAL4, double, data, hsize,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX8,
- have_coords, data_fmt_string_real, fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL4 || vtype == CCTK_VARIABLE_COMPLEX8)
+ {
+ WRITE_DATA (CCTK_REAL4, double, format[1]);
+ }
#endif
#ifdef CCTK_REAL8
- case CCTK_VARIABLE_REAL8:
- case CCTK_VARIABLE_COMPLEX16:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_REAL8, double, data, hsize,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX16,
- have_coords, data_fmt_string_real, fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL8 || vtype == CCTK_VARIABLE_COMPLEX16)
+ {
+ WRITE_DATA (CCTK_REAL8, double, format[1]);
+ }
#endif
#ifdef CCTK_REAL16
- case CCTK_VARIABLE_REAL16:
- case CCTK_VARIABLE_COMPLEX32:
- OUTPUT_TYPED_DATA (coord_data_i, coord_data_j, stagger_offset_i,
- stagger_offset_j, CCTK_REAL16, double, data, hsize,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX32,
- have_coords, data_fmt_string_real, fdset_2D[dir]);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL16 || vtype == CCTK_VARIABLE_COMPLEX32)
+ {
+ WRITE_DATA (CCTK_REAL16, double, format[1]);
+ }
#endif
- default:
- CCTK_WARN (1, "Unsupported variable type");
- break;
- }
-
- /* keep the file open but flush it */
- fflush (fdset_2D[dir]);
-
- /* free the hyperslabs */
- free (data);
- if (coord_data_i)
- {
- free (coord_data_i);
- }
- if (coord_data_j)
- {
- free (coord_data_j);
- }
-
- } /* end of outputting the data by processor 0 */
-
- } /* end of looping through xyz directions */
+ else
+ {
+ CCTK_WARN (1, "Unsupported variable type");
+ }
- return (0);
+ /* keep the file open but flush it */
+ fflush (file);
}
diff --git a/src/Write3D.c b/src/Write3D.c
index e5c477b..0aee309 100644
--- a/src/Write3D.c
+++ b/src/Write3D.c
@@ -15,81 +15,77 @@
#include "cctk.h"
#include "cctk_Parameters.h"
#include "Hyperslab.h"
+#include "CactusBase/IOUtil/src/ioGH.h"
#include "CactusBase/IOUtil/src/ioutil_AdvertisedFiles.h"
-#include "CactusBase/IOUtil/src/ioutil_CheckpointRecovery.h"
#include "ioASCIIGH.h"
/* the rcs ID and its dummy function to use it */
-static const char *rcsid = "$Id$";
+static const char *rcsid = "$Header$";
CCTK_FILEVERSION(CactusBase_IOASCII_Write3D_c)
-/* enable debug output */
-/*#define IOASCII_DEBUG 1*/
-
-/* macro to output a time volume as typed data */
-#define OUTPUT_TYPED_DATA(hsize, coord, stagger_offset, cctk_type, c_type, \
- data, have_coords, is_cmplx_type, fmt_string, file) \
- { \
- int _i, _j, _k; \
- const cctk_type *_typed_data = (const cctk_type *) (data); \
+/********************************************************************
+ ******************** Macro Definitions ************************
+ ********************************************************************/
+/* uncomment this to enable debugging output */
+/* #define DEBUG_IOASCII 1 */
+
+/* Macro to output a 3D array (with coordinates if available) as typed data
+ For readability, the macro definition implicitely uses the following
+ variables (which are defined in the calling routine):
+ hdata, hsize, is_complex, format[2], file */
+#define WRITE_DATA(cctk_type, c_type, fmt) \
+ { \
+ int _i, _j, _k; \
+ const cctk_type *_hdata = (const cctk_type *) hdata[0]; \
+ const CCTK_REAL *_coord[3]; \
+ \
\
\
- /* output coordinates if available otherwise just the indices */ \
- if (have_coords) \
+ _coord[0] = (const CCTK_REAL *) hdata[1]; \
+ _coord[1] = (const CCTK_REAL *) hdata[2]; \
+ _coord[2] = (const CCTK_REAL *) hdata[3]; \
+ for (_k = 0; _k < hsize[2]; _k++) \
+ { \
+ for (_j = 0; _j < hsize[1]; _j++) \
{ \
- for (_k = 0; _k < hsize[2]; _k++) \
+ for (_i = 0; _i < hsize[0]; _i++) \
{ \
- for (_j = 0; _j < hsize[1]; _j++) \
+ if (_coord[0]) \
{ \
- for (_i = 0; _i < hsize[0]; _i++) \
- { \
- fprintf (file, fmt_string, \
- (double) (*coord[0]++ + stagger_offset[0]), \
- (double) (*coord[1]++ + stagger_offset[1]), \
- (double) (*coord[2]++ + stagger_offset[2]), \
- (c_type) *_typed_data++); \
- if (is_cmplx_type) \
- { \
- fprintf (file, "\t\t"); \
- fprintf (file, out_real_format, (double)*_typed_data++);\
- } \
- fprintf (file, "\n"); \
- } \
- fprintf (file, "\n"); \
+ fprintf (file, fmt, \
+ (double) *_coord[0]++, (double) *_coord[1]++, \
+ (double) *_coord[2]++, (c_type) *_hdata++); \
} \
- } \
- coord[0] -= hsize[0] * hsize[1] * hsize[2]; \
- coord[1] -= hsize[0] * hsize[1] * hsize[2]; \
- coord[2] -= hsize[0] * hsize[1] * hsize[2]; \
- } \
- else \
- { \
- for (_k = 0; _k < hsize[2]; _k++) \
- { \
- for (_j = 0; _j < hsize[1]; _j++) \
+ else \
+ { \
+ fprintf (file, fmt, (double) _i, (double) _j, (double) _k, \
+ (c_type) *_hdata++); \
+ } \
+ \
+ if (is_complex) \
{ \
- for (_i = 0; _i < hsize[0]; _i++) \
- { \
- fprintf (file, fmt_string, \
- (double) _i, \
- (double) _j, \
- (double) _k, \
- (c_type) *_typed_data++); \
- if (is_cmplx_type) \
- { \
- fprintf (file, "\t\t"); \
- fprintf (file, out_real_format, (double)*_typed_data++);\
- } \
- fprintf (file, "\n"); \
- } \
- fprintf (file, "\n"); \
+ fprintf (file, format[2], (c_type) *_hdata++); \
} \
+ fputc ('\n', file); \
} \
+ fputc ('\n', file); \
} \
- }
+ } \
+ }
+/********************************************************************
+ ******************** Internal Routines ************************
+ ********************************************************************/
+static FILE *OpenFile (const cGH *GH, const char *fullname, const char *alias);
+static void WriteData (int vtype,
+ const char *header,
+ char format[3][30],
+ const CCTK_INT hsize[3],
+ void *const *const hdata,
+ FILE *file);
+
/*@@
@routine IOASCII_Write3D
@date Wed 12 Dec 2001
@@ -97,8 +93,11 @@ CCTK_FILEVERSION(CactusBase_IOASCII_Write3D_c)
@desc
Writes the 3D volume of a variable into a gnuplot ASCII file.
@enddesc
- @calls IOUtil_RestartFromRecovery
- IOUtil_AdvertiseFile
+ @calls Hyperslab_DefineGlobalMappingByIndex
+ Hyperslab_FreeMapping
+ Hyperslab_GetList
+ OpenFile
+ WriteData
@var GH
@vdesc Pointer to CCTK GH
@@ -127,344 +126,375 @@ CCTK_FILEVERSION(CactusBase_IOASCII_Write3D_c)
@@*/
int IOASCII_Write3D (const cGH *GH, int vindex, const char *alias)
{
- DECLARE_CCTK_PARAMETERS
- int myproc, groupindex, dir, have_coords;
- asciiioGH *myGH;
- char header_fmt_string[30]; /* header format string */
- char out_real_format[30]; /* data format string for a real type */
- char time_fmt_string[30]; /* time format string */
- char data_fmt_string_int[30]; /* data format string for int types */
- char data_fmt_string_real[30]; /* data format string for real types */
- FILE **file;
- int coord_index[3]; /* variable indices for xyz coordinates */
- CCTK_REAL coord_lower[3]; /* coordinates' minima */
- CCTK_REAL dummy;
- char *filename;
+ int i, total_hsize;
+ int myproc, groupindex, have_coords;
+ int num_requested_hslabs, num_returned_hslabs;
+ char header[30], buffer[30];
+ char format[3][30];
+ FILE *file;
+ cGroup gdata;
char *fullname;
- cGroup groupinfo;
- ioAdvertisedFileDesc advertised_file;
- char buffer[128];
- const int directions[3] = {1, 1, 1};
- const int origin[3] = {0, 0, 0};
- const int lengths[3] = {-1, -1, -1};
- const int downsamples[3] = {1, 1, 1};
- int hsize[3];
- CCTK_REAL *coord_data[3], stagger_offset[3];
- void *data;
-
+ void *hdata[4];
+ int extent_int[3];
+ CCTK_REAL offset[3];
+ CCTK_INT mapping;
+ CCTK_INT vindices[4];
+ CCTK_INT extent[3], hsize[3];
+ const CCTK_INT origin[] = {0, 0, 0},
+ direction[] = {1, 0, 0, 0, 1, 0, 0, 0, 1};
+ DECLARE_CCTK_PARAMETERS
- /* to make the compiler happy */
- file = NULL;
- filename = fullname = NULL;
/* get the variable group information */
+ fullname = CCTK_FullName (vindex);
groupindex = CCTK_GroupIndexFromVarI (vindex);
- CCTK_GroupData (groupindex, &groupinfo);
+ CCTK_GroupData (groupindex, &gdata);
/* check if variable has storage assigned */
if (! CCTK_QueryGroupStorageI (GH, groupindex))
{
- fullname = CCTK_FullName (vindex);
CCTK_VWarn (2, __LINE__, __FILE__, CCTK_THORNSTRING,
"No IOASCII 3D output for '%s' (no storage)", fullname);
free (fullname);
return (-1);
}
- /* Get the handle for IOASCII extensions */
- myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
-
- /* set header and data format strings */
- sprintf (header_fmt_string, "\n\n#Time = %%%s\n", out_format);
- sprintf (out_real_format, "%%%s", out_format);
- dir = 0;
- if (CCTK_Equals (out3D_style, "gnuplot f(t,x,y,z)"))
- {
- sprintf (time_fmt_string, "%%%s\t\t", out_format);
- sprintf (data_fmt_string_int, time_fmt_string, (double) GH->cctk_time);
- sprintf (data_fmt_string_real, time_fmt_string, (double) GH->cctk_time);
- dir = strlen (data_fmt_string_int);
- }
- sprintf (data_fmt_string_int + dir, "%%%s\t\t%%%s\t\t%%d\t\t%%d",
- out_format, out_format);
- sprintf (data_fmt_string_real + dir, "%%%s\t\t%%%s\t\t%%%s\t\t%%%s",
- out_format, out_format, out_format, out_format);
-
- /* get the coordinate indices if we output a grid function */
- if (groupinfo.grouptype == CCTK_GF)
+ /* get the coordinate indices for CCTK_GF variables
+ (CCTK_ARRAY variables never have coordinates associated) */
+ vindices[0] = vindex;
+ have_coords = gdata.grouptype == CCTK_GF;
+ if (have_coords)
{
- have_coords = 1;
- for (dir = 0; dir < 3; dir++)
+ for (i = 1; i <= 3; i++)
{
- CCTK_CoordRange (GH, &coord_lower[dir], &dummy, dir+1, NULL, "cart3d");
- coord_index[dir] = CCTK_CoordIndex (dir + 1, NULL, "cart3d");
- have_coords &= coord_index[dir] >= 0;
+ vindices[i] = CCTK_CoordIndex (i, NULL, "cart3d");
+ have_coords &= vindices[i] >= 0;
}
if (! have_coords)
{
- CCTK_VWarn (8, __LINE__, __FILE__, CCTK_THORNSTRING,
- "IOASCII_Write3D: No coordinate ranges found for '%s'",
- "cart3d");
+ CCTK_WARN (8, "IOASCII_Write3D: No coordinate ranges found for 'card3d'");
}
}
+ num_requested_hslabs = have_coords ? 4 : 1;
+
+ /* set header and data format strings */
+ sprintf (buffer, "\n\n#Time = %%%s\n", out_format);
+ sprintf (header, buffer, (double) GH->cctk_time);
+ i = 0;
+ if (CCTK_Equals (out3D_style, "gnuplot f(t,x,y,z)"))
+ {
+ sprintf (buffer, "%%%s\t\t", out_format);
+ sprintf (format[0], buffer, (double) GH->cctk_time);
+ sprintf (format[1], buffer, (double) GH->cctk_time);
+ i = strlen (format[0]);
+ }
+ if (have_coords)
+ {
+ sprintf (format[0] + i, "%%%s\t\t%%%s\t\t%%d\t\t%%d",
+ out_format, out_format);
+ sprintf (format[1] + i, "%%%s\t\t%%%s\t\t%%%s\t\t%%%s",
+ out_format, out_format, out_format, out_format);
+ }
else
{
- /* CCTK_ARRAY variables never have coordinates associated */
- have_coords = 0;
+ sprintf (format[0] + i, "%%d\t\t%%d\t\t%%d\t\t%%d");
+ sprintf (format[1] + i, "%%d\t\t%%d\t\t%%%s\t\t%%%s",
+ out_format, out_format);
}
+ sprintf (format[2], "\t\t%%%s", out_format);
/* What processor are we on? */
myproc = CCTK_MyProc (GH);
- /* Open the files on the first trip through if we are proc. 0 */
+ /* Open the file on processor 0 */
+ file = myproc == 0 ? OpenFile (GH, fullname, alias) : NULL;
+
+ /* set the extent vector (copy from 'int' to 'CCTK_INT' */
+ CCTK_GroupgshVI (GH, 3, extent_int, vindex);
+ for (i = 0; i < 3; i++)
+ {
+ extent[i] = extent_int[i];
+ }
+
+ /* get the hyperslab mapping */
+ mapping = Hyperslab_DefineGlobalMappingByIndex (GH, vindex, 3,
+ direction,
+ origin,
+ extent,
+ NULL, /* downsample */
+ -1, /* table handle */
+ NULL /* conversion fn */,
+ hsize);
+ if (mapping < 0)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write3D: Failed to define hyperslab mapping for "
+ "variable '%s'", fullname);
+ free (fullname);
+ return (-1);
+ }
+ total_hsize = hsize[0] * hsize[1] * hsize[2];
+ if (total_hsize <= 0)
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write3D: selected hyperslab has zero size for "
+ "variable '%s'", fullname);
+ Hyperslab_FreeMapping (mapping);
+ free (fullname);
+ return (-1);
+ }
+
+ if (myproc == 0)
+ {
+ /* allocate hyperslab buffers */
+ hdata[0] = malloc (total_hsize * CCTK_VarTypeSize (gdata.vartype));
+ hdata[1] = have_coords ? malloc (3 * total_hsize * sizeof (CCTK_REAL)) :
+ NULL;
+ hdata[2] = (CCTK_REAL *) hdata[1] + 1*total_hsize;
+ hdata[3] = (CCTK_REAL *) hdata[1] + 2*total_hsize;
+ }
+
+ /* get the hyperslabs */
+ num_returned_hslabs = Hyperslab_GetList (GH, mapping, num_requested_hslabs,
+ NULL, vindices, NULL, NULL, hdata,
+ NULL);
+
+ /* And dump the data to file */
if (myproc == 0)
{
- /* see if output file for this alias name was already created */
- file = (FILE **) GetNamedData (myGH->fileList_3D, alias);
- if (file == NULL)
+ if (num_returned_hslabs == num_requested_hslabs)
{
- file = (FILE **) malloc (sizeof (FILE *));
- filename = (char *) malloc (strlen (myGH->outdir3D) + strlen (alias) + 9);
-
- /* get the variable's full name */
- fullname = CCTK_FullName (vindex);
-
- /* Open/Create the file */
- /* skip pathname if output goes into current directory */
- if (strcmp (myGH->outdir3D, "."))
+ if (have_coords)
{
- sprintf (filename, "%s/%s_3D.asc", myGH->outdir3D, alias);
- }
- else
- {
- sprintf (filename, "%s_3D.asc", alias);
+ /* get the staggering offset for the coordinates */
+ for (i = 0; i < 3; i++)
+ {
+ offset[i] = 0.5 * GH->cctk_delta_space[i] *
+ CCTK_StaggerDirIndex (i, gdata.stagtype);
+ }
+ for (i = 0; i < total_hsize; i++)
+ {
+ ((CCTK_REAL *) hdata[1])[i] += offset[0];
+ ((CCTK_REAL *) hdata[2])[i] += offset[1];
+ ((CCTK_REAL *) hdata[3])[i] += offset[2];
+ }
}
- /* if restart from recovery, try to open an existing file ... */
- *file = NULL;
- if (IOUtil_RestartFromRecovery (GH))
- {
- *file = fopen (filename, "a");
- }
+ WriteData (gdata.vartype, header, format, hsize, hdata, file);
+ }
+ else
+ {
+ CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
+ "IOASCII_Write3D: Failed to extract hyperslab for "
+ "variable '%s'", fullname);
+ }
- /* otherwise or if that failed, create a new one */
- if (! *file)
- {
- *file = fopen (filename, "w");
- }
- if (! *file)
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Cannot open 3D IOASCII output file '%s'", filename);
- return (-2);
- }
+ /* clean up */
+ free (hdata[0]);
+ if (hdata[1])
+ {
+ free (hdata[1]);
+ }
+ } /* end of outputting the data by processor 0 */
- /* advertise the file for downloading and write file info */
- /* FIXME: this can go when we permanently switch the the
- new filename scheme */
- advertised_file.slice = "";
- advertised_file.thorn = CCTK_THORNSTRING;
- advertised_file.varname = fullname;
- advertised_file.description = "Full-dimensional variable contents";
- advertised_file.mimetype = "application/gnuplot";
+ free (fullname);
- IOUtil_AdvertiseFile (GH, filename, &advertised_file);
+ return (0);
+}
- if (CCTK_Equals (out_fileinfo, "parameter filename") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- buffer[0] = 0;
- CCTK_ParameterFilename (sizeof (buffer), buffer);
- fprintf (*file, "#Parameter file %s\n", buffer);
- }
- if (CCTK_Equals (out_fileinfo, "creation date") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- buffer[0] = 0;
- Util_CurrentDate (sizeof (buffer), buffer);
- fprintf (*file, "#Created %s ", buffer);
- Util_CurrentTime (sizeof (buffer), buffer);
- fprintf (*file, "%s\n", buffer);
- }
- if (CCTK_Equals (out_fileinfo, "axis labels") ||
- CCTK_Equals (out_fileinfo, "all"))
- {
- fprintf (*file, "#z-label %s\n", advertised_file.varname);
- }
- }
- /* store file desriptors in database */
- StoreNamedData (&myGH->fileList_3D, alias, file);
+/********************************************************************
+ ******************** Internal Routines ************************
+ ********************************************************************/
+/*@@
+ @routine OpenFile
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Opens an ASCII file for a given alias name.
+ If this is the first time through, it will create the file,
+ write some header information, and advertise it to IOUtil.
+ @enddesc
- free (filename);
- free (fullname);
- }
+ @returntype FILE *
+ @returndesc
+ the file descriptor, or NULL if the file couldn't be created
+ @endreturndesc
+ @@*/
+static FILE *OpenFile (const cGH *GH, const char *fullname, const char *alias)
+{
+ FILE **file;
+ char *filename;
+ char buffer[128];
+ asciiioGH *myGH;
+ const ioGH *ioUtilGH;
+ ioAdvertisedFileDesc advertised_file;
+ DECLARE_CCTK_PARAMETERS
- /* get the coordinates for grid function output */
- if (have_coords)
+
+ /* get handles for IOUtil and IOASCII extensions */
+ myGH = (asciiioGH *) CCTK_GHExtension (GH, "IOASCII");
+ ioUtilGH = (const ioGH *) CCTK_GHExtension (GH, "IO");
+
+ /* see if we are the first time through */
+ file = (FILE **) GetNamedData (myGH->fileList_3D, alias);
+ if (file)
{
- /* get the i-coordinate volume */
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[0], 0, 3,
- origin, directions, lengths, downsamples,
- (void **) &coord_data[0], hsize) < 0)
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 3D hyperslab for x-coordinate");
- return (-3);
- }
+ return (*file);
+ }
- /* get the j-coordinate volume */
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[1], 0, 3,
- origin, directions, lengths, downsamples,
- (void **) &coord_data[1], hsize) < 0)
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 3D hyperslab for y-coordinate");
- free (coord_data[0]);
- return (-3);
- }
+ file = (FILE **) malloc (sizeof (FILE *));
+ filename = (char *) malloc (strlen (myGH->outdir3D) + strlen (alias) + 9);
- /* get the k-coordinate volume */
- if (Hyperslab_GetHyperslab (GH, 0, coord_index[2], 0, 3,
- origin, directions, lengths, downsamples,
- (void **) &coord_data[2], hsize) < 0)
- {
- CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 3D hyperslab for z-coordinate");
- free (coord_data[1]);
- free (coord_data[0]);
- return (-3);
- }
+ /* Open/Create the file */
+ /* skip pathname if output goes into current directory */
+ if (strcmp (myGH->outdir3D, "."))
+ {
+ sprintf (filename, "%s/%s_3D.asc", myGH->outdir3D, alias);
}
else
{
- /* grid arrays don't have coordinates assigned */
- coord_data[0] = coord_data[1] = coord_data[2] = NULL;
+ sprintf (filename, "%s_3D.asc", alias);
}
- /* get the variable volume */
- if (Hyperslab_GetHyperslab (GH, 0, vindex, 0, 3, origin, directions,
- lengths, downsamples, &data, hsize) < 0)
+ /* if restart from recovery, try to open an existing file ... */
+ *file = fopen (filename, ioUtilGH->recovered ? "a" : "w");
+ if (! *file)
{
- fullname = CCTK_FullName (vindex);
CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING,
- "Failed to extract 3D hyperslab for variable '%s'", fullname);
- free (fullname);
- for (dir = 0; dir < 3; dir++)
- {
- if (coord_data[dir])
- {
- free (coord_data[dir]);
- }
- }
- return (-3);
+ "Cannot open 3D IOASCII output file '%s'", filename);
+ return (NULL);
}
- /* proc 0 writes */
- if (myproc == 0)
+ /* advertise the file for downloading and write file info */
+ advertised_file.slice = "";
+ advertised_file.thorn = CCTK_THORNSTRING;
+ advertised_file.varname = fullname;
+ advertised_file.description = "Full-dimensional variable contents";
+ advertised_file.mimetype = "application/gnuplot";
+
+ IOUtil_AdvertiseFile (GH, filename, &advertised_file);
+
+ if (CCTK_Equals (out_fileinfo, "parameter filename") ||
+ CCTK_Equals (out_fileinfo, "all"))
{
- /* get the staggering offset for the coordinates */
- for (dir = 0; dir < 3; dir++)
- {
- stagger_offset[dir] = CCTK_StaggerDirIndex (dir, groupinfo.stagtype) *
- 0.5 * GH->cctk_delta_space[dir];
- }
+ buffer[0] = 0;
+ CCTK_ParameterFilename (sizeof (buffer), buffer);
+ fprintf (*file, "#Parameter file %s\n", buffer);
+ }
+ if (CCTK_Equals (out_fileinfo, "creation date") ||
+ CCTK_Equals (out_fileinfo, "all"))
+ {
+ buffer[0] = 0;
+ Util_CurrentDate (sizeof (buffer), buffer);
+ fprintf (*file, "#Created %s ", buffer);
+ Util_CurrentTime (sizeof (buffer), buffer);
+ fprintf (*file, "%s\n", buffer);
+ }
+ if (CCTK_Equals (out_fileinfo, "axis labels") ||
+ CCTK_Equals (out_fileinfo, "all"))
+ {
+ fprintf (*file, "#z-label %s\n", advertised_file.varname);
+ }
- /* print out header */
- fprintf (*file, header_fmt_string, GH->cctk_time);
+ /* store file desriptors in database */
+ StoreNamedData (&myGH->fileList_3D, alias, file);
+
+ free (filename);
+
+ return (*file);
+}
- switch (groupinfo.vartype)
- {
- case CCTK_VARIABLE_CHAR:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_BYTE, int,
- data, have_coords, 0, data_fmt_string_int, *file);
- break;
-
- case CCTK_VARIABLE_INT:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_INT, int,
- data, have_coords, 0, data_fmt_string_int, *file);
- break;
-
- case CCTK_VARIABLE_REAL:
- case CCTK_VARIABLE_COMPLEX:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_REAL, double,
- data, have_coords,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX,
- data_fmt_string_real, *file);
- break;
+
+/*@@
+ @routine WriteData
+ @date Wed 12 Dec 2001
+ @author Thomas Radke
+ @desc
+ Writes the given hyperslab data into a file.
+ @enddesc
+ @@*/
+static void WriteData (int vtype,
+ const char *header,
+ char format[3][30],
+ const CCTK_INT hsize[3],
+ void *const *const hdata,
+ FILE *file)
+{
+ int is_complex;
+
+
+ if (file == NULL)
+ {
+ return;
+ }
+
+ is_complex = strncmp (CCTK_VarTypeName (vtype), "CCTK_COMPLEX", 12) == 0;
+
+ /* print out header */
+ fputs (header, file);
+
+ if (vtype == CCTK_VARIABLE_CHAR)
+ {
+ WRITE_DATA (CCTK_BYTE, int, format[0]);
+ }
+ else if (vtype == CCTK_VARIABLE_INT)
+ {
+ WRITE_DATA (CCTK_INT, int, format[0]);
+ }
+ else if (vtype == CCTK_VARIABLE_REAL || vtype == CCTK_VARIABLE_COMPLEX)
+ {
+ WRITE_DATA (CCTK_REAL, double, format[1]);
+ }
#ifdef CCTK_INT2
- case CCTK_VARIABLE_INT2:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_INT2, int,
- data, have_coords, 0, data_fmt_string_int, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_INT2)
+ {
+ WRITE_DATA (CCTK_INT2, int, format[0]);
+ }
#endif
#ifdef CCTK_INT4
- case CCTK_VARIABLE_INT4:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_INT4, int,
- data, have_coords, 0, data_fmt_string_int, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_INT4)
+ {
+ WRITE_DATA (CCTK_INT4, int, format[0]);
+ }
#endif
#ifdef CCTK_INT8
- case CCTK_VARIABLE_INT8:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_INT8, int,
- data, have_coords, 0, data_fmt_string_int, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_INT8)
+ {
+ WRITE_DATA (CCTK_INT8, int, format[0]);
+ }
#endif
#ifdef CCTK_REAL4
- case CCTK_VARIABLE_REAL4:
- case CCTK_VARIABLE_COMPLEX8:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_REAL4,
- double, data, have_coords,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX8,
- data_fmt_string_real, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL4 || vtype == CCTK_VARIABLE_COMPLEX8)
+ {
+ WRITE_DATA (CCTK_REAL4, double, format[1]);
+ }
#endif
#ifdef CCTK_REAL8
- case CCTK_VARIABLE_REAL8:
- case CCTK_VARIABLE_COMPLEX16:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_REAL8,
- double, data, have_coords,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX16,
- data_fmt_string_real, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL8 || vtype == CCTK_VARIABLE_COMPLEX16)
+ {
+ WRITE_DATA (CCTK_REAL8, double, format[1]);
+ }
#endif
#ifdef CCTK_REAL16
- case CCTK_VARIABLE_REAL16:
- case CCTK_VARIABLE_COMPLEX32:
- OUTPUT_TYPED_DATA (hsize, coord_data, stagger_offset, CCTK_REAL16,
- double, data, have_coords,
- groupinfo.vartype == CCTK_VARIABLE_COMPLEX32,
- data_fmt_string_real, *file);
- break;
+ else if (vtype == CCTK_VARIABLE_REAL16 || vtype == CCTK_VARIABLE_COMPLEX32)
+ {
+ WRITE_DATA (CCTK_REAL16, double, format[1]);
+ }
#endif
- default:
- CCTK_WARN (1, "Unsupported variable type");
- break;
- }
-
- /* keep the file open but flush it */
- fflush (*file);
-
- /* free the hyperslabs */
- free (data);
- for (dir = 0; dir < 3; dir++)
- {
- if (coord_data[dir])
- {
- free (coord_data[dir]);
- }
- }
-
- } /* end of outputting the data by processor 0 */
-
+ else
+ {
+ CCTK_WARN (1, "Unsupported variable type");
+ }
- return (0);
+ /* keep the file open but flush it */
+ fflush (file);
}
diff --git a/src/ioASCIIGH.h b/src/ioASCIIGH.h
index 1b9f705..19d5316 100644
--- a/src/ioASCIIGH.h
+++ b/src/ioASCIIGH.h
@@ -19,30 +19,23 @@ extern "C"
typedef struct IOASCIIGH
{
- /* the number of times output */
- int out1D_every;
- int out2D_every;
- int out3D_every;
+ /* default number of times to output */
+ int out1D_every_default, out2D_every_default, out3D_every_default;
- /* flags indicating output for var [i] */
- char *do_out1D;
- char *do_out2D;
- char *do_out3D;
+ /* flags indicating output for var[i] */
+ int *out1D_every, *out2D_every, *out3D_every;
+
+ /* variables to output */
+ char *out1D_vars, *out2D_vars, *out3D_vars;
/* directories in which to output */
- char *outdir1D;
- char *outdir2D;
- char *outdir3D;
+ char *outdir1D, *outdir2D, *outdir3D;
/* the last iteration output for var [i] */
- int *out1D_last;
- int *out2D_last;
- int *out3D_last;
+ int *out1D_last, *out2D_last, *out3D_last;
/* database for names of output files that were already created */
- pNamedData *filenameList1D;
- pNamedData *fileList_2D;
- pNamedData *fileList_3D;
+ pNamedData *filenameList1D, *fileList_2D, *fileList_3D;
/* for 1D lines, we define the index where to start the line:
spxyz[maxdim][XYZdirection][xyzstart_index] */