diff options
| author | Andrew Bell <andrew.bell.ia@gmail.com> | 2019-05-15 10:47:03 -0400 |
|---|---|---|
| committer | Andrew Bell <andrew.bell.ia@gmail.com> | 2019-05-15 10:47:03 -0400 |
| commit | 8f268409d37cea329d263e177b83e42f8384d3c7 (patch) | |
| tree | c4d0f3dd19456600f718a6e0c8573577f433549b /src/projections/lcc.cpp | |
| parent | 886ced02f0aaab5d66d16459435f7447cf976650 (diff) | |
| parent | d67203a6f76a74f5ac029ff052dbcc72e3b59624 (diff) | |
| download | PROJ-8f268409d37cea329d263e177b83e42f8384d3c7.tar.gz PROJ-8f268409d37cea329d263e177b83e42f8384d3c7.zip | |
Merge remote-tracking branch 'origin/master'
Diffstat (limited to 'src/projections/lcc.cpp')
| -rw-r--r-- | src/projections/lcc.cpp | 31 |
1 files changed, 26 insertions, 5 deletions
diff --git a/src/projections/lcc.cpp b/src/projections/lcc.cpp index a1fe79a9..beb2efd1 100644 --- a/src/projections/lcc.cpp +++ b/src/projections/lcc.cpp @@ -20,7 +20,7 @@ struct pj_opaque { } // anonymous namespace -static PJ_XY e_forward (PJ_LP lp, PJ *P) { /* Ellipsoidal, forward */ +static PJ_XY lcc_e_forward (PJ_LP lp, PJ *P) { /* Ellipsoidal, forward */ PJ_XY xy = {0., 0.}; struct pj_opaque *Q = static_cast<struct pj_opaque*>(P->opaque); double rho; @@ -43,7 +43,7 @@ static PJ_XY e_forward (PJ_LP lp, PJ *P) { /* Ellipsoidal, forward */ } -static PJ_LP e_inverse (PJ_XY xy, PJ *P) { /* Ellipsoidal, inverse */ +static PJ_LP lcc_e_inverse (PJ_XY xy, PJ *P) { /* Ellipsoidal, inverse */ PJ_LP lp = {0., 0.}; struct pj_opaque *Q = static_cast<struct pj_opaque*>(P->opaque); double rho; @@ -94,6 +94,8 @@ PJ *PROJECTION(lcc) { if (!pj_param(P->ctx, P->params, "tlat_0").i) P->phi0 = Q->phi1; } + if (fabs(Q->phi1) > M_HALFPI || fabs(Q->phi2) > M_HALFPI) + return pj_default_destructor(P, PJD_ERR_LAT_LARGER_THAN_90); if (fabs(Q->phi1 + Q->phi2) < EPS10) return pj_default_destructor(P, PJD_ERR_CONIC_LAT_EQUAL); @@ -105,15 +107,34 @@ PJ *PROJECTION(lcc) { m1 = pj_msfn(sinphi, cosphi, P->es); ml1 = pj_tsfn(Q->phi1, sinphi, P->e); + if( ml1 == 0 ) { + return pj_default_destructor(P, PJD_ERR_LAT_1_OR_2_ZERO_OR_90); + } if (secant) { /* secant cone */ sinphi = sin(Q->phi2); Q->n = log(m1 / pj_msfn(sinphi, cos(Q->phi2), P->es)); - Q->n /= log(ml1 / pj_tsfn(Q->phi2, sinphi, P->e)); + if (Q->n == 0) { + // Not quite, but es is very close to 1... + return pj_default_destructor(P, PJD_ERR_INVALID_ECCENTRICITY); + } + const double ml2 = pj_tsfn(Q->phi2, sinphi, P->e); + if( ml2 == 0 ) { + return pj_default_destructor(P, PJD_ERR_LAT_1_OR_2_ZERO_OR_90); + } + const double denom = log(ml1 / ml2); + if( denom == 0 ) { + // Not quite, but es is very close to 1... + return pj_default_destructor(P, PJD_ERR_INVALID_ECCENTRICITY); + } + Q->n /= denom; } Q->c = (Q->rho0 = m1 * pow(ml1, -Q->n) / Q->n); Q->rho0 *= (fabs(fabs(P->phi0) - M_HALFPI) < EPS10) ? 0. : pow(pj_tsfn(P->phi0, sin(P->phi0), P->e), Q->n); } else { + if( fabs(cosphi) < EPS10 || fabs(cos(Q->phi2)) < EPS10 ) { + return pj_default_destructor(P, PJD_ERR_LAT_1_OR_2_ZERO_OR_90); + } if (secant) Q->n = log(cosphi / cos(Q->phi2)) / log(tan(M_FORTPI + .5 * Q->phi2) / @@ -123,8 +144,8 @@ PJ *PROJECTION(lcc) { Q->c * pow(tan(M_FORTPI + .5 * P->phi0), -Q->n); } - P->inv = e_inverse; - P->fwd = e_forward; + P->inv = lcc_e_inverse; + P->fwd = lcc_e_forward; return P; } |
