WCSLIB  4.25.1
lin.h
Go to the documentation of this file.
1 /*============================================================================
2 
3  WCSLIB 5.0 - an implementation of the FITS WCS standard.
4  Copyright (C) 1995-2015, Mark Calabretta
5 
6  This file is part of WCSLIB.
7 
8  WCSLIB is free software: you can redistribute it and/or modify it under the
9  terms of the GNU Lesser General Public License as published by the Free
10  Software Foundation, either version 3 of the License, or (at your option)
11  any later version.
12 
13  WCSLIB is distributed in the hope that it will be useful, but WITHOUT ANY
14  WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
15  FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for
16  more details.
17 
18  You should have received a copy of the GNU Lesser General Public License
19  along with WCSLIB. If not, see http://www.gnu.org/licenses.
20 
21  Direct correspondence concerning WCSLIB to mark@calabretta.id.au
22 
23  Author: Mark Calabretta, Australia Telescope National Facility, CSIRO.
24  http://www.atnf.csiro.au/people/Mark.Calabretta
25  $Id: lin.h,v 5.0 2015/04/05 12:24:59 mcalabre Exp $
26 *=============================================================================
27 *
28 * WCSLIB 5.0 - C routines that implement the FITS World Coordinate System
29 * (WCS) standard. Refer to
30 *
31 * "Representations of world coordinates in FITS",
32 * Greisen, E.W., & Calabretta, M.R. 2002, A&A, 395, 1061 (Paper I)
33 *
34 * Refer to the README file provided with WCSLIB for an overview of the
35 * library.
36 *
37 *
38 * Summary of the lin routines
39 * ---------------------------
40 * These routines apply the linear transformation defined by the FITS WCS
41 * standard. They are based on the linprm struct which contains all
42 * information needed for the computations. The struct contains some members
43 * that must be set by the user, and others that are maintained by these
44 * routines, somewhat like a C++ class but with no encapsulation.
45 *
46 * Four routines, linini(), lindis(), lincpy(), and linfree() are provided to
47 * manage the linprm struct, and another, linprt(), prints its contents.
48 *
49 * linperr() prints the error message(s) (if any) stored in a linprm struct,
50 * and the disprm structs that it may contain.
51 *
52 * A setup routine, linset(), computes intermediate values in the linprm struct
53 * from parameters in it that were supplied by the user. The struct always
54 * needs to be set up by linset() but need not be called explicitly - refer to
55 * the explanation of linprm::flag.
56 *
57 * linp2x() and linx2p() implement the WCS linear transformations.
58 *
59 * An auxiliary matrix inversion routine, matinv(), is included. It uses
60 * LU-triangular factorization with scaled partial pivoting.
61 *
62 *
63 * linini() - Default constructor for the linprm struct
64 * ----------------------------------------------------
65 * linini() allocates memory for arrays in a linprm struct and sets all members
66 * of the struct to default values.
67 *
68 * PLEASE NOTE: every linprm struct must be initialized by linini(), possibly
69 * repeatedly. On the first invokation, and only the first invokation,
70 * linprm::flag must be set to -1 to initialize memory management, regardless
71 * of whether linini() will actually be used to allocate memory.
72 *
73 * Given:
74 * alloc int If true, allocate memory unconditionally for arrays in
75 * the linprm struct.
76 *
77 * If false, it is assumed that pointers to these arrays
78 * have been set by the user except if they are null
79 * pointers in which case memory will be allocated for
80 * them regardless. (In other words, setting alloc true
81 * saves having to initalize these pointers to zero.)
82 *
83 * naxis int The number of world coordinate axes, used to determine
84 * array sizes.
85 *
86 * Given and returned:
87 * lin struct linprm*
88 * Linear transformation parameters. Note that, in order
89 * to initialize memory management linprm::flag should be
90 * set to -1 when lin is initialized for the first time
91 * (memory leaks may result if it had already been
92 * initialized).
93 *
94 * Function return value:
95 * int Status return value:
96 * 0: Success.
97 * 1: Null linprm pointer passed.
98 * 2: Memory allocation failed.
99 *
100 * For returns > 1, a detailed error message is set in
101 * linprm::err if enabled, see wcserr_enable().
102 *
103 *
104 * lindis() - Assign a distortion to a linprm struct
105 * -------------------------------------------------
106 * lindis() may be used to assign the address of a disprm struct to
107 * linprm::dispre or linprm::disseq. The linprm struct must already have been
108 * initialized by linini().
109 *
110 * The disprm struct must have been allocated from the heap (e.g. using
111 * malloc(), calloc(), etc.). lindis() will immediately initialize it via a
112 * call to disini() using the value of linprm::naxis. Subsequently, it will be
113 * reinitialized by calls to linini(), and freed by linfree(), neither of which
114 * would happen if the disprm struct was assigned directly.
115 *
116 * If the disprm struct had previously been assigned via lindis(), it will be
117 * freed before reassignment. It is also permissable for a null disprm pointer
118 * to be assigned to disable the distortion correction.
119 *
120 * Given:
121 * sequence int Is it a prior or sequent distortion?
122 * 1: Prior, the assignment is to linprm::dispre.
123 * 2: Sequent, the assignment is to linprm::disseq.
124 *
125 * Anything else is an error.
126 *
127 * Given and returned:
128 * lin struct linprm*
129 * Linear transformation parameters.
130 *
131 * dis struct disprm*
132 * Distortion function parameters.
133 *
134 * Function return value:
135 * int Status return value:
136 * 0: Success.
137 * 1: Null linprm pointer passed.
138 * 4: Invalid sequence.
139 *
140 *
141 * lincpy() - Copy routine for the linprm struct
142 * ---------------------------------------------
143 * lincpy() does a deep copy of one linprm struct to another, using linini() to
144 * allocate memory for its arrays if required. Only the "information to be
145 * provided" part of the struct is copied; a call to linset() is required to
146 * initialize the remainder.
147 *
148 * Given:
149 * alloc int If true, allocate memory for the crpix, pc, and cdelt
150 * arrays in the destination. Otherwise, it is assumed
151 * that pointers to these arrays have been set by the
152 * user except if they are null pointers in which case
153 * memory will be allocated for them regardless.
154 *
155 * linsrc const struct linprm*
156 * Struct to copy from.
157 *
158 * Given and returned:
159 * lindst struct linprm*
160 * Struct to copy to. linprm::flag should be set to -1
161 * if lindst was not previously initialized (memory leaks
162 * may result if it was previously initialized).
163 *
164 * Function return value:
165 * int Status return value:
166 * 0: Success.
167 * 1: Null linprm pointer passed.
168 * 2: Memory allocation failed.
169 *
170 * For returns > 1, a detailed error message is set in
171 * linprm::err if enabled, see wcserr_enable().
172 *
173 *
174 * linfree() - Destructor for the linprm struct
175 * --------------------------------------------
176 * linfree() frees memory allocated for the linprm arrays by linini() and/or
177 * linset(). linini() keeps a record of the memory it allocates and linfree()
178 * will only attempt to free this.
179 *
180 * PLEASE NOTE: linfree() must not be invoked on a linprm struct that was not
181 * initialized by linini().
182 *
183 * Given:
184 * lin struct linprm*
185 * Linear transformation parameters.
186 *
187 * Function return value:
188 * int Status return value:
189 * 0: Success.
190 * 1: Null linprm pointer passed.
191 *
192 *
193 * linprt() - Print routine for the linprm struct
194 * ----------------------------------------------
195 * linprt() prints the contents of a linprm struct using wcsprintf(). Mainly
196 * intended for diagnostic purposes.
197 *
198 * Given:
199 * lin const struct linprm*
200 * Linear transformation parameters.
201 *
202 * Function return value:
203 * int Status return value:
204 * 0: Success.
205 * 1: Null linprm pointer passed.
206 *
207 *
208 * linperr() - Print error messages from a linprm struct
209 * -----------------------------------------------------
210 * linperr() prints the error message(s) (if any) stored in a linprm struct,
211 * and the disprm structs that it may contain. If there are no errors then
212 * nothing is printed. It uses wcserr_prt(), q.v.
213 *
214 * Given:
215 * lin const struct linprm*
216 * Coordinate transformation parameters.
217 *
218 * prefix const char *
219 * If non-NULL, each output line will be prefixed with
220 * this string.
221 *
222 * Function return value:
223 * int Status return value:
224 * 0: Success.
225 * 1: Null linprm pointer passed.
226 *
227 *
228 * linset() - Setup routine for the linprm struct
229 * ----------------------------------------------
230 * linset(), if necessary, allocates memory for the linprm::piximg and
231 * linprm::imgpix arrays and sets up the linprm struct according to information
232 * supplied within it - refer to the explanation of linprm::flag.
233 *
234 * Note that this routine need not be called directly; it will be invoked by
235 * linp2x() and linx2p() if the linprm::flag is anything other than a
236 * predefined magic value.
237 *
238 * Given and returned:
239 * lin struct linprm*
240 * Linear transformation parameters.
241 *
242 * Function return value:
243 * int Status return value:
244 * 0: Success.
245 * 1: Null linprm pointer passed.
246 * 2: Memory allocation failed.
247 * 3: PCi_ja matrix is singular.
248 *
249 * For returns > 1, a detailed error message is set in
250 * linprm::err if enabled, see wcserr_enable().
251 *
252 *
253 * linp2x() - Pixel-to-world linear transformation
254 * -----------------------------------------------
255 * linp2x() transforms pixel coordinates to intermediate world coordinates.
256 *
257 * Given and returned:
258 * lin struct linprm*
259 * Linear transformation parameters.
260 *
261 * Given:
262 * ncoord,
263 * nelem int The number of coordinates, each of vector length nelem
264 * but containing lin.naxis coordinate elements.
265 *
266 * pixcrd const double[ncoord][nelem]
267 * Array of pixel coordinates.
268 *
269 * Returned:
270 * imgcrd double[ncoord][nelem]
271 * Array of intermediate world coordinates.
272 *
273 * Function return value:
274 * int Status return value:
275 * 0: Success.
276 * 1: Null linprm pointer passed.
277 * 2: Memory allocation failed.
278 * 3: PCi_ja matrix is singular.
279 *
280 * For returns > 1, a detailed error message is set in
281 * linprm::err if enabled, see wcserr_enable().
282 *
283 *
284 * linx2p() - World-to-pixel linear transformation
285 * -----------------------------------------------
286 * linx2p() transforms intermediate world coordinates to pixel coordinates.
287 *
288 * Given and returned:
289 * lin struct linprm*
290 * Linear transformation parameters.
291 *
292 * Given:
293 * ncoord,
294 * nelem int The number of coordinates, each of vector length nelem
295 * but containing lin.naxis coordinate elements.
296 *
297 * imgcrd const double[ncoord][nelem]
298 * Array of intermediate world coordinates.
299 *
300 * Returned:
301 * pixcrd double[ncoord][nelem]
302 * Array of pixel coordinates.
303 *
304 * int Status return value:
305 * 0: Success.
306 * 1: Null linprm pointer passed.
307 * 2: Memory allocation failed.
308 * 3: PCi_ja matrix is singular.
309 *
310 * For returns > 1, a detailed error message is set in
311 * linprm::err if enabled, see wcserr_enable().
312 *
313 *
314 * linprm struct - Linear transformation parameters
315 * ------------------------------------------------
316 * The linprm struct contains all of the information required to perform a
317 * linear transformation. It consists of certain members that must be set by
318 * the user ("given") and others that are set by the WCSLIB routines
319 * ("returned").
320 *
321 * int flag
322 * (Given and returned) This flag must be set to zero whenever any of the
323 * following members of the linprm struct are set or modified:
324 *
325 * - linprm::naxis (q.v., not normally set by the user),
326 * - linprm::pc,
327 * - linprm::cdelt,
328 * - linprm::dispre.
329 * - linprm::disseq.
330 *
331 * This signals the initialization routine, linset(), to recompute the
332 * returned members of the linprm struct. linset() will reset flag to
333 * indicate that this has been done.
334 *
335 * PLEASE NOTE: flag should be set to -1 when linini() is called for the
336 * first time for a particular linprm struct in order to initialize memory
337 * management. It must ONLY be used on the first initialization otherwise
338 * memory leaks may result.
339 *
340 * int naxis
341 * (Given or returned) Number of pixel and world coordinate elements.
342 *
343 * If linini() is used to initialize the linprm struct (as would normally
344 * be the case) then it will set naxis from the value passed to it as a
345 * function argument. The user should not subsequently modify it.
346 *
347 * double *crpix
348 * (Given) Pointer to the first element of an array of double containing
349 * the coordinate reference pixel, CRPIXja.
350 *
351 * It is not necessary to reset the linprm struct (via linset()) when
352 * linprm::crpix is changed.
353 *
354 * double *pc
355 * (Given) Pointer to the first element of the PCi_ja (pixel coordinate)
356 * transformation matrix. The expected order is
357 *
358 = struct linprm lin;
359 = lin.pc = {PC1_1, PC1_2, PC2_1, PC2_2};
360 *
361 * This may be constructed conveniently from a 2-D array via
362 *
363 = double m[2][2] = {{PC1_1, PC1_2},
364 = {PC2_1, PC2_2}};
365 *
366 * which is equivalent to
367 *
368 = double m[2][2];
369 = m[0][0] = PC1_1;
370 = m[0][1] = PC1_2;
371 = m[1][0] = PC2_1;
372 = m[1][1] = PC2_2;
373 *
374 * The storage order for this 2-D array is the same as for the 1-D array,
375 * whence
376 *
377 = lin.pc = *m;
378 *
379 * would be legitimate.
380 *
381 * double *cdelt
382 * (Given) Pointer to the first element of an array of double containing
383 * the coordinate increments, CDELTia.
384 *
385 * struct disprm *dispre
386 * (Given) Pointer to a disprm struct holding parameters for prior
387 * distortion functions, or a null (0x0) pointer if there are none.
388 *
389 * Function lindis() may be used to assign a disprm pointer to a linprm
390 * struct, allowing it to take control of any memory allocated for it, as
391 * in the following example:
392 *
393 = void add_distortion(struct linprm *lin)
394 = {
395 = struct disprm *dispre;
396 =
397 = dispre = malloc(sizeof(struct disprm);
398 = dispre->flag = -1;
399 = lindis(1, lin, dispre);
400 = :
401 = (Set up dispre.)
402 = :
403 =
404 = return;
405 = }
406 *
407 * Here, after the distortion function parameters etc. are copied into
408 * dispre, dispre is assigned using lindis() which takes control of the
409 * allocated memory. It will be free'd later when linfree() is invoked on
410 * the linprm struct.
411 *
412 * Consider also the following erroneous code:
413 *
414 = void bad_code(struct linprm *lin)
415 = {
416 = struct disprm dispre;
417 =
418 = dispre.flag = -1;
419 = lindis(1, lin, &dispre); // WRONG.
420 = :
421 =
422 = return;
423 = }
424 *
425 * Here, dispre is declared as a struct, rather than a pointer. When the
426 * function returns, dispre will go out of scope and its memory will most
427 * likely be reused, thereby trashing its contents. Later, a segfault will
428 * occur when linfree() tries to free dispre's stale address.
429 *
430 * struct disprm *disseq
431 * (Given) Pointer to a disprm struct holding parameters for sequent
432 * distortion functions, or a null (0x0) pointer if there are none.
433 *
434 * Refer to the comments and examples given for disprm::dispre.
435 *
436 * double *piximg
437 * (Returned) Pointer to the first element of the matrix containing the
438 * product of the CDELTia diagonal matrix and the PCi_ja matrix.
439 *
440 * double *imgpix
441 * (Returned) Pointer to the first element of the inverse of the
442 * linprm::piximg matrix.
443 *
444 * int i_naxis
445 * (Returned) The dimension of linprm::piximg and linprm::imgpix (normally
446 * equal to naxis).
447 *
448 * int unity
449 * (Returned) True if the linear transformation matrix is unity.
450 *
451 * int affine
452 * (Returned) True if there are no distortions.
453 *
454 * int simple
455 * (Returned) True if unity and no distortions.
456 *
457 * struct wcserr *err
458 * (Returned) If enabled, when an error status is returned, this struct
459 * contains detailed information about the error, see wcserr_enable().
460 *
461 * double *tmpcrd
462 * (For internal use only.)
463 * int m_flag
464 * (For internal use only.)
465 * int m_naxis
466 * (For internal use only.)
467 * double *m_crpix
468 * (For internal use only.)
469 * double *m_pc
470 * (For internal use only.)
471 * double *m_cdelt
472 * (For internal use only.)
473 * struct disprm *m_dispre
474 * (For internal use only.)
475 * struct disprm *m_disseq
476 * (For internal use only.)
477 *
478 *
479 * Global variable: const char *lin_errmsg[] - Status return messages
480 * ------------------------------------------------------------------
481 * Error messages to match the status value returned from each function.
482 *
483 *===========================================================================*/
484 
485 #ifndef WCSLIB_LIN
486 #define WCSLIB_LIN
487 
488 #ifdef __cplusplus
489 extern "C" {
490 #endif
491 
492 
493 extern const char *lin_errmsg[];
494 
496  LINERR_SUCCESS = 0, /* Success. */
497  LINERR_NULL_POINTER = 1, /* Null linprm pointer passed. */
498  LINERR_MEMORY = 2, /* Memory allocation failed. */
499  LINERR_SINGULAR_MTX = 3, /* PCi_ja matrix is singular. */
500  LINERR_DISTORT_INIT = 4, /* Failed to initialise distortions. */
501  LINERR_DISTORT = 5, /* Distort error. */
502  LINERR_DEDISTORT = 6 /* De-distort error. */
503 };
504 
505 struct linprm {
506  /* Initialization flag (see the prologue above). */
507  /*------------------------------------------------------------------------*/
508  int flag; /* Set to zero to force initialization. */
509 
510  /* Parameters to be provided (see the prologue above). */
511  /*------------------------------------------------------------------------*/
512  int naxis; /* The number of axes, given by NAXIS. */
513  double *crpix; /* CRPIXja keywords for each pixel axis. */
514  double *pc; /* PCi_ja linear transformation matrix. */
515  double *cdelt; /* CDELTia keywords for each coord axis. */
516  struct disprm *dispre; /* Prior distortion parameters, if any. */
517  struct disprm *disseq; /* Sequent distortion parameters, if any. */
518 
519  /* Information derived from the parameters supplied. */
520  /*------------------------------------------------------------------------*/
521  double *piximg; /* Product of CDELTia and PCi_ja matrices. */
522  double *imgpix; /* Inverse of the piximg matrix. */
523  int i_naxis; /* Dimension of piximg and imgpix. */
524  int unity; /* True if the PCi_ja matrix is unity. */
525  int affine; /* True if there are no distortions. */
526  int simple; /* True if unity and no distortions. */
527 
528  /* Error handling, if enabled. */
529  /*------------------------------------------------------------------------*/
530  struct wcserr *err;
531 
532  /* Private - the remainder are for internal use. */
533  /*------------------------------------------------------------------------*/
534  double *tmpcrd;
535 
537  double *m_crpix, *m_pc, *m_cdelt;
539 };
540 
541 /* Size of the linprm struct in int units, used by the Fortran wrappers. */
542 #define LINLEN (sizeof(struct linprm)/sizeof(int))
543 
544 
545 int linini(int alloc, int naxis, struct linprm *lin);
546 
547 int lindis(int sequence, struct linprm *lin, struct disprm *dis);
548 
549 int lincpy(int alloc, const struct linprm *linsrc, struct linprm *lindst);
550 
551 int linfree(struct linprm *lin);
552 
553 int linprt(const struct linprm *lin);
554 
555 int linperr(const struct linprm *lin, const char *prefix);
556 
557 int linset(struct linprm *lin);
558 
559 int linp2x(struct linprm *lin, int ncoord, int nelem, const double pixcrd[],
560  double imgcrd[]);
561 
562 int linx2p(struct linprm *lin, int ncoord, int nelem, const double imgcrd[],
563  double pixcrd[]);
564 
565 int matinv(int n, const double mat[], double inv[]);
566 
567 
568 /* Deprecated. */
569 #define linini_errmsg lin_errmsg
570 #define lincpy_errmsg lin_errmsg
571 #define linfree_errmsg lin_errmsg
572 #define linprt_errmsg lin_errmsg
573 #define linset_errmsg lin_errmsg
574 #define linp2x_errmsg lin_errmsg
575 #define linx2p_errmsg lin_errmsg
576 
577 #ifdef __cplusplus
578 }
579 #endif
580 
581 #endif /* WCSLIB_LIN */
double * m_pc
Definition: lin.h:537
int linp2x(struct linprm *lin, int ncoord, int nelem, const double pixcrd[], double imgcrd[])
Pixel-to-world linear transformation.
struct disprm * dispre
Definition: lin.h:516
double * tmpcrd
Definition: lin.h:534
Definition: lin.h:502
int naxis
Definition: lin.h:512
double * crpix
Definition: lin.h:513
Definition: lin.h:498
int m_flag
Definition: lin.h:536
int unity
Definition: lin.h:524
struct disprm * m_dispre
Definition: lin.h:538
Error message handling.
Definition: wcserr.h:221
int m_naxis
Definition: lin.h:536
struct wcserr * err
Definition: lin.h:530
int naxis
Definition: dis.h:501
int matinv(int n, const double mat[], double inv[])
Matrix inversion.
Linear transformation parameters.
Definition: lin.h:505
const char * lin_errmsg[]
Status return messages.
Distortion parameters.
Definition: dis.h:494
int linperr(const struct linprm *lin, const char *prefix)
Print error messages from a linprm struct.
double * piximg
Definition: lin.h:521
int simple
Definition: lin.h:526
int i_naxis
Definition: lin.h:523
double * m_crpix
Definition: lin.h:537
struct disprm * m_disseq
Definition: lin.h:538
int linfree(struct linprm *lin)
Destructor for the linprm struct.
int linset(struct linprm *lin)
Setup routine for the linprm struct.
Definition: lin.h:496
int linini(int alloc, int naxis, struct linprm *lin)
Default constructor for the linprm struct.
double * cdelt
Definition: lin.h:515
lin_errmsg_enum
Definition: lin.h:495
int flag
Definition: lin.h:508
int affine
Definition: lin.h:525
Definition: lin.h:500
int lincpy(int alloc, const struct linprm *linsrc, struct linprm *lindst)
Copy routine for the linprm struct.
double * pc
Definition: lin.h:514
int linx2p(struct linprm *lin, int ncoord, int nelem, const double imgcrd[], double pixcrd[])
World-to-pixel linear transformation.
int lindis(int sequence, struct linprm *lin, struct disprm *dis)
Assign a distortion to a linprm struct.
struct disprm * disseq
Definition: lin.h:517
double * imgpix
Definition: lin.h:522
double * m_cdelt
Definition: lin.h:537
Definition: lin.h:499
int linprt(const struct linprm *lin)
Print routine for the linprm struct.
Definition: lin.h:501
Definition: lin.h:497