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 #ifdef HAVE_CONFIG_H
00028 # include <config.h>
00029 #endif
00030
00031
00037
00040
00041
00042
00043 #include <xsh_data_instrument.h>
00044 #include <xsh_data_order.h>
00045 #include <xsh_data_spectralformat.h>
00046 #include <xsh_msg.h>
00047 #include <xsh_error.h>
00048 #include <string.h>
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00065
00066 xsh_instrument* xsh_instrument_new (void)
00067 {
00068 xsh_instrument* instrument = NULL;
00069 instrument = (xsh_instrument*)cpl_malloc(sizeof(xsh_instrument));
00070 assure (instrument != NULL, CPL_ERROR_ILLEGAL_OUTPUT,
00071 "Memory allocation failed!");
00072
00073 instrument->mode = XSH_MODE_UNDEFINED;
00074 instrument->arm = XSH_ARM_UNDEFINED;
00075 instrument->lamp = XSH_LAMP_UNDEFINED;
00076 instrument->config = NULL;
00077 instrument->pipeline_id = PACKAGE "/" PACKAGE_VERSION;
00078 instrument->dictionary = "PRO-1.15";
00079 instrument->recipe_id = NULL;
00080 instrument->update = 0;
00081 instrument->uvb_orders_nb = XSH_ORDERS_UVB;
00082 instrument->uvb_orders_qth_nb = XSH_ORDERS_UVB_QTH;
00083 instrument->uvb_orders_d2_nb = XSH_ORDERS_UVB_D2;
00084 instrument->uvb_orders_min = XSH_ORDER_MIN_UVB;
00085 instrument->uvb_orders_max = XSH_ORDER_MAX_UVB;
00086 instrument->vis_orders_nb = XSH_ORDERS_VIS;
00087 instrument->vis_orders_min = XSH_ORDER_MIN_VIS;
00088 instrument->vis_orders_max = XSH_ORDER_MAX_VIS;
00089 instrument->nir_orders_nb = XSH_ORDERS_NIR;
00090 instrument->nir_orders_min = XSH_ORDER_MIN_NIR;
00091 instrument->nir_orders_max = XSH_ORDER_MAX_NIR;
00092 instrument->binx = 1;
00093 instrument->biny = 1;
00094
00095 cleanup:
00096 return instrument;
00097 }
00098
00099 xsh_instrument * xsh_instrument_duplicate( xsh_instrument * old )
00100 {
00101 xsh_instrument * new = NULL ;
00102
00103 check( new = xsh_instrument_new() ) ;
00104
00105 memcpy( new, old, sizeof( xsh_instrument ) ) ;
00106 new->config = malloc( sizeof( XSH_INSTRCONFIG ) ) ;
00107 memcpy( new->config, old->config, sizeof( XSH_INSTRCONFIG ) ) ;
00108
00109 cleanup:
00110 return new ;
00111 }
00112
00113
00119
00120 void xsh_instrument_free(xsh_instrument** instrument){
00121 if(instrument && *instrument){
00122 if((*instrument)->config != NULL){
00123 cpl_free((*instrument)->config);
00124 (*instrument)->config = NULL;
00125 }
00126 cpl_free(*instrument);
00127 instrument = NULL;
00128 }
00129 }
00130
00131
00137
00138 XSH_ARM xsh_arm_get(const char* tag){
00139 return
00140 (strstr(tag,"UVB") != NULL)? XSH_ARM_UVB :
00141 (strstr(tag,"VIS") != NULL)? XSH_ARM_VIS :
00142 (strstr(tag,"NIR") != NULL)? XSH_ARM_NIR : XSH_ARM_UNDEFINED;
00143 }
00144
00145
00151
00152 XSH_MODE xsh_mode_get(const char* tag){
00153 return
00154 (strstr(tag,"IFU") != NULL)? XSH_MODE_IFU :
00155 (strstr(tag,"SLIT") != NULL)? XSH_MODE_SLIT : XSH_MODE_UNDEFINED;
00156 }
00157
00158
00165
00166 void
00167 xsh_mode_set(xsh_instrument* instrument, XSH_MODE mode){
00168 instrument->mode = mode;
00169 return;
00170 }
00171
00172
00178
00179 XSH_LAMP xsh_lamp_get(const char* tag){
00180 return
00181 (strstr(tag,"QTH") != NULL)? XSH_LAMP_QTH :
00182 (strstr(tag,"D2") != NULL)? XSH_LAMP_D2 :
00183 (strstr(tag,"THAR") != NULL)? XSH_LAMP_THAR : XSH_LAMP_UNDEFINED;
00184 }
00185
00186
00187
00193
00194 void xsh_instrument_parse_tag(xsh_instrument* inst,const char* tag){
00195 XSH_ARM arm = xsh_arm_get(tag);
00196 XSH_MODE mode = xsh_mode_get(tag);
00197 XSH_LAMP lamp = xsh_lamp_get(tag);
00198
00199 xsh_instrument_set_arm(inst,arm);
00200 xsh_instrument_set_mode(inst,mode);
00201 xsh_instrument_set_lamp(inst,lamp);
00202
00203 }
00204
00211
00212 void xsh_instrument_set_mode(xsh_instrument* i,XSH_MODE mode){
00213 if (mode != XSH_MODE_UNDEFINED){
00214 if ( (i->mode == XSH_MODE_UNDEFINED)|| (mode == i->mode) ){
00215 i->mode = mode;
00216 }
00217 else {
00218
00219
00220
00221
00222
00223
00224 }
00225 }
00226
00227 return;
00228 }
00229
00230
00237
00238 void xsh_instrument_set_arm(xsh_instrument* i,XSH_ARM arm){
00239 if (arm == XSH_ARM_UNDEFINED) {
00240
00241 assure(0,CPL_ERROR_ILLEGAL_INPUT,"arm must be UVB, VIS or NIR");
00242 }
00243 else {
00244 if( (i->arm == XSH_ARM_UNDEFINED) || (arm == i->arm) ){
00245 i->update = 1;
00246 i->arm = arm;
00247 }
00248 else {
00249
00250 assure(0,CPL_ERROR_ILLEGAL_INPUT,
00251 "Arm %s already set for the instrument; could'nt update with %s",
00252 xsh_instrument_arm_tostring(i),xsh_arm_tostring(arm));
00253 }
00254 }
00255 cleanup:
00256 return;
00257 }
00258
00259
00266
00267 void xsh_instrument_set_lamp(xsh_instrument* i,XSH_LAMP lamp){
00268 if (lamp != XSH_LAMP_UNDEFINED) {
00269 if( (i->lamp == XSH_LAMP_UNDEFINED) || (i->lamp == lamp) ){
00270 i->lamp = lamp;
00271 }
00272 else {
00273 if ( (i->arm == XSH_ARM_UVB) && ( ( lamp == XSH_LAMP_QTH)||
00274 ( lamp == XSH_LAMP_D2))){
00275 i->lamp = XSH_LAMP_QTH_D2;
00276 }
00277 else{
00278
00279 assure(0,CPL_ERROR_ILLEGAL_INPUT,
00280 "Lamp %s already set for the instrument; could not update with %s",
00281 xsh_instrument_lamp_tostring(i),xsh_lamp_tostring(lamp));
00282 }
00283 }
00284 }
00285 cleanup:
00286 return;
00287 }
00288
00289 void xsh_instrument_update_lamp(xsh_instrument* i, XSH_LAMP lamp)
00290 {
00291 XSH_ASSURE_NOT_NULL( i);
00292 i->lamp = lamp;
00293 i->update = 1;
00294
00295 cleanup:
00296 return;
00297 }
00298
00299 void xsh_instrument_update_from_spectralformat( xsh_instrument* i,
00300 cpl_frame* spectralformat_frame)
00301 {
00302 xsh_spectralformat_list *spec_list = NULL;
00303 int max_order, min_order;
00304 int nb_qth, nb_d2, nb_total;
00305 int j;
00306
00307
00308 XSH_ASSURE_NOT_NULL( i);
00309
00310 if (spectralformat_frame != NULL){
00311 check( spec_list = xsh_spectralformat_list_load( spectralformat_frame,
00312 i));
00313
00314 nb_total = spec_list->size;
00315 nb_qth = 0;
00316 nb_d2 = 0;
00317 XSH_ASSURE_NOT_ILLEGAL( nb_total > 0);
00318
00319 max_order = spec_list->list[0].absorder;
00320 min_order = spec_list->list[0].absorder;
00321
00322 for(j=0; j< spec_list->size; j++){
00323 int absorder;
00324 const char* lamp = NULL;
00325
00326 absorder= spec_list->list[j].absorder;
00327 lamp = spec_list->list[j].lamp;
00328
00329 if ( absorder > max_order){
00330 max_order = absorder;
00331 }
00332 if ( absorder < min_order ){
00333 min_order = absorder;
00334 }
00335 if (lamp != NULL){
00336 if ( strcmp(lamp,"QTH")== 0){
00337 nb_qth++;
00338 }
00339 else if ( strcmp(lamp,"D2") == 0){
00340 nb_d2++;
00341 }
00342 }
00343 }
00344 assure(i->arm != XSH_ARM_UNDEFINED,CPL_ERROR_ILLEGAL_INPUT,
00345 "config is defined only for valid arm");
00346 switch (i->arm){
00347 case XSH_ARM_UVB:
00348 i->uvb_orders_nb = nb_total ;
00349 i->uvb_orders_qth_nb = nb_qth;
00350 i->uvb_orders_d2_nb = nb_d2;
00351 i->uvb_orders_min = min_order;
00352 i->uvb_orders_max = max_order;
00353 break;
00354 case XSH_ARM_VIS:
00355 i->vis_orders_nb = nb_total;
00356 i->vis_orders_min = min_order;
00357 i->vis_orders_max = max_order;
00358 break;
00359 case XSH_ARM_NIR:
00360 i->nir_orders_nb = nb_total;
00361 i->nir_orders_min = min_order;
00362 i->nir_orders_max = max_order;
00363 break;
00364 default:
00365 break;
00366 }
00367 i->update = 1;
00368 xsh_msg_dbg_low("Orders config updated for arm %s", xsh_arm_tostring( i->arm));
00369 xsh_msg_dbg_low(" Nb orders %d (qth %d, d2 %d) : from %d to %d",
00370 nb_total, nb_qth, nb_d2, min_order, max_order);
00371 }
00372 else{
00373 xsh_msg(" No spectralformat : Get default config");
00374 }
00375
00376 cleanup:
00377 xsh_spectralformat_list_free( &spec_list);
00378 return;
00379 }
00380
00381
00387
00388 void xsh_instrument_set_recipe_id(xsh_instrument* instrument,
00389 const char *recipe_id)
00390 {
00391 if (recipe_id != NULL) {
00392 instrument->recipe_id = recipe_id;
00393 }
00394 else {
00395
00396 instrument->recipe_id = "unknown";
00397 }
00398
00399 return;
00400 }
00401
00402
00407
00408 XSH_MODE xsh_instrument_get_mode(xsh_instrument* i){
00409 return i->mode;
00410 }
00411
00412
00417
00418 XSH_ARM xsh_instrument_get_arm(xsh_instrument* i){
00419 return i->arm;
00420 }
00421
00422
00428
00429 XSH_LAMP xsh_instrument_get_lamp(xsh_instrument* i){
00430 return i->lamp;
00431 }
00432
00433
00439
00440 double xsh_arcsec_get(xsh_instrument * instrument )
00441 {
00442 return
00443 ( instrument->arm == XSH_ARM_NIR) ? XSH_ARCSEC_NIR :
00444 ( instrument->arm == XSH_ARM_UVB) ? XSH_ARCSEC_UVB :
00445 ( instrument->arm == XSH_ARM_VIS) ? XSH_ARCSEC_VIS : 0. ;
00446 }
00447
00448
00449
00457
00458 double xsh_resolution_get( xsh_instrument *instrument, double slit)
00459 {
00460 double resolution = 0.0;
00461
00462 if ( (instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.5)){
00463 resolution = 9100;
00464 }
00465 else if ((instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.8)){
00466 resolution = 6200;
00467 }
00468 else if ((instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.0)){
00469 resolution = 5100;
00470 }
00471 else if ((instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.3)){
00472 resolution = 4000;
00473 }
00474 else if ((instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.6)){
00475 resolution = 3300;
00476 }
00477 else if ((instrument->arm == XSH_ARM_UVB) && (instrument->mode = XSH_MODE_IFU)){
00478 resolution = 7900;
00479 }
00480 else if ( (instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.4)){
00481 resolution = 17400;
00482 }
00483 else if ((instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.7)){
00484 resolution = 11000;
00485 }
00486 else if ((instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.9)){
00487 resolution = 8800;
00488 }
00489 else if ((instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.2)){
00490 resolution = 6700;
00491 }
00492 else if ((instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.5)){
00493 resolution = 5400;
00494 }
00495 else if ((instrument->arm == XSH_ARM_VIS) && (instrument->mode = XSH_MODE_IFU)){
00496 resolution = 12600;
00497 }
00498 if ( (instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.4)){
00499 resolution = 11300;
00500 }
00501 else if ((instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.6)){
00502 resolution = 8100;
00503 }
00504 else if ((instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 0.9)){
00505 resolution = 5600;
00506 }
00507 else if ((instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.2)){
00508 resolution = 4300;
00509 }
00510 else if ((instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_SLIT) && ( slit == 1.5)){
00511 resolution = 3500;
00512 }
00513 else if ((instrument->arm == XSH_ARM_NIR) && (instrument->mode = XSH_MODE_IFU)){
00514 resolution = 8100;
00515 }
00516 else{
00517 resolution = 0.0;
00518 }
00519 return resolution;
00520 }
00521
00522
00528
00529 XSH_INSTRCONFIG * xsh_instrument_get_config(xsh_instrument * i)
00530 {
00531 assure(i->arm != XSH_ARM_UNDEFINED,CPL_ERROR_ILLEGAL_INPUT,
00532 "config is defined only for valid arm");
00533
00534 if ( (i->config != NULL) && (i->update == 1)) {
00535 XSH_FREE( i->config);
00536 i->update = 0;
00537 }
00538 if (i->config == NULL){
00539 i->update=0;
00540 XSH_MALLOC( i->config, XSH_INSTRCONFIG, 1);
00541
00542
00543 i->config->naxis = 2;
00544
00545 switch (i->arm){
00546 case XSH_ARM_UVB:
00547 i->config->bitpix = 16;
00548 i->config->nx = 2048;
00549 i->config->ny = 3000;
00550 i->config->prscx = 0;
00551 i->config->prscy = 0;
00552 i->config->ovscx = 0;
00553 i->config->ovscy = 0;
00554 i->config->ron = 9.0;
00555 i->config->conad = 1.9;
00556 if (i->lamp == XSH_LAMP_D2){
00557 i->config->orders = i->uvb_orders_d2_nb;
00558 }
00559 else if (i->lamp == XSH_LAMP_QTH){
00560 i->config->orders = i->uvb_orders_qth_nb;
00561 }
00562 else{
00563 i->config->orders = i->uvb_orders_nb;
00564 }
00565 i->config->order_min = i->uvb_orders_min;
00566 i->config->order_max = i->uvb_orders_max ;
00567 break;
00568 case XSH_ARM_VIS:
00569 i->config->bitpix = 16;
00570 i->config->nx = 2048;
00571 i->config->ny = 4000;
00572 i->config->prscx = 0;
00573 i->config->prscy = 0;
00574 i->config->ovscx = 0;
00575 i->config->ovscy = 0;
00576 i->config->ron = 0.6;
00577 i->config->conad = 1.9;
00578 i->config->orders = i->vis_orders_nb;
00579 i->config->order_min = i->vis_orders_min;
00580 i->config->order_max = i->vis_orders_max;
00581 break;
00582 default:
00583 i->config->bitpix = 32;
00584 i->config->nx = 1020;
00585 i->config->ny = 2040;
00586 i->config->prscx = 0;
00587 i->config->prscy = 0;
00588 i->config->ovscx = 0;
00589 i->config->ovscy = 0;
00590 i->config->ron = 0.6;
00591 i->config->conad = 1.9;
00592 i->config->pxspace = 1.8E-05 ;
00593 i->config->orders = i->nir_orders_nb;
00594 i->config->order_min = i->nir_orders_min;
00595 i->config->order_max = i->nir_orders_max;
00596 break;
00597 }
00598 i->config->naxis1 = (i->config->nx + i->config->prscx + i->config->ovscx)
00599 / i->binx;
00600 i->config->naxis2 = (i->config->ny + i->config->prscy + i->config->ovscy)
00601 / i->biny;
00602 }
00603 cleanup:
00604 return i->config;
00605
00606 }
00607
00608 int xsh_instrument_get_binx( xsh_instrument * instrument )
00609 {
00610 int res = 1 ;
00611
00612 XSH_ASSURE_NOT_NULL( instrument ) ;
00613 res = instrument->binx ;
00614
00615 cleanup:
00616 return res ;
00617 }
00618
00619 int xsh_instrument_get_biny( xsh_instrument * instrument )
00620 {
00621 int res = 1 ;
00622
00623 XSH_ASSURE_NOT_NULL( instrument ) ;
00624 res = instrument->biny ;
00625
00626 cleanup:
00627 return res ;
00628 }
00629
00630 void xsh_instrument_set_binx( xsh_instrument * instrument, const int binx )
00631 {
00632
00633 XSH_ASSURE_NOT_NULL( instrument ) ;
00634 instrument->binx = binx;
00635
00636 cleanup:
00637 return ;
00638 }
00639
00640 void xsh_instrument_set_biny( xsh_instrument * instrument, const int biny )
00641 {
00642
00643 XSH_ASSURE_NOT_NULL( instrument ) ;
00644 instrument->biny = biny;
00645
00646 cleanup:
00647 return ;
00648 }
00649
00650
00656
00657 const char* xsh_instrument_mode_tostring(xsh_instrument* i){
00658 return xsh_mode_tostring(i->mode);
00659 }
00660
00661
00667
00668 const char* xsh_instrument_arm_tostring(xsh_instrument* i){
00669 return xsh_arm_tostring(i->arm);
00670 }
00671
00672
00678
00679 const char* xsh_instrument_lamp_tostring(xsh_instrument* i){
00680 return xsh_lamp_tostring(i->lamp);
00681 }
00682
00683
00684
00690
00691 const char* xsh_mode_tostring(XSH_MODE mode){
00692 return
00693 (mode == XSH_MODE_IFU) ? "IFU" :
00694 (mode == XSH_MODE_SLIT) ? "SLIT" : "UNDEFINED";
00695 }
00696
00697
00703
00704 const char* xsh_arm_tostring(XSH_ARM arm){
00705 return
00706 (arm == XSH_ARM_UVB) ? "UVB" :
00707 (arm == XSH_ARM_VIS) ? "VIS" :
00708 (arm == XSH_ARM_NIR) ? "NIR" : "UNDEFINED";
00709 }
00710
00711
00717
00718 const char* xsh_lamp_tostring(XSH_LAMP lamp){
00719 return
00720 (lamp == XSH_LAMP_QTH) ? "QTH" :
00721 (lamp == XSH_LAMP_D2) ? "D2" :
00722 (lamp == XSH_LAMP_THAR) ? "THAR" : "UNDEFINED";
00723 }
00724