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
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086 #define SKYMETRICTESTC_ENORM 0
00087 #define SKYMETRICTESTC_ESUB 1
00088 #define SKYMETRICTESTC_EARG 2
00089 #define SKYMETRICTESTC_EVAL 3
00090 #define SKYMETRICTESTC_EMEM 4
00091 #define SKYMETRICTESTC_ERNG 5
00092 #define SKYMETRICTESTC_EFILE 6
00093
00094 #define SKYMETRICTESTC_MSGENORM "Normal exit"
00095 #define SKYMETRICTESTC_MSGESUB "Subroutine failed"
00096 #define SKYMETRICTESTC_MSGEARG "Error parsing arguments"
00097 #define SKYMETRICTESTC_MSGEVAL "Input argument out of valid range"
00098 #define SKYMETRICTESTC_MSGEMEM "Memory allocation error"
00099 #define SKYMETRICTESTC_MSGERNG "Could not find area with valid metric"
00100 #define SKYMETRICTESTC_MSGEFILE "Could not open file"
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165 #include <math.h>
00166 #include <stdlib.h>
00167 #include <lal/LALStdlib.h>
00168 #include <lal/LALStdio.h>
00169 #include <lal/LALConstants.h>
00170 #include <lal/AVFactories.h>
00171 #include <lal/Grid.h>
00172 #include <lal/StreamOutput.h>
00173 #include <lal/StackMetric.h>
00174 #include <lal/PulsarTimes.h>
00175
00176 NRCSID( SKYMETRICTESTC, "$Id: SkyMetricTest.c,v 1.3 2007/06/08 14:41:52 bema Exp $" );
00177
00178
00179 int lalDebugLevel = 0;
00180 #define NSTACKS 1
00181 #define STACKLENGTH 86400.0
00182 #define STARTTIME 0.0
00183 #define LATITUDE 52.247
00184 #define LONGITUDE 9.822
00185 #define FREQUENCY 1000.0
00186 #define RA_MIN 188.8594813
00187 #define RA_MAX 196.8594813
00188 #define DEC_MIN 23.1282511
00189 #define DEC_MAX 31.1282511
00190 #define MISMATCH 0.25
00191
00192
00193 #define USAGE "Usage: %s [-o metricfile rangefile] [-p n dt t0 f0]\n" \
00194 "\t[-l lat lon] [-r ra1 ra2 dec1 dec2] [-d debuglevel]\n"
00195
00196
00197 #define NMAX 10000
00198 #define DTMAX 3e10
00199 #define F0MAX 1e4
00200
00201
00202
00203
00204
00205 #define SPACING 5.0
00206 #define MSGLEN 1024
00207
00208
00209
00210 #define ERROR( code, msg, statement ) \
00211 do \
00212 if ( lalDebugLevel & LALERROR ) \
00213 { \
00214 LALPrintError( "Error[0] %d: program %s, file %s, line %d, %s\n" \
00215 " %s %s\n", (code), *argv, __FILE__, \
00216 __LINE__, SKYMETRICTESTC, statement ? statement : \
00217 "", (msg) ); \
00218 } \
00219 while (0)
00220
00221 #define WARNING( statement ) \
00222 do \
00223 if ( lalDebugLevel & LALWARNING ) \
00224 { \
00225 LALPrintError( "Warning[0]: program %s, file %s, line %d, %s\n" \
00226 " %s\n", *argv, __FILE__, __LINE__, \
00227 SKYMETRICTESTC, (statement) ); \
00228 } \
00229 while (0)
00230
00231 #define INFO( statement ) \
00232 do \
00233 if ( lalDebugLevel & LALINFO ) \
00234 { \
00235 LALPrintError( "Info[0]: program %s, file %s, line %d, %s\n" \
00236 " %s\n", *argv, __FILE__, __LINE__, \
00237 SKYMETRICTESTC, (statement) ); \
00238 } \
00239 while (0)
00240
00241 #define SUB( func, statusptr ) \
00242 do \
00243 if ( (func), (statusptr)->statusCode ) \
00244 { \
00245 ERROR( SKYMETRICTESTC_ESUB, SKYMETRICTESTC_MSGESUB, \
00246 "Function call \"" #func "\" failed:" ); \
00247 return SKYMETRICTESTC_ESUB; \
00248 } \
00249 while (0)
00250
00251 #define CHECKVAL( val, lower, upper ) \
00252 do \
00253 if ( ( (val) <= (lower) ) || ( (val) > (upper) ) ) \
00254 { \
00255 ERROR( SKYMETRICTESTC_EVAL, SKYMETRICTESTC_MSGESUB, \
00256 "Value of " #val " out of range:" ); \
00257 LALPrintError( #val " = %f, range = (%f,%f]\n", (REAL8)(val), \
00258 (REAL8)(lower), (REAL8)(upper) ); \
00259 return SKYMETRICTESTC_EVAL; \
00260 } \
00261 while (0)
00262
00263
00264 #ifndef NDEBUG
00265 char *lalWatch;
00266 #endif
00267
00268 int
00269 main(int argc, char **argv)
00270 {
00271
00272 INT4 arg;
00273 CHAR *metricfile = NULL;
00274 CHAR *rangefile = NULL;
00275 UINT4 n = NSTACKS;
00276 REAL8 dt = STACKLENGTH;
00277 REAL8 t0 = STARTTIME;
00278 REAL8 f0 = FREQUENCY;
00279 REAL8 lat = LATITUDE;
00280 REAL8 lon = LONGITUDE;
00281 REAL8 ra[2], dec[2];
00282
00283
00284 UINT4 i, j, k;
00285 UINT4 nRA, nDec;
00286 REAL8 dRA, dDec;
00287 UINT4 warnings = 0;
00288 UINT4 errors = 0;
00289 static LALStatus stat;
00290 static LIGOTimeGPS start;
00291 REAL4Grid *metricGrid = NULL;
00292 REAL4 *gData;
00293 REAL4Grid *rangeGrid = NULL;
00294 REAL4 *rData;
00295 REAL4 propVol = 0.0;
00296 UINT4 nVol = 0;
00297 UINT4Vector *dimLength = NULL;
00298 REAL8Vector *lambda = NULL;
00299 REAL8Vector *metric = NULL;
00300 REAL8 *mData;
00301 INT4 *topRange, *botRange;
00302 INT4 *topRange2, *botRange2;
00303 static MetricParamStruc params;
00304 static PulsarTimesParamStruc baryParams;
00305
00306
00307 ra[0] = RA_MIN; dec[0] = DEC_MIN;
00308 ra[1] = RA_MAX; dec[1] = DEC_MAX;
00309
00310
00311
00312
00313
00314
00315 arg = 1;
00316 while ( arg < argc ) {
00317
00318 if ( !strcmp( argv[arg], "-o" ) ) {
00319 if ( argc > arg + 2 ) {
00320 arg++;
00321 metricfile = argv[arg++];
00322 rangefile = argv[arg++];
00323 } else {
00324 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00325 LALPrintError( USAGE, *argv );
00326 return SKYMETRICTESTC_EARG;
00327 }
00328 }
00329
00330 else if ( !strcmp( argv[arg], "-p" ) ) {
00331 if ( argc > arg + 4 ) {
00332 arg++;
00333 n = atoi( argv[arg++] );
00334 dt = atof( argv[arg++] );
00335 t0 = atof( argv[arg++] );
00336 f0 = atof( argv[arg++] );
00337 } else {
00338 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00339 LALPrintError( USAGE, *argv );
00340 return SKYMETRICTESTC_EARG;
00341 }
00342 }
00343
00344 else if ( !strcmp( argv[arg], "-l" ) ) {
00345 if ( argc > arg + 2 ) {
00346 arg++;
00347 lat = atof( argv[arg++] );
00348 lon = atof( argv[arg++] );
00349 } else {
00350 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00351 LALPrintError( USAGE, *argv );
00352 return SKYMETRICTESTC_EARG;
00353 }
00354 }
00355
00356 else if ( !strcmp( argv[arg], "-r" ) ) {
00357 if ( argc > arg + 4 ) {
00358 arg++;
00359 ra[0] = atof( argv[arg++] );
00360 ra[1] = atof( argv[arg++] );
00361 dec[0] = atof( argv[arg++] );
00362 dec[1] = atof( argv[arg++] );
00363 } else {
00364 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00365 LALPrintError( USAGE, *argv );
00366 return SKYMETRICTESTC_EARG;
00367 }
00368 }
00369
00370 else if ( !strcmp( argv[arg], "-d" ) ) {
00371 if ( argc > arg + 1 ) {
00372 arg++;
00373 lalDebugLevel = atoi( argv[arg++] );
00374 } else {
00375 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00376 LALPrintError( USAGE, *argv );
00377 return SKYMETRICTESTC_EARG;
00378 }
00379 }
00380
00381 else if ( argv[arg][0] == '-' ) {
00382 ERROR( SKYMETRICTESTC_EARG, SKYMETRICTESTC_MSGEARG, 0 );
00383 LALPrintError( USAGE, *argv );
00384 return SKYMETRICTESTC_EARG;
00385 }
00386 }
00387
00388
00389 if ( lalDebugLevel & LALERROR ) {
00390 CHECKVAL( n, 0, NMAX );
00391 CHECKVAL( f0, 0.0, F0MAX );
00392 CHECKVAL( dt, 1.0/f0, DTMAX );
00393 CHECKVAL( lat, -90.0, 90.0 );
00394 CHECKVAL( lon, -360.0, 360.0 );
00395 }
00396
00397
00398
00399
00400
00401
00402 start.gpsSeconds = (INT4)t0;
00403 start.gpsNanoSeconds = (INT4)( 1.0e9*( t0 - start.gpsSeconds ) );
00404 t0 = 0.0;
00405
00406
00407 baryParams.epoch = start;
00408 baryParams.latitude = LAL_PI_180*lat;
00409 baryParams.longitude = LAL_PI_180*lon;
00410 SUB( LALGetEarthTimes( &stat, &baryParams ), &stat );
00411
00412
00413 params.dtCanon = LALDTBaryPtolemaic;
00414 params.constants = &baryParams;
00415 params.start = t0;
00416 params.deltaT = dt;
00417 params.n = n;
00418 params.errors = 1;
00419
00420
00421 if ( params.errors )
00422 SUB( LALDCreateVector( &stat, &metric, 12 ), &stat );
00423 else
00424 SUB( LALDCreateVector( &stat, &metric, 6 ), &stat );
00425 mData = metric->data;
00426 SUB( LALU4CreateVector( &stat, &dimLength, 3 ), &stat );
00427 nRA = (UINT4)( ( ra[1] - ra[0] )/SPACING ) + 2;
00428 nDec = (UINT4)( ( dec[1] - dec[0] )/SPACING ) + 2;
00429 dimLength->data[0] = nDec;
00430 dimLength->data[1] = nRA;
00431 dimLength->data[2] = 3;
00432 SUB( LALSCreateGrid( &stat, &metricGrid, dimLength, 2 ), &stat );
00433 SUB( LALU4DestroyVector( &stat, &dimLength ), &stat );
00434 metricGrid->offset->data[0] = dec[0];
00435 metricGrid->offset->data[1] = ra[0];
00436 metricGrid->interval->data[0] = dDec = ( dec[1] - dec[0] )/( nDec - 1.0 );
00437 metricGrid->interval->data[1] = dRA = ( ra[1] - ra[0] )/( nRA - 1.0 );
00438 gData = metricGrid->data->data;
00439 SUB( LALDCreateVector( &stat, &lambda, 3 ), &stat );
00440 lambda->data[0] = f0;
00441
00442
00443 topRange = (INT4 *)LALMalloc( nRA*sizeof( INT4 ) );
00444 botRange = (INT4 *)LALMalloc( nRA*sizeof( INT4 ) );
00445 if ( !topRange || !botRange ) {
00446 ERROR( SKYMETRICTESTC_EMEM, SKYMETRICTESTC_MSGEMEM, 0 );
00447 return SKYMETRICTESTC_EMEM;
00448 }
00449 for ( i = 0; i < nRA; i++ ) {
00450 topRange[i] = 0;
00451 botRange[i] = nRA;
00452 }
00453
00454
00455 k = 0;
00456 fprintf( stdout, "Computing metric on %ix%i grid:\n", nDec, nRA );
00457 for ( i = 0; i < nDec; i++ ) {
00458 BOOLEAN bottom = 1, top = 0;
00459
00460 lambda->data[2] = LAL_PI_180*( dec[0] + i*dDec );
00461 for ( j = 0; j < nRA; j++ ) {
00462 if ( top )
00463 fprintf( stdout, "o" );
00464 else {
00465 REAL4 gxx, gyy, gxy;
00466 lambda->data[1] = LAL_PI_180*( ra[0] + j*dRA );
00467 SUB( LALStackMetric( &stat, metric, lambda, ¶ms ), &stat );
00468 SUB( LALProjectMetric( &stat, metric, params.errors ), &stat );
00469
00470
00471 if ( params.errors ) {
00472 INT2 sign = 1;
00473 gxx = mData[10] + mData[11];
00474 gyy = mData[4] + mData[5];
00475 gxy = mData[8];
00476 if ( gxy < 0.0 )
00477 sign = -1;
00478 if ( fabs( gxy ) <= fabs( mData[9] ) )
00479 gxy = 0.0;
00480 else
00481 gxy = sign*( fabs( gxy ) - fabs( mData[9] ) );
00482 if ( gxx < 0.0 || gyy < 0.0 || gxx*gyy - gxy*gxy < 0.0 ) {
00483 errors++;
00484 fprintf( stdout, "o" );
00485 } else if ( fabs( mData[4]*mData[11] ) +
00486 fabs( mData[5]*mData[10] ) +
00487 fabs( mData[8]*mData[9] )*2.0 >=
00488 mData[4]*mData[10] - mData[8]*mData[8] ) {
00489 warnings++;
00490 fprintf( stdout, "*" );
00491 } else
00492 fprintf( stdout, "+" );
00493 }
00494
00495
00496 else {
00497 gxx = mData[5];
00498 gxy = mData[4];
00499 gyy = mData[2];
00500 if ( gxx < 0.0 || gyy < 0.0 || gxx*gyy - gxy*gxy < 0.0 ) {
00501 errors++;
00502 fprintf( stdout, "o" );
00503 } else
00504 fprintf( stdout, "+" );
00505 }
00506
00507
00508 if ( gxx > 0.0 && gyy > 0.0 && gxx*gyy - gxy*gxy > 0.0 ) {
00509 if ( bottom ) {
00510 bottom = 0;
00511 botRange[i] = j - 1;
00512 }
00513 propVol += LAL_PI_180*LAL_PI_180*sqrt( gxx*gyy - gxy*gxy );
00514 nVol++;
00515 } else {
00516 if ( !bottom ) {
00517 top = 1;
00518 topRange[i] = j;
00519 }
00520 }
00521 *(gData++) = LAL_PI_180*LAL_PI_180*gxx;
00522 *(gData++) = LAL_PI_180*LAL_PI_180*gyy;
00523 *(gData++) = LAL_PI_180*LAL_PI_180*gxy;
00524 }
00525 fflush( stdout );
00526 }
00527 if ( !top )
00528 topRange[i] = j;
00529 fprintf( stdout, "\n" );
00530 }
00531
00532
00533 SUB( LALDDestroyVector( &stat, &metric ), &stat );
00534 SUB( LALDDestroyVector( &stat, &lambda ), &stat );
00535
00536
00537 if ( errors ) {
00538 CHAR msg[MSGLEN];
00539 LALSnprintf( msg, MSGLEN, "%i of %i points had"
00540 " non-positive-definite metric", warnings,
00541 nRA*nDec );
00542 WARNING( msg );
00543 }
00544 if ( warnings ) {
00545 CHAR msg[MSGLEN];
00546 LALSnprintf( msg, MSGLEN, "%i of %i points had metric component"
00547 " errors larger than values", warnings, nRA*nDec );
00548 WARNING( msg );
00549 }
00550
00551
00552 fprintf( stdout, "Average proper volume element: %10.3e per square"
00553 " degree\n", propVol /= nVol );
00554
00555
00556
00557
00558
00559
00560
00561
00562 topRange2 = (INT4 *)LALMalloc( nDec*sizeof(INT4) );
00563 botRange2 = (INT4 *)LALMalloc( nDec*sizeof(INT4) );
00564 if ( !topRange2 || !botRange2 ) {
00565 ERROR( SKYMETRICTESTC_EMEM, SKYMETRICTESTC_MSGEMEM, 0 );
00566 return SKYMETRICTESTC_EMEM;
00567 }
00568 topRange2[0] = topRange[1] < topRange[0] ?
00569 topRange[1] - 1 : topRange[0] - 1;
00570 botRange2[0] = botRange[1] > botRange[0] ?
00571 botRange[1] + 1 : botRange[0] + 1;
00572 topRange2[nDec-1] = topRange[nDec] < topRange[nDec-1] ?
00573 topRange[nDec] - 1 : topRange[nDec-1] - 1;
00574 botRange2[nDec-1] = botRange[nDec] > botRange[nDec-1] ?
00575 botRange[nDec] + 1 : botRange[nDec-1] + 1;
00576 for ( i = 1; i < nDec - 1; i++ ) {
00577 INT4 topMin = topRange[i-1], botMax = botRange[i-1];
00578 if ( topRange[i] < topMin )
00579 topMin = topRange[i];
00580 if ( topRange[i+1] < topMin )
00581 topMin = topRange[i+1];
00582 if ( botRange[i] > botMax )
00583 botMax = botRange[i];
00584 if ( botRange[i+1] > botMax )
00585 botMax = botRange[i+1];
00586 topRange2[i] = topMin - 1;
00587 botRange2[i] = botMax + 1;
00588 }
00589 LALFree( topRange );
00590 LALFree( botRange );
00591
00592
00593 if ( topRange2[0] > botRange2[0] && topRange2[1] > botRange2[1] )
00594 i = 0;
00595 else {
00596 i = 1;
00597 while ( i < nDec - 1 && topRange2[i] <= botRange2[i] &&
00598 topRange2[i+1] <= botRange2[i+1] )
00599 i++;
00600 }
00601 j = i;
00602 while ( j < nDec - 1 && topRange2[j+1] > botRange2[j+1] )
00603 j++;
00604 if ( j == i ) {
00605 ERROR( SKYMETRICTESTC_ERNG, SKYMETRICTESTC_MSGERNG, 0 );
00606 return SKYMETRICTESTC_ERNG;
00607 }
00608
00609
00610 j = j - i + 1;
00611 SUB( LALU4CreateVector( &stat, &dimLength, 2 ), &stat );
00612 dimLength->data[0] = j;
00613 dimLength->data[1] = 2;
00614 SUB( LALSCreateGrid( &stat, &rangeGrid, dimLength, 1 ), &stat );
00615 SUB( LALU4DestroyVector( &stat, &dimLength ), &stat );
00616 rangeGrid->offset->data[0] = dec[0] + i*dDec;
00617 rangeGrid->interval->data[0] = dDec;
00618 rData = rangeGrid->data->data;
00619 nVol = 0;
00620 for ( k = 0; k < j; k++ ) {
00621 *(rData++) = ra[0] + botRange2[k]*dRA;
00622 *(rData++) = ra[0] + topRange2[k]*dRA;
00623 nVol += topRange2[k] - botRange2[k] - 1;
00624 }
00625 nVol -= topRange2[j-1] - botRange2[j-1] - 1;
00626 LALFree( topRange2 );
00627 LALFree( botRange2 );
00628
00629
00630 fprintf( stdout, "Total proper volume: %10.3e\n",
00631 propVol*nVol*dRA*dDec );
00632
00633
00634
00635
00636
00637
00638 if ( metricfile ) {
00639 FILE *fp = fopen( metricfile, "w" );
00640 if ( !fp ) {
00641 ERROR( SKYMETRICTESTC_EFILE, "- " SKYMETRICTESTC_MSGEFILE,
00642 metricfile );
00643 return SKYMETRICTESTC_EFILE;
00644 }
00645 SUB( LALSWriteGrid( &stat, fp, metricGrid ), &stat );
00646 fclose( fp );
00647 }
00648 if ( rangefile ) {
00649 FILE *fp = fopen( rangefile, "w" );
00650 if ( !fp ) {
00651 ERROR( SKYMETRICTESTC_EFILE, "- " SKYMETRICTESTC_MSGEFILE,
00652 rangefile );
00653 return SKYMETRICTESTC_EFILE;
00654 }
00655 SUB( LALSWriteGrid( &stat, fp, rangeGrid ), &stat );
00656 fclose( fp );
00657 }
00658
00659
00660 SUB( LALSDestroyGrid( &stat, &metricGrid ), &stat );
00661 SUB( LALSDestroyGrid( &stat, &rangeGrid ), &stat );
00662 LALCheckMemoryLeaks();
00663 INFO( SKYMETRICTESTC_MSGENORM );
00664 return SKYMETRICTESTC_ENORM;
00665 }