/* * swharp_vectorB. * * Created by Xudong Sun on 8/22/11. * * Modified by Monica Bobra to * -- include ALL spaceweather keywords in Leka and Barnes (2003, I and II) * -- include potential field calculation from Keiji Hayashi * -- run on los and vector data 15 april 2012 via sharp_functions.c * Bz arrays * Write out abs(B) as data segment and a few keywords as SW index * * Use: * First use the bmap module to create the in= and mask= parameters. * * then run this module: * swharp_vectorB "in=su_mbobra.bmap_fd10[401][2011.03.09_00:00:00_TAI-2011.03.10_03:00:00_TAI]" / * "mask=su_mbobra.bitmap_fd10[401][2011.03.09_00:00:00_TAI-2011.03 * .10_03:00:00_TAI]" / * "out=su_mbobra.sharp_fd10" "dzvalue=0.001" */ #include #include #include #include float cdelt1_orig; float cdelt1; double rsun_ref; double dsun_obs; double rsun_obs; float imcrpix1; float imcrpix2; float crpix1; float crpix2; #include "sharp_functions.c" #define DIE(msg) {fflush(stdout); fprintf(stderr, "%s, status=%d\n", msg, status); return(status);} #define SHOW(msg) {printf("%s", msg); fflush(stdout);} #define IN_FILES 3 /* Number of input files */ #define PI (3.141592653589793) /* Ratio of circumference to diameter of a circle*/ #define MUNAUGHT (0.0000012566370614) /* magnetic constant */ /* declaring all the functions */ int computeMu(float *bz, int *dims, float *mu, float *inverseMu); int computeAbsFlux(float *bz, int *dims, float *absFlux, float *mean_vf_ptr, int *mask, float *inverseMu); int computeBh(float *bx, float *by, float *bz, float *bh, int *dims, float *mean_hf_ptr, int *mask); int computeGamma(float *bx, float *by, float *bz, float *bh, int *dims, float *mean_gamma_ptr, int *mask); int readFits(char *filename, float **image, int *dims); int writeFits(char *filename, float *image, int *dims); int computeB_total(float *bx, float *by, float *bz, float *bt, int *dims, int *mask); int computeBtotalderivative(float *bt, int *dims, float *mean_derivative_btotal_ptr, int *mask); int computeBhderivative(float *bh, int *dims, float *mean_derivative_bh_ptr, int *mask); int computeBzderivative(float *bz, int *dims, float *mean_derivative_bz_ptr, int *mask); int computeJz(float *by, float *bx, int *dims, float *jz, float *mean_jz_ptr, float *us_i_ptr, int *mask); int computeAlpha(float *bz, int *dims, float *jz, float *mean_alpha_ptr, int *mask); int computeHelicity(float *bz, int *dims, float *jz, float *mean_ih_ptr, float *total_us_ih_ptr, float *total_abs_ih_ptr, int *mask); int computeSumAbsPerPolarity(float *bz, float *jz, int *dims, float *totaljzptr, int *mask); void greenpot(float *bx, float *by, float *bz, int nnx, int nny); int computeFreeEnergy(float *bx, float *by, float *bpx, float *bpy, int *dims, float *meanpotptr, float *totpotptr, int *mask); int computeShearAngle(float *bx, float *by, float *bz, float *bpx, float *bpy, float *bpz, int *dims, float *meanshear_angleptr, float *area_w_shear_gt_45ptr, float *meanshear_anglehptr, float *area_w_shear_gt_45hptr, int *mask); char *module_name = "swharp_vectorB"; /* Module name */ ModuleArgs_t module_args[] = { {ARG_STRING, "in", NULL, "Input vec mag recordset."}, {ARG_STRING, "mask", NULL, "Input bitmap recordset."}, {ARG_STRING, "out", NULL, "Output series."}, {ARG_FLOAT, "dzvalue", NULL, "Monopole depth."}, {ARG_END} }; int DoIt(void) { int status = DRMS_SUCCESS; char *inQuery, *outQuery; // input series query string char *maskQuery; // mask series query string DRMS_RecordSet_t *inRecSet, *outRecSet, *maskRecSet; DRMS_Record_t *inRec, *outRec, *maskRec; DRMS_Segment_t *inSegBx, *inSegBy, *inSegBz, *outSeg, *maskSeg; DRMS_Array_t *inArrayBx, *inArrayBy, *inArrayBz, *outArray, *maskArray; float *inverseMu, *mu, *bx, *by, *bz, *outData, *bh, *bt, *jz, *bpx, *bpy, *bpz; int *mask; int dims[2], nxny, nx, ny; // dimensions; NAXIS1 = dims[0] which is the number of columns. float mean_vf = 0.0; float absFlux = 0.0; float mean_hf = 0.0; float mean_gamma = 0.0; float mean_derivative_btotal = 0.0; float mean_derivative_bh = 0.0; float mean_derivative_bz = 0.0; float mean_jz = 0.0; float us_i = 0.0; float mean_alpha = 0.0; float mean_ih = 0.0; float total_us_ih = 0.0; float total_abs_ih = 0.0; float totaljz = 0.0; float totpot =0.0; float meanpot = 0.0; float area_w_shear_gt_45 = 0.0; float meanshear_angle = 0.0; float area_w_shear_gt_45h = 0.0; float meanshear_angleh = 0.0; int nrecs, irec, i; /* Input */ inQuery = (char *) params_get_str(&cmdparams, "in"); inRecSet = drms_open_records(drms_env, inQuery, &status); if (status || inRecSet->n == 0) DIE("No input data found"); nrecs = inRecSet->n; /* Mask */ maskQuery = (char *) params_get_str(&cmdparams, "mask"); maskRecSet = drms_open_records(drms_env, maskQuery, &status); if (status || maskRecSet->n == 0) DIE("No mask data found"); if (maskRecSet->n != nrecs) DIE("Mask and Input series do not have a 1:1 match"); /* Output */ outQuery = (char *) params_get_str(&cmdparams, "out"); outRecSet = drms_create_records(drms_env, nrecs, outQuery, DRMS_PERMANENT, &status); if (status) DIE("Output recordset not created"); /* Do this for each record */ for (irec = 0; irec < nrecs; irec++) { /* Input record and data */ inRec = inRecSet->records[irec]; printf("Input Record #%d of #%d\n", irec+1, nrecs); fflush(stdout); maskRec = maskRecSet->records[irec]; printf("Mask Record #%d of #%d\n", irec+1, nrecs); fflush(stdout); inSegBx = drms_segment_lookupnum(inRec, 0); /* Assume this is Bx equivalent */ inSegBy = drms_segment_lookupnum(inRec, 1); /* Assume this is By equivalent */ inSegBz = drms_segment_lookupnum(inRec, 2); /* Assume this is Bz equivalent */ maskSeg = drms_segment_lookupnum(maskRec, 0); /* This is the bitmap */ inArrayBx = drms_segment_read(inSegBx, DRMS_TYPE_FLOAT, &status); if (status) DIE("No Bx data file found. \n"); inArrayBy = drms_segment_read(inSegBy, DRMS_TYPE_FLOAT, &status); if (status) DIE("No By data file found. \n"); inArrayBz = drms_segment_read(inSegBz, DRMS_TYPE_FLOAT, &status); if (status) DIE("No Bz data file found. \n"); maskArray = drms_segment_read(maskSeg, DRMS_TYPE_INT, &status); if (status) DIE("No mask data file found. \n"); cdelt1_orig = drms_getkey_float(inRec, "CDELT1", &status); dsun_obs = drms_getkey_float(inRec, "DSUN_OBS", &status); rsun_ref = drms_getkey_double(inRec, "RSUN_REF", &status); rsun_obs = drms_getkey_double(inRec, "RSUN_OBS", &status); imcrpix1 = drms_getkey_float(inRec, "IMCRPIX1", &status); imcrpix2 = drms_getkey_float(inRec, "IMCRPIX2", &status); crpix1 = drms_getkey_float(inRec, "CRPIX1", &status); crpix2 = drms_getkey_float(inRec, "CRPIX2", &status); cdelt1=( (rsun_ref*cdelt1_orig*PI/180.) / (dsun_obs) )*(180./PI)*(3600.); //convert cdelt1 from degrees to arcsec (approximately) printf("cdelt1_orig=%f\n",cdelt1_orig); printf("cdelt1=%f\n",cdelt1); printf("rsun_obs/rsun_ref=%f\n",rsun_obs/rsun_ref); printf("rsun_ref/rsun_obs=%f\n",rsun_ref/rsun_obs); printf("test1=%f\n",((1/cdelt1_orig)*(rsun_obs/rsun_ref)*(1000000.))); printf("test2=%f\n",((cdelt1_orig)*(PI/180)*(rsun_ref)*(1/1000000.))); bx = (float *)inArrayBx->data; by = (float *)inArrayBy->data; bz = (float *)inArrayBz->data; mask = (int *)maskArray->data; nx = dims[0] = inArrayBz->axis[0]; ny = dims[1] = inArrayBz->axis[1]; nxny = dims[0] * dims[1]; if (maskArray->axis[0] != nx || maskArray->axis[1] != ny) DIE("Mask and Input series are not of the same size"); /* This is to modify the data for each PROJECTION method */ int flag; char* value1; value1 = drms_getkey_string(inRec, "PROJECTION", &status); flag = strcmp("LambertCylindrical",value1); if (flag == 0) { int i, j; for (j = 0; j < ny; j++) { for (i = 0; i < nx; i++) { by[j * nx + i] = - by[j * nx + i]; } } } /* Output data */ outRec = outRecSet->records[irec]; drms_setlink_static(outRec, "SRCLINK", inRec->recnum); /*===========================================*/ /* Malloc some arrays */ inverseMu = (float *)malloc(nx*ny*sizeof(float)); mu = (float *)malloc(nx*ny*sizeof(float)); bh = (float *)malloc(nx*ny*sizeof(float)); bt = (float *)malloc(nx*ny*sizeof(float)); jz = (float *)malloc(nx*ny*sizeof(float)); bpx = (float *)malloc(nx*ny*sizeof(float)); bpy = (float *)malloc(nx*ny*sizeof(float)); bpz = (float *)malloc(nx*ny*sizeof(float)); /*===========================================*/ /* SW Keyword computation */ computeMu(bz, dims, mu, inverseMu); if (computeAbsFlux(bz, dims, &absFlux, &mean_vf, mask, inverseMu)) { absFlux = 0.0 / 0.0; // If fail, fill in NaN mean_vf = 0.0 / 0.0; } drms_setkey_float(outRec, "USFLUX", mean_vf); for (i=0 ;i