00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035 #include "jsoc_main.h"
00036
00037 #include <stdio.h>
00038 #include <string.h>
00039 #include <stdlib.h>
00040 #include <stdarg.h>
00041 #include <math.h>
00042 #include <sys/time.h>
00043 #include <sys/resource.h>
00044
00045
00046 #include "mex.h"
00047 #include "mexhead.h"
00048 #include "mxt_jsoc.c"
00049
00050 #include "hmi_segment.h"
00051
00052 #include "roi_stats_mag_defs.h"
00053
00054 #include "segment_modelset.h"
00055
00056 #include "propagate_keys.c"
00057
00058
00059
00060
00061
00062 #define DIE(msg) do { \
00063 fflush(stdout); \
00064 fprintf(stderr, "%s: FATAL: %s. (status=%d)\n", module_name, msg, status); \
00065 return(status ? status : 1); \
00066 } while (0)
00067
00068
00069 #define WARN(msg) do { \
00070 fflush(stdout); \
00071 fprintf(stderr, "%s: WARNING: %s. Continuing.\n", module_name, msg); \
00072 fflush(stderr); \
00073 } while (0)
00074
00075
00076
00077
00078
00079
00080
00081 void
00082 V_printf(int flag, char *first, char *format, ...) {
00083 va_list args;
00084 extern char *module_name;
00085 FILE *fp = (flag > 0) ? stdout : stderr;
00086
00087 va_start(args, format);
00088 if (flag != 0) {
00089
00090
00091 if (first)
00092 fprintf(fp, "%s%s: ", first, module_name);
00093 vfprintf(fp, format, args);
00094 fflush(fp);
00095 }
00096 va_end(args);
00097 }
00098
00099
00100
00101 #define DTOR (M_PI / 180.)
00102 #define RAD2ARCSEC (648000. / M_PI)
00103
00104
00105
00106
00107
00108
00109
00110
00111 #define PIX_X(wx,wy) ((((wx-crvalx)*cosa + (wy-crvaly)*sina)/cdelt)+crpix1)
00112 #define PIX_Y(wx,wy) ((((wy-crvaly)*cosa - (wx-crvalx)*sina)/cdelt)+crpix2)
00113 #define WX(pix_x,pix_y) (((pix_x-crpix1)*cosa - (pix_y-crpix2)*sina)*cdelt+crvalx)
00114 #define WY(pix_x,pix_y) (((pix_y-crpix2)*cosa + (pix_x-crpix1)*sina)*cdelt+crvaly)
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124 static double getwalltime(void)
00125 {
00126 struct timeval tv;
00127 gettimeofday(&tv, NULL);
00128 return tv.tv_sec * 1000.0 + tv.tv_usec/1000.0;
00129 }
00130
00131 static double getcputime(double *utime, double *stime)
00132 {
00133
00134 struct rusage ru;
00135 getrusage(RUSAGE_SELF, &ru);
00136 *utime = ru.ru_utime.tv_sec * 1000.0 + ru.ru_utime.tv_usec / 1000.0;
00137 *stime = ru.ru_stime.tv_sec * 1000.0 + ru.ru_stime.tv_usec / 1000.0;
00138 return *utime + *stime;
00139 }
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154 static
00155 char *
00156 get_instrument_mode(DRMS_Record_t *xmRec)
00157 {
00158 char * const default_mode = "HMI";
00159 int status = 0;
00160 char *kw;
00161
00162 kw = drms_getkey_string(xmRec, "TELESCOP", &status);
00163 if (status == 0) {
00164
00165 if (strcasestr(kw, "SDO") || strcasestr(kw, "HMI"))
00166 return "HMI";
00167 else if (strcasestr(kw, "SOHO") || strcasestr(kw, "MDI"))
00168 return "MDI";
00169 else
00170 return default_mode;
00171 }
00172 return default_mode;
00173 }
00174
00175
00176
00177
00178
00179
00180 static void
00181 printkey_vector(char *str, int n, const mxArray *a)
00182 {
00183 const int numel = mxGetNumberOfElements(a);
00184 const double *x = mxGetPr(a);
00185 int np = 0;
00186 int i;
00187
00188 for (i = 0; (i < numel) && (n > 0); i++, n -= np) {
00189 np = snprintf(str, n, "%.4g%s", x[i], (i+1 < numel) ? "," : "");
00190 str += np;
00191 }
00192 }
00193
00194 static int
00195 setkey_code_info(char *mode, DRMS_Record_t *outRec)
00196 {
00197 extern char *hmi_segment_version;
00198 char keystr[80];
00199 int ok;
00200 int not_ok = 0;
00201
00202
00203 snprintf(keystr, sizeof(keystr), "%s ver: %s", module_name, hmi_segment_version);
00204 ok = drms_setkey_string(outRec, "ARMCODEV", keystr);
00205 if (ok != DRMS_SUCCESS) not_ok++;
00206
00207 ok = drms_setkey_string(outRec, "ARMDOCU",
00208 (strcmp(mode, "HMI") == 0) ?
00209 "http://jsoc.stanford.edu/jsocwiki/ARmaskDataSeries" :
00210 "http://jsoc.stanford.edu/jsocwiki/MDI_ARmaskDataSeries");
00211 if (ok != DRMS_SUCCESS) not_ok++;
00212
00213 return not_ok;
00214 }
00215
00216 static int
00217 setkey_mask_qual(DRMS_Record_t *outRec,
00218 int nclean,
00219 char *y,
00220 int M, int N)
00221 {
00222 const int totalval = M*N;
00223 int missval, i;
00224 int quality;
00225 int ok;
00226 int not_ok = 0;
00227
00228
00229 for (missval = i = 0; i < totalval; i++)
00230 if (y[i] == 0)
00231 missval++;
00232
00233 ok = drms_setkey_int(outRec, "TOTVALS", totalval);
00234 if (ok != DRMS_SUCCESS) not_ok++;
00235 ok = drms_setkey_int(outRec, "DATAVALS", totalval - missval);
00236 if (ok != DRMS_SUCCESS) not_ok++;
00237 ok = drms_setkey_int(outRec, "MISSVALS", missval);
00238 if (ok != DRMS_SUCCESS) not_ok++;
00239
00240 ok = drms_setkey_int(outRec, "ARM_NCLN", nclean);
00241 if (ok != DRMS_SUCCESS) not_ok++;
00242
00243 quality = 0x0;
00244 quality |= (nclean > 2000) ? 1 : 0;
00245 ok = drms_setkey_int(outRec, "ARM_QUAL", quality);
00246 if (ok != DRMS_SUCCESS) not_ok++;
00247
00248 return not_ok;
00249 }
00250
00251 static int
00252 setkey_mask_stats(DRMS_Record_t *outRec,
00253 double *s,
00254 seg_modelset_t *modelset)
00255 {
00256 const int Nc = modelset->nclass;
00257 int ok;
00258 int not_ok = 0;
00259 seg_onemodel_t *m1;
00260 int class;
00261 int sn;
00262
00263
00264 for (class = 0; class < Nc; class++) {
00265 m1 = &(modelset->models[class]);
00266 if (strstr(m1->name, "active") != 0)
00267 break;
00268 }
00269
00270
00271 if (class < modelset->nclass) {
00272
00273 for (sn = 0; sn < RS_num_stats; sn++) {
00274 const char *name1 = RS_index2mask_keyname[sn];
00275 double stat1 = s[sn*Nc+class];
00276
00277 if (name1) {
00278 switch (*name1) {
00279 case 'i':
00280 ok = drms_setkey_int(outRec, name1+1, (int) stat1);
00281 break;
00282 case 'f':
00283 ok = drms_setkey_float(outRec, name1+1, (float) stat1);
00284
00285 break;
00286 default:
00287 WARN("setkey_mask_stats: unknown key type (first char of HMI keyname)");
00288 ok = -1;
00289 break;
00290 }
00291 if (ok != DRMS_SUCCESS) not_ok++;
00292 }
00293 }
00294 } else {
00295 not_ok = -1;
00296 }
00297
00298 return not_ok;
00299 }
00300
00301 static int
00302 setkey_model_params(DRMS_Record_t *outRec,
00303 seg_modelset_t *modelset)
00304 {
00305 int ok;
00306 int not_ok = 0;
00307 seg_onemodel_t *m1;
00308 int inx;
00309 int modelnum;
00310 char *key_match;
00311
00312
00313 static char *model2key[] = {"quiet", "QUIET", "active", "ACTIVE", NULL, NULL};
00314
00315
00316 ok = drms_setkey_int(outRec, "NCLASS", modelset->nclass);
00317 if (ok != DRMS_SUCCESS) not_ok++;
00318
00319 ok = drms_setkey_int(outRec, "OFFDISK", 0);
00320 if (ok != DRMS_SUCCESS) not_ok++;
00321
00322 ok = drms_setkey_int(outRec, "ON_PATCH", 32);
00323 if (ok != DRMS_SUCCESS) not_ok++;
00324
00325 for (inx = 0; model2key[inx] != NULL; inx += 2) {
00326
00327 modelnum = seg_modelname2modelnum(modelset, model2key[inx]);
00328 if (modelnum < 0) {
00329 not_ok++;
00330 } else {
00331
00332 ok = drms_setkey_int(outRec, model2key[inx+1], modelnum+1);
00333 if (ok != DRMS_SUCCESS) not_ok++;
00334 }
00335 }
00336
00337 return not_ok;
00338 }
00339
00340
00341 static int
00342 setkey_algorithm_params(DRMS_Record_t *outRec,
00343 const char *modelName,
00344 mxArray *prhs[])
00345 {
00346 char kstr[256];
00347 const int sz = sizeof(kstr);
00348 int ok;
00349 int not_ok = 0;
00350
00351
00352 printkey_vector(kstr, sz, prhs[MXT_Hseg_ARG_iter]);
00353 ok = drms_setkey_string(outRec, "ARM_ITER", kstr);
00354 if (ok != DRMS_SUCCESS) not_ok++;
00355
00356 printkey_vector(kstr, sz, prhs[MXT_Hseg_ARG_T]);
00357 ok = drms_setkey_string(outRec, "ARM_TEMP", kstr);
00358 if (ok != DRMS_SUCCESS) not_ok++;
00359
00360 printkey_vector(kstr, sz, prhs[MXT_Hseg_ARG_beta]);
00361 ok = drms_setkey_string(outRec, "ARM_BETA", kstr);
00362 if (ok != DRMS_SUCCESS) not_ok++;
00363
00364 printkey_vector(kstr, sz, prhs[MXT_Hseg_ARG_alpha]);
00365 ok = drms_setkey_string(outRec, "ARM_ALFA", kstr);
00366 if (ok != DRMS_SUCCESS) not_ok++;
00367
00368 ok = drms_setkey_float(outRec, "ARM_RHO",
00369 (float) mxGetScalar(prhs[MXT_Hseg_ARG_rho]));
00370 if (ok != DRMS_SUCCESS) not_ok++;
00371
00372
00373 ok = drms_setkey_float(outRec, "ARM_KPAR", -1.0);
00374 if (ok != DRMS_SUCCESS) not_ok++;
00375
00376
00377 snprintf(kstr, sz, "(unused)");
00378 ok = drms_setkey_string(outRec, "ARM_KWT", kstr);
00379 if (ok != DRMS_SUCCESS) not_ok++;
00380
00381
00382 ok = drms_setkey_float(outRec, "ARM_THRS", -1.0);
00383 if (ok != DRMS_SUCCESS) not_ok++;
00384
00385 ok = drms_setkey_float(outRec, "ARM_EDGE",
00386 mxGetScalar(prhs[MXT_Hseg_ARG_edge]));
00387 if (ok != DRMS_SUCCESS) not_ok++;
00388
00389 drms_setkey_string(outRec, "ARM_MODL", modelName);
00390 if (ok != DRMS_SUCCESS) not_ok++;
00391
00392 return not_ok;
00393 }
00394
00395
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405
00406
00407 #define kRecSetXM "xm"
00408 #define kRecSetXP "xp"
00409 #define kParEdge "edge"
00410 #define kParIter "iter"
00411 #define kParT "T"
00412 #define kParBeta "beta"
00413
00414 #define kParRho "rho"
00415 #define kParModel "model"
00416 #define kSeriesOut "y"
00417 #define kVerb "VERB"
00418
00419 char *module_name = "hmi_segment_module";
00420 char *mex2c_progname = "hmi_segment_module";
00421 char *hmi_segment_version = "2.0";
00422
00423
00424 ModuleArgs_t module_args[] =
00425 {
00426 {ARG_STRING, kRecSetXM, "", "Input mgram data records."},
00427 {ARG_STRING, kRecSetXP, "", "Input pgram data records."},
00428 {ARG_FLOAT, kParEdge, "2.5", "Limb width set-to-quiet (pixels)"},
00429 {ARG_FLOATS, kParIter, "[0,0.05]", "Iterations (RV(2))"},
00430 {ARG_FLOATS, kParT, "[1,1,0.9,0]","Temperature (RV(4))"},
00431 {ARG_FLOAT, kParBeta, "0.3", "Smoothness"},
00432 {ARG_FLOAT, kParRho, "100", "Smoothness Anisotropy"},
00433 {ARG_STRING, kParModel, "", "Model set name (`/builtin/all' for list)"},
00434 {ARG_STRING, kSeriesOut, "", "Output data series."},
00435 {ARG_INT, kVerb, "1", "Verbosity: 0=errs only; 1, 2, 3 = more"},
00436 {ARG_END}
00437 };
00438
00439
00440
00441
00442
00443
00444
00445
00446 int DoIt(void)
00447 {
00448
00449 int status = DRMS_SUCCESS;
00450 char errmsg[256];
00451 char *msg;
00452 CmdParams_t *params = &cmdparams;
00453 const char *xmRecQuery = params_get_str(params, kRecSetXM);
00454 const char *xpRecQuery = params_get_str(params, kRecSetXP);
00455 const char *yRecQuery = params_get_str(params, kSeriesOut);
00456 const double edge_pix = params_get_float(params, kParEdge);
00457 const char *modelName = params_get_str(params, kParModel);
00458 const int verbflag = params_get_int(params, kVerb);
00459
00460 DRMS_RecordSet_t *xmRD, *xpRD, *yRD;
00461 DRMS_Record_t *xmRec, *xpRec, *yRec;
00462 DRMS_Segment_t *xmSeg, *xpSeg, *ySeg;
00463 DRMS_Array_t *xmArray, *xpArray, *yArray;
00464 DRMS_Link_t *srcLink_M, *srcLink_P;
00465
00466
00467 int nrhs;
00468 const int nlhs = MXT_Hseg_NARGOUT_MAX;
00469 mxArray *prhs[MXT_Hseg_NARGIN_MAX];
00470 mxArray *plhs[MXT_Hseg_NARGOUT_MAX];
00471 double *xm_tmp, *xp_tmp;
00472
00473 seg_modelset_t *modelset;
00474 seg_onemodel_t *m1;
00475 int Nclass, class, class_quiet;
00476 int ds, Nds, ds_good;
00477 int M, N;
00478
00479 double rSun, x0, y0, p0, beta;
00480 TIME t_rec;
00481 char time_buf[64];
00482 char *inst_mode;
00483
00484 float crvalx, crvaly, cdelt, crpix1, crpix2, crota2, crlt, sina, cosa;
00485 double rsun_ref, dsun_obs;
00486
00487 double wt0, wt1, wt;
00488 double ut0, ut1, ut;
00489 double st0, st1, st;
00490 double ct0, ct1, ct;
00491
00492
00493 wt0 = getwalltime();
00494 ct0 = getcputime(&ut0, &st0);
00495
00496 if (strcmp(modelName, SEG_BUILTIN_PREFIX "/all") == 0) {
00497 modelset = NULL;
00498 } else {
00499 modelset = seg_modelsetname2modelset(modelName, &msg, 1);
00500 if (modelset == NULL)
00501 fprintf(stderr, "%s: Did not recognize model <%s>\nError: %s\n",
00502 module_name, modelName, msg);
00503 }
00504
00505 if (modelset == NULL) {
00506
00507 fprintf(stderr, "Built-in models are:\n");
00508 seg_modelsets_fprintf(stderr, (verbflag > 0) ? 1 : 0);
00509 DIE("Did not find a known model. Cannot make masks");
00510 }
00511
00512 if (verbflag > 2)
00513 seg_modelset_fprintf(stdout, 1, modelset);
00514 class_quiet = seg_modelname2modelnum(modelset, "quiet");
00515 if (class_quiet < 0)
00516 DIE("Quiet class not found in modelset, check modelset.models[*]->name");
00517 Nclass = modelset->nclass;
00518 nrhs = MXT_Hseg_ARG_m1 + Nclass;
00519 if (nrhs > MXT_Hseg_NARGIN_MAX) {
00520
00521 fprintf(stderr, "Given modelset has %d classes, max is %d\n",
00522 Nclass, MXT_Hseg_NARGIN_MAX - MXT_Hseg_ARG_m1);
00523 DIE("Given modelset has too many classes, must recompile");
00524 }
00525
00526
00527 prhs[MXT_Hseg_ARG_edge] = mxCreateDoubleMatrix(1, 2, mxREAL);
00528 prhs[MXT_Hseg_ARG_iter] = mxt_param_to_matrix(params, kParIter, 1, -1);
00529 prhs[MXT_Hseg_ARG_T] = mxt_param_to_matrix(params, kParT, 1, -1);
00530 prhs[MXT_Hseg_ARG_beta] = mxt_param_to_scalar(params, kParBeta);
00531 prhs[MXT_Hseg_ARG_geom] = mxCreateDoubleMatrix(1, 5, mxREAL);
00532 prhs[MXT_Hseg_ARG_rho] = mxt_param_to_scalar(params, kParRho);
00533
00534 if (!prhs[MXT_Hseg_ARG_edge] ||
00535 !prhs[MXT_Hseg_ARG_iter] ||
00536 !prhs[MXT_Hseg_ARG_T] ||
00537 !prhs[MXT_Hseg_ARG_beta] ||
00538 !prhs[MXT_Hseg_ARG_geom] ||
00539 !prhs[MXT_Hseg_ARG_rho])
00540 DIE("failed to set up a miscellaneous parameter");
00541
00542 mxGetPr(prhs[MXT_Hseg_ARG_edge])[0] = edge_pix;
00543 mxGetPr(prhs[MXT_Hseg_ARG_edge])[1] = class_quiet+1;
00544
00545
00546 prhs[MXT_Hseg_ARG_alpha] = mxCreateDoubleMatrix(1, Nclass, mxREAL);
00547 if (!prhs[MXT_Hseg_ARG_alpha])
00548 DIE("failed to set up parameter alpha");
00549 memcpy(mxGetPr(prhs[MXT_Hseg_ARG_alpha]), modelset->alpha,
00550 Nclass*sizeof(double));
00551
00552
00553 for (class = 0; class < Nclass; class++) {
00554 m1 = &(modelset->models[class]);
00555 prhs[MXT_Hseg_ARG_m1 + class] = mxCreateDoubleMatrix(6, m1->k, mxREAL);
00556 if (!prhs[MXT_Hseg_ARG_m1 + class]) {
00557 fprintf(stderr, "Fatal: could not set up model %d (%d components, %s)\n",
00558 class, m1->k, m1->name);
00559 DIE("failed to set up a model parameter matrix");
00560 }
00561 memcpy(mxGetPr(prhs[MXT_Hseg_ARG_m1 + class]),
00562 m1->params, 6 * (m1->k) * sizeof(double));
00563 }
00564
00565
00566 if (0) {
00567 int k;
00568 for (class = 0; class < Nclass; class++) {
00569 double *p1 = mxGetPr(prhs[MXT_Hseg_ARG_m1+class]);
00570 for (k = 0; k < mxGetN(prhs[MXT_Hseg_ARG_m1+class]); k++)
00571 V_printf(verbflag > 2, NULL,
00572 "\tmod(%d)[%d][0:5] = %.3f %g,%g %g,%g,%g\n", class, k,
00573 p1[6*k], p1[6*k+1], p1[6*k+2], p1[6*k+3], p1[6*k+4], p1[6*k+5]);
00574 }
00575 }
00576
00577
00578 xmRD = drms_open_records(drms_env, (char *) xmRecQuery, &status);
00579 if (status || xmRD->n == 0)
00580 DIE("No mgram input data found");
00581 Nds = xmRD->n;
00582
00583
00584 xpRD = drms_open_records(drms_env, (char *) xpRecQuery, &status);
00585 if (status || xpRD->n == 0)
00586 DIE("No pgram input data found");
00587 if (xpRD->n != Nds)
00588 DIE("pgram series length does not match mgram series length");
00589
00590
00591 for (ds_good = ds = 0; ds < Nds; ds++) {
00592 V_printf(verbflag, "", "begin record %d of %d\n", ds+1, Nds);
00593
00594
00595 wt1 = getwalltime();
00596 ct1 = getcputime(&ut1, &st1);
00597
00598 xmRec = xmRD->records[ds];
00599 xpRec = xpRD->records[ds];
00600
00601
00602
00603
00604 t_rec = drms_getkey_time(xmRec, "T_REC", &status);
00605 if (status || drms_getkey_time(xpRec, "T_REC", &status) != t_rec) {
00606 WARN("mgram and pgram input record T_REC's don't match");
00607 continue;
00608 }
00609
00610 sprint_time(time_buf, t_rec, "TAI", 0);
00611 V_printf(verbflag, "\t", "processing images at T_REC = %s\n", time_buf);
00612
00613
00614 crvalx = drms_getkey_float(xmRec, "CRVAL1", &status);
00615 crvaly = drms_getkey_float(xmRec, "CRVAL2", &status);
00616 cdelt = drms_getkey_float(xmRec, "CDELT1", &status);
00617 crpix1 = drms_getkey_float(xmRec, "CRPIX1", &status);
00618 crpix2 = drms_getkey_float(xmRec, "CRPIX2", &status);
00619 crota2 = drms_getkey_float(xmRec, "CROTA2", &status);
00620 crlt = drms_getkey_float(xmRec, "CRLT_OBS", &status);
00621 if (status) {
00622 WARN("could not get WCS from mgram (missing image?). skipping");
00623 continue;
00624 }
00625 if (isnan(crota2) || isnan(crlt) ||
00626 isnan(crvalx) || isnan(cdelt) || isnan(crpix1)) {
00627 WARN("WCS from mgram had at least one NaN (missing image?). skipping");
00628 continue;
00629 }
00630
00631
00632 if (1 == 1) {
00633 float crvalxP, crvalyP, cdeltP, crpix1P, crpix2P, crota2P, crltP;
00634 const double THR = 1e-4;
00635
00636 crvalxP = drms_getkey_float(xpRec, "CRVAL1", &status);
00637 crvalyP = drms_getkey_float(xpRec, "CRVAL2", &status);
00638 cdeltP = drms_getkey_float(xpRec, "CDELT1", &status);
00639 crpix1P = drms_getkey_float(xpRec, "CRPIX1", &status);
00640 crpix2P = drms_getkey_float(xpRec, "CRPIX2", &status);
00641 crota2P = drms_getkey_float(xpRec, "CROTA2", &status);
00642 crltP = drms_getkey_float(xpRec, "CRLT_OBS", &status);
00643 if (status) {
00644 WARN("could not get WCS from pgram (missing image?). skipping");
00645 continue;
00646 }
00647 if (isnan(crota2P) || isnan(crltP) ||
00648 isnan(crvalxP) || isnan(cdeltP) || isnan(crpix1P)) {
00649 WARN("WCS from pgram had at least one NaN (missing image?). skipping");
00650 continue;
00651 }
00652 if (fabs(crvalxP - crvalx) > THR ||
00653 fabs(crvalyP - crvaly) > THR ||
00654 fabs(cdeltP - cdelt) > THR ||
00655 fabs(crpix1P - crpix1) > THR ||
00656 fabs(crpix2P - crpix2) > THR ||
00657 fabs(crota2P - crota2) > THR ||
00658 fabs(crltP - crlt) > THR) {
00659 WARN("WCS from pgram and mgram did not match. skipping");
00660 continue;
00661 }
00662 }
00663
00664
00665 sina = sin(crota2 * DTOR);
00666 cosa = cos(crota2 * DTOR);
00667 p0 = -crota2;
00668 beta = crlt;
00669 x0 = PIX_X(0.0,0.0) - 1.0;
00670 y0 = PIX_Y(0.0,0.0) - 1.0;
00671 rsun_ref = drms_getkey_double(xmRec, "RSUN_REF", &status);
00672 if (status) {
00673 rsun_ref = 6.96e8;
00674 status = 0;
00675 }
00676 dsun_obs = drms_getkey_double(xmRec, "DSUN_OBS", &status);
00677 if (status) {
00678 WARN("could not get DSUN_OBS from mgram. skipping");
00679 continue;
00680 }
00681 rSun = asin(rsun_ref / dsun_obs) * RAD2ARCSEC / cdelt;
00682 V_printf(verbflag > 1, NULL,
00683 "\t\tX0=%.3f, Y0=%.3f, RSUN=%.3f, P0=%.2f, beta=%.2f\n",
00684 x0, y0, rSun, p0, beta);
00685
00686 if (isnan(rSun) || isnan(x0) || isnan(y0) || isnan(p0) || isnan(beta)) {
00687 WARN("Computed disk parameters from mgram had at least one NaN. skipping");
00688 continue;
00689 }
00690
00691
00692
00693
00694
00695 xmSeg = drms_segment_lookupnum(xmRec, 0);
00696 if (!xmSeg) {
00697 WARN("problem looking up mgram. skipping");
00698 continue;
00699 }
00700
00701 xmArray = drms_segment_read(xmSeg, DRMS_TYPE_DOUBLE, &status);
00702 if (status) {
00703 drms_free_array(xmArray);
00704 WARN("problem reading mgram. skipping");
00705 continue;
00706 }
00707
00708 M = xmArray->axis[0]; N = xmArray->axis[1];
00709
00710
00711 xpSeg = drms_segment_lookupnum(xpRec, 0);
00712 if (!xpSeg) {
00713 drms_free_array(xmArray);
00714 WARN("problem looking up pgram. skipping");
00715 continue;
00716 }
00717 xpArray = drms_segment_read(xpSeg, DRMS_TYPE_DOUBLE, &status);
00718 if (status) {
00719 drms_free_array(xmArray);
00720 drms_free_array(xpArray);
00721 WARN("problem reading pgram. skipping");
00722 continue;
00723 }
00724
00725 if (xpArray->axis[0] != M || xpArray->axis[1] != N) {
00726 drms_free_array(xmArray);
00727 drms_free_array(xpArray);
00728 WARN("pgram and mgram dimensions don't match. skipping");
00729 continue;
00730 }
00731
00732
00733 V_printf(verbflag, "\t", "create_record\n");
00734 yRec = drms_create_record(drms_env, (char *) yRecQuery, DRMS_PERMANENT, &status);
00735 if (status) {
00736 drms_free_array(xmArray);
00737 drms_free_array(xpArray);
00738 WARN("Output recordset for labeling could not be created. skipping");
00739 continue;
00740 }
00741
00742
00743
00744
00745
00746 if ((prhs[MXT_Hseg_ARG_xm] = mxCreateDoubleMatrix(M, N, mxREAL)) == NULL)
00747 DIE("failed calloc for mgram");
00748 xm_tmp = mxGetPr(prhs[MXT_Hseg_ARG_xm]);
00749 mxSetPr(prhs[MXT_Hseg_ARG_xm], (double *) xmArray->data);
00750 if ((prhs[MXT_Hseg_ARG_xp] = mxCreateDoubleMatrix(M, N, mxREAL)) == NULL)
00751 DIE("failed calloc for pgram");
00752 xp_tmp = mxGetPr(prhs[MXT_Hseg_ARG_xp]);
00753 mxSetPr(prhs[MXT_Hseg_ARG_xp], (double *) xpArray->data);
00754
00755
00756
00757
00758 mxGetPr(prhs[MXT_Hseg_ARG_geom])[0] = x0+1;
00759 mxGetPr(prhs[MXT_Hseg_ARG_geom])[1] = y0+1;
00760 mxGetPr(prhs[MXT_Hseg_ARG_geom])[2] = rSun;
00761 mxGetPr(prhs[MXT_Hseg_ARG_geom])[3] = beta;
00762 mxGetPr(prhs[MXT_Hseg_ARG_geom])[4] = p0;
00763
00764
00765 V_printf(verbflag > 1, NULL,
00766 "\t\tM[%d,%d] = %f\n\t\tP[%d,%d] = %f\n",
00767 M/2, N/2, ((double *) xmArray->data)[M*N/2+M/2],
00768 M/2, N/2, ((double *) xpArray->data)[M*N/2+M/2]);
00769
00770
00771
00772
00773 V_printf(verbflag, "\t", "calling mexfunction `hmi_segment'.\n");
00774 fflush(stdout);
00775 msg = main_hmi_segment(nlhs, plhs, nrhs, prhs);
00776 if (msg == NULL) {
00777 V_printf(verbflag, "\t", "returned OK from mexfunction.\n");
00778 } else {
00779
00780 V_printf(1, "\t",
00781 "returned via error from mexfunction. Message: %s\n" , msg);
00782
00783 status = 1;
00784 DIE("mexFunction failed (mexErrMsgTxt)");
00785 }
00786
00787
00788 V_printf(verbflag > 1, "\t", "y[%d,%d] = %g\n",
00789 M/2, N/2, mxGetPr(plhs[MXT_Hseg_ARG_y])[M*N/2+M/2]);
00790
00791
00792 if (mxGetM(plhs[MXT_Hseg_ARG_s]) != Nclass) {
00793 snprintf(errmsg, sizeof(errmsg),
00794 "Modelset has %d classes, region stats have %d, %s",
00795 Nclass, (int) mxGetM(plhs[MXT_Hseg_ARG_s]),
00796 Nclass > mxGetM(plhs[MXT_Hseg_ARG_s]) ?
00797 "can very rarely happen" : "should NOT happen");
00798 WARN(errmsg);
00799 }
00800
00801
00802
00803
00804 mxSetPr(prhs[MXT_Hseg_ARG_xm], (double *) xm_tmp);
00805 mxSetPr(prhs[MXT_Hseg_ARG_xp], (double *) xp_tmp);
00806
00807 V_printf(verbflag > 1, "\t", "within-loop input-image frees\n");
00808 mxDestroyArray(prhs[MXT_Hseg_ARG_xm]);
00809 mxDestroyArray(prhs[MXT_Hseg_ARG_xp]);
00810
00811 drms_free_array(xmArray);
00812 drms_free_array(xpArray);
00813
00814
00815
00816
00817
00818 V_printf(verbflag, "\t", "looking up mask segment\n");
00819 ySeg = drms_segment_lookupnum(yRec, 0);
00820
00821
00822 yArray = mxArray2drms_array(plhs[MXT_Hseg_ARG_y], DRMS_TYPE_CHAR);
00823 if (!yArray)
00824 DIE("problem creating drms array for labeling");
00825 yArray->parent_segment = ySeg;
00826 V_printf(verbflag, "\t", "writing mask segment\n");
00827 status = drms_segment_write(ySeg, yArray, 0);
00828 if (status)
00829 DIE("problem writing drms segment for labeling");
00830
00831
00832
00833
00834 inst_mode = get_instrument_mode(xmRec);
00835
00836 status = setkey_mask_qual(yRec,
00837 (int) mxGetScalar(plhs[MXT_Hseg_ARG_nclean]),
00838 yArray->data, M, N);
00839 if (status > 0) {
00840 snprintf(errmsg, sizeof(errmsg),
00841 "Mask quality keyword insertion failed for %d keys", status);
00842 WARN(errmsg);
00843 }
00844
00845 status = setkey_mask_stats(yRec, mxGetPr(plhs[MXT_Hseg_ARG_s]), modelset);
00846 if (status > 0) {
00847 snprintf(errmsg, sizeof(errmsg),
00848 "Mask stats keyword insertion failed for %d keys", status);
00849 WARN(errmsg);
00850 } else if (status < 0) {
00851 WARN("Class with `active' not found. Failed to insert mask stats keys");
00852 }
00853
00854 status = propagate_keys_mag2mask(inst_mode, xmRec, yRec);
00855 if (status < 0) {
00856 WARN("Mag -> Mask key propagation failed, internal error, should not happen");
00857 } else if (status > 0) {
00858 snprintf(errmsg, sizeof(errmsg),
00859 "Mag -> Mask key propagation failed for %d keys", status);
00860 WARN(errmsg);
00861 }
00862
00863 status = propagate_keys_intensity2mask(inst_mode, xpRec, yRec);
00864 if (status < 0) {
00865 WARN("Ic -> Mask key propagation failed, internal error, should not happen");
00866 } else if (status > 0) {
00867 snprintf(errmsg, sizeof(errmsg),
00868 "Ic -> Mask key propagation failed for %d keys", status);
00869 WARN(errmsg);
00870 }
00871
00872 status = setkey_algorithm_params(yRec, modelName, prhs);
00873 if (status > 0) {
00874 snprintf(errmsg, sizeof(errmsg),
00875 "Algorithm keyword insertion failed for %d keys", status);
00876 WARN(errmsg);
00877 }
00878
00879 status = setkey_model_params(yRec, modelset);
00880 if (status > 0) {
00881 snprintf(errmsg, sizeof(errmsg),
00882 "Class model keyword insertion failed for %d keys", status);
00883 WARN(errmsg);
00884 }
00885
00886 status = setkey_code_info(inst_mode, yRec);
00887 if (status > 0) {
00888 snprintf(errmsg, sizeof(errmsg),
00889 "Code info keyword insertion failed for %d keys", status);
00890 WARN(errmsg);
00891 }
00892
00893 drms_copykey(yRec, xmRec, "T_REC");
00894
00895 drms_setkey_time(yRec, "DATE", CURRENT_SYSTEM_TIME);
00896 drms_setkey_string(yRec, "BLD_VERS", jsoc_version);
00897
00898
00899 if ((srcLink_M = hcon_lookup_lower(&yRec->links, "MDATA")) != NULL)
00900 status = drms_setlink_static(yRec, "MDATA", xmRec->recnum);
00901 if (!srcLink_M) WARN("MDATA link failed: bad lookup");
00902 if (status) WARN("MDATA link failed: bad setlink");
00903 if ((srcLink_P = hcon_lookup_lower(&yRec->links, "PDATA")) != NULL)
00904 status = drms_setlink_static(yRec, "PDATA", xpRec->recnum);
00905 if (!srcLink_P) WARN("PDATA link failed: bad lookup");
00906 if (status) WARN("PDATA link failed: bad setlink");
00907
00908
00909 V_printf(verbflag, "\t", "inserting mask record\n");
00910 drms_close_record(yRec, DRMS_INSERT_RECORD);
00911 ds_good++;
00912
00913
00914 V_printf(verbflag > 1, "\t", "within-loop result frees\n");
00915 mxDestroyArray(plhs[MXT_Hseg_ARG_y]);
00916 mxDestroyArray(plhs[MXT_Hseg_ARG_s]);
00917 mxDestroyArray(plhs[MXT_Hseg_ARG_post]);
00918 mxDestroyArray(plhs[MXT_Hseg_ARG_nclean]);
00919
00920 drms_free_array(yArray);
00921
00922
00923 wt = getwalltime();
00924 ct = getcputime(&ut, &st);
00925 V_printf(verbflag, "\t", "record %d time used: %.3f s wall, %.3f s cpu\n",
00926 ds+1, (wt - wt1)*1e-3, (ct - ct1)*1e-3);
00927 V_printf(verbflag, "\t", "record %d done.\n", ds+1);
00928 }
00929 V_printf(verbflag, "", "close records (mgram)\n");
00930 drms_close_records(xmRD, DRMS_FREE_RECORD);
00931 V_printf(verbflag, "", "close records (pgram)\n");
00932 drms_close_records(xpRD, DRMS_FREE_RECORD);
00933
00934
00935 V_printf(verbflag, "", "final destroy arrays\n");
00936 mxDestroyArray(prhs[MXT_Hseg_ARG_edge]);
00937 mxDestroyArray(prhs[MXT_Hseg_ARG_iter]);
00938 mxDestroyArray(prhs[MXT_Hseg_ARG_T]);
00939 mxDestroyArray(prhs[MXT_Hseg_ARG_beta]);
00940 mxDestroyArray(prhs[MXT_Hseg_ARG_alpha]);
00941 mxDestroyArray(prhs[MXT_Hseg_ARG_geom]);
00942 mxDestroyArray(prhs[MXT_Hseg_ARG_rho]);
00943 for (class = 0; class < Nclass; class++)
00944 mxDestroyArray(prhs[MXT_Hseg_ARG_m1 + class]);
00945
00946
00947 V_printf(verbflag, "", "successfully added %d of %d masks.\n", ds_good, Nds);
00948 if (ds_good < Nds)
00949 WARN("Some masks were not able to be computed from the input series");
00950
00951 wt = getwalltime();
00952 ct = getcputime(&ut, &st);
00953 V_printf(verbflag, "", "total time used: %.3f s wall, %.3f s cpu\n",
00954 (wt - wt0)*1e-3, (ct - ct0)*1e-3);
00955
00956
00957 return DRMS_SUCCESS;
00958 }
00959