?????????? ????????? - ??????????????? - /home/agenciai/public_html/cd38d8/policies.zip
???????
PK b��[�se� � 02-keylime-remote-attestationnu �[��� # PROC_SUPER_MAGIC dont_measure fsmagic=0x9fa0 # SYSFS_MAGIC dont_measure fsmagic=0x62656572 # DEBUGFS_MAGIC dont_measure fsmagic=0x64626720 # TMPFS_MAGIC dont_measure fsmagic=0x01021994 # DEVPTS_SUPER_MAGIC dont_measure fsmagic=0x1cd1 # BINFMTFS_MAGIC dont_measure fsmagic=0x42494e4d # SECURITYFS_MAGIC dont_measure fsmagic=0x73636673 # SELINUX_MAGIC dont_measure fsmagic=0xf97cff8c # SMACK_MAGIC dont_measure fsmagic=0x43415d53 # CGROUP_SUPER_MAGIC dont_measure fsmagic=0x27e0eb # CGROUP2_SUPER_MAGIC dont_measure fsmagic=0x63677270 # NSFS_MAGIC dont_measure fsmagic=0x6e736673 # EFIVARFS_MAGIC dont_measure fsmagic=0xde5e81e4 # OVERLAYFS_MAGIC # when containers are used we almost always want to ignore them dont_measure fsmagic=0x794c7630 # Measure and log keys loaded onto the .ima keyring measure func=KEY_CHECK keyrings=.ima # Measure and log executables measure func=BPRM_CHECK # Measure and log shared libraries measure func=FILE_MMAP mask=MAY_EXEC PK b��[�� ) 01-appraise-executable-and-lib-signaturesnu �[��� # Skip some unsupported filesystems # This list of the filesystems can be found on # https://www.kernel.org/doc/Documentation/ABI/testing/ima_policy # PROC_SUPER_MAGIC dont_appraise fsmagic=0x9fa0 # SYSFS_MAGIC dont_appraise fsmagic=0x62656572 # DEBUGFS_MAGIC dont_appraise fsmagic=0x64626720 # TMPFS_MAGIC dont_appraise fsmagic=0x01021994 # RAMFS_MAGIC dont_appraise fsmagic=0x858458f6 # DEVPTS_SUPER_MAGIC dont_appraise fsmagic=0x1cd1 # BINFMTFS_MAGIC dont_appraise fsmagic=0x42494e4d # SECURITYFS_MAGIC dont_appraise fsmagic=0x73636673 # SELINUX_MAGIC dont_appraise fsmagic=0xf97cff8c # CGROUP_SUPER_MAGIC dont_appraise fsmagic=0x27e0eb # NSFS_MAGIC dont_appraise fsmagic=0x6e736673 appraise func=MMAP_CHECK mask=MAY_EXEC appraise_type=imasig appraise func=BPRM_CHECK appraise_type=imasig PK �!\o���= = FUTURE.polnu �[��� # A level that will provide security on a conservative level that is # believed to withstand any near-term future attacks. And also provide # some (not complete) preparation for post quantum encryption support # in form of 256 bit symmetric encryption requirement. # It provides at least an 128-bit security. This level may prevent # communication with many used systems that provide weaker security levels # (e.g., systems that use SHA-1 as signature algorithm). # MACs: all HMAC with SHA256 or better + all modern MACs (Poly1305 etc) # Curves: all prime >= 255 bits (including Bernstein curves) # Signature algorithms: with SHA-256 hash or better (no DSA) # TLS Ciphers: >= 256-bit key, >= 128-bit block, only Authenticated Encryption (AE) ciphers, no CBC ciphers # non-TLS Ciphers: same as TLS Ciphers with added non AE ciphers, CBC only for Kerberos # key exchange: ECDHE, DHE (no DHE-DSS) # DH params size: >= 3072 # RSA params size: >= 3072 # TLS protocols: TLS >= 1.2, DTLS >= 1.2 mac = AEAD HMAC-SHA2-256 UMAC-128 HMAC-SHA2-384 HMAC-SHA2-512 mac@Kerberos = HMAC-SHA2-384 HMAC-SHA2-256 AEAD UMAC-128 HMAC-SHA2-512 group = X25519 SECP256R1 X448 SECP521R1 SECP384R1 \ FFDHE-3072 FFDHE-4096 FFDHE-6144 FFDHE-8192 hash = SHA2-256 SHA2-384 SHA2-512 SHA3-256 SHA3-384 SHA3-512 SHAKE-256 hash@RPM = SHA1+ sign = ECDSA-SHA3-256 ECDSA-SHA2-256 ECDSA-SHA2-256-FIDO \ ECDSA-SHA3-384 ECDSA-SHA2-384 \ ECDSA-SHA3-512 ECDSA-SHA2-512 \ EDDSA-ED25519 EDDSA-ED25519-FIDO EDDSA-ED448 \ RSA-PSS-SHA3-256 RSA-PSS-SHA2-256 \ RSA-PSS-SHA3-384 RSA-PSS-SHA2-384 \ RSA-PSS-SHA3-512 RSA-PSS-SHA2-512 \ RSA-PSS-RSAE-SHA3-256 RSA-PSS-RSAE-SHA2-256 \ RSA-PSS-RSAE-SHA3-384 RSA-PSS-RSAE-SHA2-384 \ RSA-PSS-RSAE-SHA3-512 RSA-PSS-RSAE-SHA2-512 \ RSA-SHA3-256 RSA-SHA2-256 \ RSA-SHA3-384 RSA-SHA2-384 \ RSA-SHA3-512 RSA-SHA2-512 cipher = AES-256-GCM AES-256-CCM CHACHA20-POLY1305 \ AES-256-CTR cipher@Kerberos = AES-256-CBC+ cipher@TLS = AES-256-GCM AES-256-CCM CHACHA20-POLY1305 cipher@RPM = AES-256-CFB AES-256-GCM AES-256-OCB AES-256-EAX # CBC ciphers in SSH are considered vulnerable to plaintext recovery attacks # and disabled in client OpenSSH 7.6 (2017) and server OpenSSH 6.7 (2014). cipher@SSH = -*-CBC key_exchange = ECDHE DHE DHE-RSA PSK DHE-PSK ECDHE-PSK ECDHE-GSS DHE-GSS protocol@TLS = TLS1.3 TLS1.2 DTLS1.2 protocol@IKE = IKEv2 # Parameter sizes min_dh_size = 3072 min_dsa_size = 3072 # DSA is disabled min_rsa_size = 3072 # GnuTLS only for now sha1_in_certs = 0 arbitrary_dh_groups = 1 ssh_certs = 1 etm@ssh = ANY PK �!\�T� � modules/SHA1.pmodnu �[��� # This subpolicy adds SHA1 hash and signature support hash = SHA1+ sign = ECDSA-SHA1+ RSA-PSS-SHA1+ RSA-SHA1+ sha1_in_certs = 1 PK �!\9���{ { modules/NO-SHA1.pmodnu �[��� # This is an example subpolicy dropping the SHA1 hash and signature support hash = -SHA1 sign = -*-SHA1 sha1_in_certs = 0 PK �!\��\ modules/AD-SUPPORT.pmodnu �[��� # AD-SUPPORT subpolicy is intended to be used in Active Directory environments. # This subpolicy is provided for enabling aes256-cts-hmac-sha1-96, # the strongest Kerberos encryption type interoperable with Active Directory. cipher@kerberos = AES-256-CBC+ mac@kerberos = HMAC-SHA1+ PK �!\�%�=� � modules/AD-SUPPORT-LEGACY.pmodnu �[��� # AD-SUPPORT-LEGACY subpolicy is intended to be used in Active Directory # environments where either accounts or trusted domain objects were not yet # migrated to AES or future encryption types. # This subpolicy enables all AES and RC4 Kerberos encryption types # to maximize Active Directory interoperability at the expense of security. cipher@kerberos = AES-256-CBC+ AES-128-CBC+ RC4-128+ mac@kerberos = HMAC-SHA2-384+ HMAC-SHA2-256+ HMAC-SHA1+ hash@kerberos = MD5+ PK �!\'jf� � modules/PQ.pmodnu �[��� # An subpolicy enabling some of the # post-quantum and hybrid algorithms # currently available in RHEL-9. # Note that not all the backends support all the algorithms. group = +MLKEM1024-X448 group = +P384-MLKEM1024 group = +P256-MLKEM768 group = +MLKEM768-X25519 sign = +MLDSA87-ED448 sign = +MLDSA65-ED25519 sign = +MLDSA87 sign = +MLDSA65 sign = +MLDSA44 key_exchange = +KEM-ECDH PK �!\Qe� � modules/NO-ENFORCE-EMS.pmodnu �[��� # As per FIPS 140-3 IG Annex D.Q, EMS is mandatory in TLS 1.2 since 2023-05-16. # This subpolicy disables this mandatory EMS enforcement of the FIPS policy. # Doing so violates FIPS requirements, do not use in FIPS-compliant setups. __ems = RELAX PK �!\ԇhG modules/OSPP.pmodnu �[��� # Restrict FIPS policy for the Common Criteria OSPP profile. # SSH (upper limit) # Ciphers: aes256-ctr, aes256-cbc, aes256-gcm@openssh.com # PubkeyAcceptedKeyTypes: rsa-sha2-256, rsa‑sha2‑512 # MACs: hmac-sha2-256, hmac-sha2-512, implicit for aes256-gcm@openssh.com # KexAlgorithms: ecdh-sha2-nistp384, ecdh-sha2-nistp521, diffie-hellman-group16-sha512, diffie-hellman-group18-sha512 # TLS ciphers (suggested minimal set for openssl) # * TLS_RSA_WITH_AES_128_CBC_SHA - excluded by FIPS, uses RSA key exchange # * TLS_RSA_WITH_AES_256_CBC_SHA - excluded by FIPS, uses RSA key exchange # * TLS_RSA_WITH_AES_128_CBC_SHA256 - excluded by FIPS, uses RSA key exchange # * TLS_RSA_WITH_AES_256_CBC_SHA256 - excluded by FIPS, uses RSA key exchange # * TLS_RSA_WITH_AES_128_GCM_SHA256 - excluded by FIPS, uses RSA key exchange # * TLS_RSA_WITH_AES_256_GCM_SHA384 - excluded by FIPS, uses RSA key exchange # * TLS_DHE_RSA_WITH_AES_128_CBC_SHA256 - excluded by FIPS (CBC) # * TLS_DHE_RSA_WITH_AES_256_CBC_SHA256 - excluded by FIPS (CBC) # * TLS_DHE_RSA_WITH_AES_128_GCM_SHA256 - disabled, AES 128 # * TLS_DHE_RSA_WITH_AES_256_GCM_SHA384 # * TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256 - disabled, AES 128 # * TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 - disabled, AES 128 # * TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384 - disabled in openssl itself # * TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 # * TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256 - disabled, AES 128 + CBC # * TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 - disabled, AES 128 # * TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384 - disabled in openssl itself # * TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 # Supported Groups Extension in ClientHello: secp256r1, secp384r1, secp521r1 mac = -HMAC-SHA1 # see above, both SSH and TLS ended up not using it group = -SECP256R1 -FFDHE-2048 hash = -SHA2-224 -SHA3-* sign = -*-SHA2-224 -ECDSA-SHA2-256 cipher = -AES-*-CCM -AES-128-* cipher@!{ssh,tls} = -AES-*-CTR ssh_certs = 0 etm@ssh = DISABLE_ETM protocol@TLS = -TLS1.3 min_dh_size = 3072 min_rsa_size = 3072 arbitrary_dh_groups = 0 PK �!\�h1� � modules/ECDHE-ONLY.pmodnu �[��� # This is an example of a subpolicy # enforcing ECDHE and ECDHE with PSK key exchanges key_exchange = ECDHE ECDHE-PSK group = -FFDHE-* PK �!\�f'25 5 DEFAULT.polnu �[��� # A reasonable default for today's standards. # It should provide 112-bit security. # SHA1 is allowed in HMAC where collision resistance does not matter. # MACs: all HMAC with SHA1 or better + all modern MACs (Poly1305 etc) # Curves: all prime >= 255 bits (including Bernstein curves) # Signature algorithms: with SHA-224 hash or better (no DSA) # Ciphers: >= 128-bit key, >= 128-bit block (AES, ChaCha20) # key exchange: ECDHE, RSA, DHE (no DHE-DSS) # DH params size: >= 2048 # RSA params size: >= 2048 # TLS protocols: TLS >= 1.2, DTLS >= 1.2 mac = AEAD HMAC-SHA2-256 HMAC-SHA1 UMAC-128 HMAC-SHA2-384 HMAC-SHA2-512 mac@Kerberos = HMAC-SHA2-384 HMAC-SHA2-256 AEAD UMAC-128 HMAC-SHA2-512 HMAC-SHA1 group = X25519 SECP256R1 X448 SECP521R1 SECP384R1 \ FFDHE-2048 FFDHE-3072 FFDHE-4096 FFDHE-6144 FFDHE-8192 hash = SHA2-256 SHA2-384 SHA2-512 SHA3-256 SHA3-384 SHA3-512 SHA2-224 SHA3-224 \ SHAKE-256 hash@RPM = SHA1+ sign = ECDSA-SHA3-256 ECDSA-SHA2-256 ECDSA-SHA2-256-FIDO \ ECDSA-SHA3-384 ECDSA-SHA2-384 \ ECDSA-SHA3-512 ECDSA-SHA2-512 \ EDDSA-ED25519 EDDSA-ED25519-FIDO EDDSA-ED448 \ RSA-PSS-SHA3-256 RSA-PSS-SHA2-256 \ RSA-PSS-SHA3-384 RSA-PSS-SHA2-384 \ RSA-PSS-SHA3-512 RSA-PSS-SHA2-512 \ RSA-PSS-RSAE-SHA3-256 RSA-PSS-RSAE-SHA2-256 \ RSA-PSS-RSAE-SHA3-384 RSA-PSS-RSAE-SHA2-384 \ RSA-PSS-RSAE-SHA3-512 RSA-PSS-RSAE-SHA2-512 \ RSA-SHA3-256 RSA-SHA2-256 \ RSA-SHA3-384 RSA-SHA2-384 \ RSA-SHA3-512 RSA-SHA2-512 \ ECDSA-SHA2-224 RSA-PSS-SHA2-224 RSA-SHA2-224 \ ECDSA-SHA3-224 RSA-PSS-SHA3-224 RSA-SHA3-224 cipher = AES-256-GCM AES-256-CCM CHACHA20-POLY1305 \ AES-256-CTR AES-256-CBC \ AES-128-GCM AES-128-CCM \ AES-128-CTR AES-128-CBC cipher@TLS = AES-256-GCM AES-256-CCM CHACHA20-POLY1305 AES-256-CBC \ AES-128-GCM AES-128-CCM AES-128-CBC cipher@RPM = AES-256-CFB AES-256-GCM AES-256-OCB AES-256-EAX \ AES-128-CFB AES-128-GCM AES-128-OCB AES-128-EAX # CBC ciphers in SSH are considered vulnerable to plaintext recovery attacks # and disabled in client OpenSSH 7.6 (2017) and server OpenSSH 6.7 (2014). cipher@SSH = -*-CBC # 'RSA' is intentionally before DHE ciphersuites, as the DHE ciphersuites have # interoperability issues in TLS. key_exchange = ECDHE RSA DHE DHE-RSA PSK DHE-PSK ECDHE-PSK RSA-PSK ECDHE-GSS DHE-GSS protocol@TLS = TLS1.3 TLS1.2 DTLS1.2 protocol@IKE = IKEv2 # Parameter sizes min_dh_size = 2048 min_dsa_size = 2048 # DSA is disabled min_rsa_size = 2048 # GnuTLS only for now sha1_in_certs = 0 arbitrary_dh_groups = 1 ssh_certs = 1 etm@SSH = ANY PK �!\@(�} } FIPS.polnu �[��� # Only FIPS approved or allowed algorithms. It does not provide FIPS compliance # by itself, the FIPS validated crypto modules must be properly installed # and the machine must be booted into the FIPS mode. # MACs: SHA-256 or better # Curves: all prime >= 256 bits # Signature algorithms: with SHA-224 hash or better (no DSA) # TLS Ciphers: >= 128-bit key, >= 128-bit block (AES, excluding AES-CBC) # key exchange: ECDHE, RSA, DHE (no DHE-DSS) # DH params size: >= 2048 # RSA params size: >= 2048 # TLS protocols: TLS >= 1.2, DTLS >= 1.2 mac = AEAD HMAC-SHA2-256 HMAC-SHA2-384 HMAC-SHA2-512 mac@Kerberos = HMAC-SHA2-384 HMAC-SHA2-256 AEAD HMAC-SHA2-512 group = SECP256R1 SECP521R1 SECP384R1 \ FFDHE-2048 FFDHE-3072 FFDHE-4096 FFDHE-6144 FFDHE-8192 hash = SHA2-256 SHA2-384 SHA2-512 SHA2-224 SHA3-256 SHA3-384 SHA3-512 SHAKE-256 hash@RPM = SHA1+ sign = ECDSA-SHA3-256 ECDSA-SHA2-256 \ ECDSA-SHA3-384 ECDSA-SHA2-384 \ ECDSA-SHA3-512 ECDSA-SHA2-512 \ RSA-PSS-SHA3-256 RSA-PSS-SHA2-256 \ RSA-PSS-SHA3-384 RSA-PSS-SHA2-384 \ RSA-PSS-SHA3-512 RSA-PSS-SHA2-512 \ RSA-PSS-RSAE-SHA3-256 RSA-PSS-RSAE-SHA2-256 \ RSA-PSS-RSAE-SHA3-384 RSA-PSS-RSAE-SHA2-384 \ RSA-PSS-RSAE-SHA3-512 RSA-PSS-RSAE-SHA2-512 \ RSA-SHA3-256 RSA-SHA2-256 \ RSA-SHA3-384 RSA-SHA2-384 \ RSA-SHA3-512 RSA-SHA2-512 \ ECDSA-SHA2-224 RSA-PSS-SHA2-224 RSA-SHA2-224 sign@RPM = MLDSA65-ED25519+ MLDSA87-ED448+ # Standardized in OpenPGP cipher = AES-256-GCM AES-256-CCM AES-256-CTR \ AES-128-GCM AES-128-CCM AES-128-CTR cipher@TLS = AES-256-GCM AES-256-CCM \ AES-128-GCM AES-128-CCM cipher@RPM = AES-256-GCM AES-256-CFB AES-128-GCM AES-128-CFB # Kerberos is an exception, # we allow CBC CTS ciphers as there are no other options cipher@Kerberos = AES-256-CBC AES-128-CBC key_exchange = ECDHE DHE DHE-RSA PSK DHE-PSK ECDHE-PSK protocol@TLS = TLS1.3 TLS1.2 DTLS1.2 protocol@IKE = IKEv2 # Parameter sizes min_dh_size = 2048 min_dsa_size = 2048 # DSA is disabled min_rsa_size = 2048 # GnuTLS only for now sha1_in_certs = 0 arbitrary_dh_groups = 1 ssh_certs = 1 etm@SSH = ANY __ems = ENFORCE PK �!\�� EMPTY.polnu �[��� # Just an empty policy for testing mac = group = hash = sign = cipher = key_exchange = #protocol = # Parameter sizes min_dh_size = 0 min_dsa_size = 0 min_rsa_size = 0 # GnuTLS only for now sha1_in_certs = 0 arbitrary_dh_groups = 0 ssh_certs = 0 etm@SSH = DISABLE_ETM PK �!\��%�� � LEGACY.polnu �[��� # Provides settings for ensuring maximum compatibility with legacy systems. # This policy is less secure and intended to be a easy way to switch system # to be compatible with older systems. # It should provide at least 80-bit security and excludes 3DES and RC4. # MACs: all HMAC with SHA1 or better + all modern MACs (Poly1305 etc) # Curves: all prime >= 255 bits (including Bernstein curves) # Signature algorithms: with SHA-1 hash or better (no DSA) # Ciphers: all available > 112-bit key, >= 128-bit block # (excluding 3DES and RC4) # key exchange: ECDHE, RSA, DHE (no DHE-DSS) # DH params size: >= 2048 # RSA params size: >= 2048 # DSA params size: DSA is not allowed # TLS protocols: TLS >= 1.2 DTLS >= 1.2 mac = AEAD HMAC-SHA2-256 HMAC-SHA1 UMAC-128 HMAC-SHA2-384 HMAC-SHA2-512 mac@Kerberos = HMAC-SHA2-384 HMAC-SHA2-256 AEAD UMAC-128 HMAC-SHA2-512 HMAC-SHA1 group = X25519 SECP256R1 X448 SECP521R1 SECP384R1 \ FFDHE-2048 FFDHE-3072 FFDHE-4096 FFDHE-6144 FFDHE-8192 FFDHE-1536 hash = SHA2-256 SHA2-384 SHA2-512 SHA3-256 SHA3-384 SHA3-512 SHA2-224 SHA3-224 \ SHAKE-256 SHAKE-128 SHA1 sign = ECDSA-SHA3-256 ECDSA-SHA2-256 ECDSA-SHA2-256-FIDO \ ECDSA-SHA3-384 ECDSA-SHA2-384 \ ECDSA-SHA3-512 ECDSA-SHA2-512 \ EDDSA-ED25519 EDDSA-ED25519-FIDO EDDSA-ED448 \ RSA-PSS-SHA3-256 RSA-PSS-SHA2-256 \ RSA-PSS-SHA3-384 RSA-PSS-SHA2-384 \ RSA-PSS-SHA3-512 RSA-PSS-SHA2-512 \ RSA-PSS-RSAE-SHA3-256 RSA-PSS-RSAE-SHA2-256 \ RSA-PSS-RSAE-SHA3-384 RSA-PSS-RSAE-SHA2-384 \ RSA-PSS-RSAE-SHA3-512 RSA-PSS-RSAE-SHA2-512 \ RSA-SHA3-256 RSA-SHA2-256 \ RSA-SHA3-384 RSA-SHA2-384 \ RSA-SHA3-512 RSA-SHA2-512 \ ECDSA-SHA2-224 RSA-PSS-SHA2-224 RSA-SHA2-224 \ ECDSA-SHA3-224 RSA-PSS-SHA3-224 RSA-SHA3-224 \ ECDSA-SHA1 RSA-PSS-SHA1 RSA-SHA1 cipher = AES-256-GCM AES-256-CCM \ CHACHA20-POLY1305 \ AES-256-CTR AES-256-CBC \ AES-128-GCM AES-128-CCM \ AES-128-CTR AES-128-CBC cipher@TLS = AES-256-GCM AES-256-CCM CHACHA20-POLY1305 AES-256-CBC \ AES-128-GCM AES-128-CCM AES-128-CBC cipher@SSH = AES-256-GCM CHACHA20-POLY1305 AES-256-CTR AES-256-CBC \ AES-128-GCM AES-128-CTR AES-128-CBC cipher@RPM = AES-256-CFB AES-256-GCM AES-256-OCB AES-256-EAX \ AES-128-CFB AES-128-GCM AES-128-OCB AES-128-EAX # 'RSA' is intentionally before DHE ciphersuites, as the DHE ciphersuites have # interoperability issues in TLS. key_exchange = ECDHE RSA DHE DHE-RSA PSK DHE-PSK ECDHE-PSK RSA-PSK ECDHE-GSS DHE-GSS protocol@TLS = TLS1.3 TLS1.2 DTLS1.2 protocol@IKE = IKEv2 # Parameter sizes min_dh_size = 2048 min_dsa_size = 2048 # DSA is disabled min_rsa_size = 2048 # GnuTLS only for now sha1_in_certs = 1 arbitrary_dh_groups = 1 ssh_certs = 1 etm@SSH = ANY PK 7�!\�u3E�� �� policy.hppnu �[��� // Copyright John Maddock 2007. // Use, modification and distribution are subject to the // Boost Software License, Version 1.0. (See accompanying file // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_MATH_POLICY_HPP #define BOOST_MATH_POLICY_HPP #include <boost/mpl/list.hpp> #include <boost/mpl/contains.hpp> #include <boost/mpl/if.hpp> #include <boost/mpl/find_if.hpp> #include <boost/mpl/remove_if.hpp> #include <boost/mpl/vector.hpp> #include <boost/mpl/push_back.hpp> #include <boost/mpl/at.hpp> #include <boost/mpl/size.hpp> #include <boost/mpl/comparison.hpp> #include <boost/type_traits/is_same.hpp> #include <boost/static_assert.hpp> #include <boost/assert.hpp> #include <boost/math/tools/config.hpp> #include <limits> // Sadly we do need the .h versions of these to be sure of getting // FLT_MANT_DIG etc. #include <limits.h> #include <stdlib.h> #include <stddef.h> #include <math.h> namespace boost{ namespace math{ namespace tools{ template <class T> BOOST_MATH_CONSTEXPR int digits(BOOST_MATH_EXPLICIT_TEMPLATE_TYPE(T)) BOOST_NOEXCEPT; template <class T> BOOST_MATH_CONSTEXPR T epsilon(BOOST_MATH_EXPLICIT_TEMPLATE_TYPE(T)) BOOST_MATH_NOEXCEPT(T); } namespace policies{ // // Define macros for our default policies, if they're not defined already: // // Special cases for exceptions disabled first: // #ifdef BOOST_NO_EXCEPTIONS # ifndef BOOST_MATH_DOMAIN_ERROR_POLICY # define BOOST_MATH_DOMAIN_ERROR_POLICY errno_on_error # endif # ifndef BOOST_MATH_POLE_ERROR_POLICY # define BOOST_MATH_POLE_ERROR_POLICY errno_on_error # endif # ifndef BOOST_MATH_OVERFLOW_ERROR_POLICY # define BOOST_MATH_OVERFLOW_ERROR_POLICY errno_on_error # endif # ifndef BOOST_MATH_EVALUATION_ERROR_POLICY # define BOOST_MATH_EVALUATION_ERROR_POLICY errno_on_error # endif # ifndef BOOST_MATH_ROUNDING_ERROR_POLICY # define BOOST_MATH_ROUNDING_ERROR_POLICY errno_on_error # endif #endif // // Then the regular cases: // #ifndef BOOST_MATH_DOMAIN_ERROR_POLICY #define BOOST_MATH_DOMAIN_ERROR_POLICY throw_on_error #endif #ifndef BOOST_MATH_POLE_ERROR_POLICY #define BOOST_MATH_POLE_ERROR_POLICY throw_on_error #endif #ifndef BOOST_MATH_OVERFLOW_ERROR_POLICY #define BOOST_MATH_OVERFLOW_ERROR_POLICY throw_on_error #endif #ifndef BOOST_MATH_EVALUATION_ERROR_POLICY #define BOOST_MATH_EVALUATION_ERROR_POLICY throw_on_error #endif #ifndef BOOST_MATH_ROUNDING_ERROR_POLICY #define BOOST_MATH_ROUNDING_ERROR_POLICY throw_on_error #endif #ifndef BOOST_MATH_UNDERFLOW_ERROR_POLICY #define BOOST_MATH_UNDERFLOW_ERROR_POLICY ignore_error #endif #ifndef BOOST_MATH_DENORM_ERROR_POLICY #define BOOST_MATH_DENORM_ERROR_POLICY ignore_error #endif #ifndef BOOST_MATH_INDETERMINATE_RESULT_ERROR_POLICY #define BOOST_MATH_INDETERMINATE_RESULT_ERROR_POLICY ignore_error #endif #ifndef BOOST_MATH_DIGITS10_POLICY #define BOOST_MATH_DIGITS10_POLICY 0 #endif #ifndef BOOST_MATH_PROMOTE_FLOAT_POLICY #define BOOST_MATH_PROMOTE_FLOAT_POLICY true #endif #ifndef BOOST_MATH_PROMOTE_DOUBLE_POLICY #ifdef BOOST_MATH_NO_LONG_DOUBLE_MATH_FUNCTIONS #define BOOST_MATH_PROMOTE_DOUBLE_POLICY false #else #define BOOST_MATH_PROMOTE_DOUBLE_POLICY true #endif #endif #ifndef BOOST_MATH_DISCRETE_QUANTILE_POLICY #define BOOST_MATH_DISCRETE_QUANTILE_POLICY integer_round_outwards #endif #ifndef BOOST_MATH_ASSERT_UNDEFINED_POLICY #define BOOST_MATH_ASSERT_UNDEFINED_POLICY true #endif #ifndef BOOST_MATH_MAX_SERIES_ITERATION_POLICY #define BOOST_MATH_MAX_SERIES_ITERATION_POLICY 1000000 #endif #ifndef BOOST_MATH_MAX_ROOT_ITERATION_POLICY #define BOOST_MATH_MAX_ROOT_ITERATION_POLICY 200 #endif #if !defined(BOOST_BORLANDC) #define BOOST_MATH_META_INT(type, name, Default)\ template <type N = Default> struct name : public boost::integral_constant<int, N>{};\ namespace detail{\ template <type N>\ char test_is_valid_arg(const name<N>*);\ char test_is_default_arg(const name<Default>*);\ template <class T> struct is_##name##_imp\ {\ template <type N> static char test(const name<N>*);\ static double test(...);\ BOOST_STATIC_CONSTANT(bool, value = sizeof(test(static_cast<T*>(0))) == 1);\ };\ }\ template <class T> struct is_##name : public boost::integral_constant<bool, ::boost::math::policies::detail::is_##name##_imp<T>::value>{}; #define BOOST_MATH_META_BOOL(name, Default)\ template <bool N = Default> struct name : public boost::integral_constant<bool, N>{};\ namespace detail{\ template <bool N>\ char test_is_valid_arg(const name<N>*);\ char test_is_default_arg(const name<Default>*);\ template <class T> struct is_##name##_imp\ {\ template <bool N> static char test(const name<N>*);\ static double test(...);\ BOOST_STATIC_CONSTANT(bool, value = sizeof(test(static_cast<T*>(0))) == 1);\ };\ }\ template <class T> struct is_##name : public boost::integral_constant<bool, ::boost::math::policies::detail::is_##name##_imp<T>::value>{}; #else #define BOOST_MATH_META_INT(Type, name, Default)\ template <Type N = Default> struct name : public boost::integral_constant<int, N>{};\ namespace detail{\ template <Type N>\ char test_is_valid_arg(const name<N>*);\ char test_is_default_arg(const name<Default>*);\ template <class T> struct is_##name##_tester\ {\ template <Type N> static char test(const name<N>&);\ static double test(...);\ };\ template <class T> struct is_##name##_imp\ {\ static T inst;\ BOOST_STATIC_CONSTANT(bool, value = sizeof( ::boost::math::policies::detail::is_##name##_tester<T>::test(inst)) == 1);\ };\ }\ template <class T> struct is_##name : public boost::integral_constant<bool, ::boost::math::policies::detail::is_##name##_imp<T>::value>\ {\ template <class U> struct apply{ typedef is_##name<U> type; };\ }; #define BOOST_MATH_META_BOOL(name, Default)\ template <bool N = Default> struct name : public boost::integral_constant<bool, N>{};\ namespace detail{\ template <bool N>\ char test_is_valid_arg(const name<N>*);\ char test_is_default_arg(const name<Default>*);\ template <class T> struct is_##name##_tester\ {\ template <bool N> static char test(const name<N>&);\ static double test(...);\ };\ template <class T> struct is_##name##_imp\ {\ static T inst;\ BOOST_STATIC_CONSTANT(bool, value = sizeof( ::boost::math::policies::detail::is_##name##_tester<T>::test(inst)) == 1);\ };\ }\ template <class T> struct is_##name : public boost::integral_constant<bool, ::boost::math::policies::detail::is_##name##_imp<T>::value>\ {\ template <class U> struct apply{ typedef is_##name<U> type; };\ }; #endif // // Begin by defining policy types for error handling: // enum error_policy_type { throw_on_error = 0, errno_on_error = 1, ignore_error = 2, user_error = 3 }; BOOST_MATH_META_INT(error_policy_type, domain_error, BOOST_MATH_DOMAIN_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, pole_error, BOOST_MATH_POLE_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, overflow_error, BOOST_MATH_OVERFLOW_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, underflow_error, BOOST_MATH_UNDERFLOW_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, denorm_error, BOOST_MATH_DENORM_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, evaluation_error, BOOST_MATH_EVALUATION_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, rounding_error, BOOST_MATH_ROUNDING_ERROR_POLICY) BOOST_MATH_META_INT(error_policy_type, indeterminate_result_error, BOOST_MATH_INDETERMINATE_RESULT_ERROR_POLICY) // // Policy types for internal promotion: // BOOST_MATH_META_BOOL(promote_float, BOOST_MATH_PROMOTE_FLOAT_POLICY) BOOST_MATH_META_BOOL(promote_double, BOOST_MATH_PROMOTE_DOUBLE_POLICY) BOOST_MATH_META_BOOL(assert_undefined, BOOST_MATH_ASSERT_UNDEFINED_POLICY) // // Policy types for discrete quantiles: // enum discrete_quantile_policy_type { real, integer_round_outwards, integer_round_inwards, integer_round_down, integer_round_up, integer_round_nearest }; BOOST_MATH_META_INT(discrete_quantile_policy_type, discrete_quantile, BOOST_MATH_DISCRETE_QUANTILE_POLICY) // // Precision: // BOOST_MATH_META_INT(int, digits10, BOOST_MATH_DIGITS10_POLICY) BOOST_MATH_META_INT(int, digits2, 0) // // Iterations: // BOOST_MATH_META_INT(unsigned long, max_series_iterations, BOOST_MATH_MAX_SERIES_ITERATION_POLICY) BOOST_MATH_META_INT(unsigned long, max_root_iterations, BOOST_MATH_MAX_ROOT_ITERATION_POLICY) // // Define the names for each possible policy: // #define BOOST_MATH_PARAMETER(name)\ BOOST_PARAMETER_TEMPLATE_KEYWORD(name##_name)\ BOOST_PARAMETER_NAME(name##_name) struct default_policy{}; namespace detail{ // // Trait to work out bits precision from digits10 and digits2: // template <class Digits10, class Digits2> struct precision { // // Now work out the precision: // typedef typename mpl::if_c< (Digits10::value == 0), digits2<0>, digits2<((Digits10::value + 1) * 1000L) / 301L> >::type digits2_type; public: #ifdef BOOST_BORLANDC typedef typename mpl::if_c< (Digits2::value > ::boost::math::policies::detail::precision<Digits10,Digits2>::digits2_type::value), Digits2, digits2_type>::type type; #else typedef typename mpl::if_c< (Digits2::value > digits2_type::value), Digits2, digits2_type>::type type; #endif }; template <class A, class B, bool b> struct select_result { typedef A type; }; template <class A, class B> struct select_result<A, B, false> { typedef typename mpl::deref<B>::type type; }; template <class Seq, class Pred, class DefaultType> struct find_arg { private: typedef typename mpl::find_if<Seq, Pred>::type iter; typedef typename mpl::end<Seq>::type end_type; public: typedef typename select_result< DefaultType, iter, ::boost::is_same<iter, end_type>::value>::type type; }; double test_is_valid_arg(...); double test_is_default_arg(...); char test_is_valid_arg(const default_policy*); char test_is_default_arg(const default_policy*); template <class T> struct is_valid_policy_imp { BOOST_STATIC_CONSTANT(bool, value = sizeof(::boost::math::policies::detail::test_is_valid_arg(static_cast<T*>(0))) == 1); }; template <class T> struct is_default_policy_imp { BOOST_STATIC_CONSTANT(bool, value = sizeof(::boost::math::policies::detail::test_is_default_arg(static_cast<T*>(0))) == 1); }; template <class T> struct is_valid_policy : public boost::integral_constant<bool, ::boost::math::policies::detail::is_valid_policy_imp<T>::value> {}; template <class T> struct is_default_policy : public boost::integral_constant<bool, ::boost::math::policies::detail::is_default_policy_imp<T>::value> { template <class U> struct apply { typedef is_default_policy<U> type; }; }; template <class Seq, class T, int N> struct append_N { typedef typename mpl::push_back<Seq, T>::type new_seq; typedef typename append_N<new_seq, T, N-1>::type type; }; template <class Seq, class T> struct append_N<Seq, T, 0> { typedef Seq type; }; // // Traits class to work out what template parameters our default // policy<> class will have when modified for forwarding: // template <bool f, bool d> struct default_args { typedef promote_float<false> arg1; typedef promote_double<false> arg2; }; template <> struct default_args<false, false> { typedef default_policy arg1; typedef default_policy arg2; }; template <> struct default_args<true, false> { typedef promote_float<false> arg1; typedef default_policy arg2; }; template <> struct default_args<false, true> { typedef promote_double<false> arg1; typedef default_policy arg2; }; typedef default_args<BOOST_MATH_PROMOTE_FLOAT_POLICY, BOOST_MATH_PROMOTE_DOUBLE_POLICY>::arg1 forwarding_arg1; typedef default_args<BOOST_MATH_PROMOTE_FLOAT_POLICY, BOOST_MATH_PROMOTE_DOUBLE_POLICY>::arg2 forwarding_arg2; } // detail // // Now define the policy type with enough arguments to handle all // the policies: // template <class A1 = default_policy, class A2 = default_policy, class A3 = default_policy, class A4 = default_policy, class A5 = default_policy, class A6 = default_policy, class A7 = default_policy, class A8 = default_policy, class A9 = default_policy, class A10 = default_policy, class A11 = default_policy, class A12 = default_policy, class A13 = default_policy> struct policy { private: // // Validate all our arguments: // BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A1>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A2>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A3>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A4>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A5>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A6>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A7>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A8>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A9>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A10>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A11>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A12>::value); BOOST_STATIC_ASSERT(::boost::math::policies::detail::is_valid_policy<A13>::value); // // Typelist of the arguments: // typedef mpl::list<A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13> arg_list; public: typedef typename detail::find_arg<arg_list, is_domain_error<mpl::_1>, domain_error<> >::type domain_error_type; typedef typename detail::find_arg<arg_list, is_pole_error<mpl::_1>, pole_error<> >::type pole_error_type; typedef typename detail::find_arg<arg_list, is_overflow_error<mpl::_1>, overflow_error<> >::type overflow_error_type; typedef typename detail::find_arg<arg_list, is_underflow_error<mpl::_1>, underflow_error<> >::type underflow_error_type; typedef typename detail::find_arg<arg_list, is_denorm_error<mpl::_1>, denorm_error<> >::type denorm_error_type; typedef typename detail::find_arg<arg_list, is_evaluation_error<mpl::_1>, evaluation_error<> >::type evaluation_error_type; typedef typename detail::find_arg<arg_list, is_rounding_error<mpl::_1>, rounding_error<> >::type rounding_error_type; typedef typename detail::find_arg<arg_list, is_indeterminate_result_error<mpl::_1>, indeterminate_result_error<> >::type indeterminate_result_error_type; private: // // Now work out the precision: // typedef typename detail::find_arg<arg_list, is_digits10<mpl::_1>, digits10<> >::type digits10_type; typedef typename detail::find_arg<arg_list, is_digits2<mpl::_1>, digits2<> >::type bits_precision_type; public: typedef typename detail::precision<digits10_type, bits_precision_type>::type precision_type; // // Internal promotion: // typedef typename detail::find_arg<arg_list, is_promote_float<mpl::_1>, promote_float<> >::type promote_float_type; typedef typename detail::find_arg<arg_list, is_promote_double<mpl::_1>, promote_double<> >::type promote_double_type; // // Discrete quantiles: // typedef typename detail::find_arg<arg_list, is_discrete_quantile<mpl::_1>, discrete_quantile<> >::type discrete_quantile_type; // // Mathematically undefined properties: // typedef typename detail::find_arg<arg_list, is_assert_undefined<mpl::_1>, assert_undefined<> >::type assert_undefined_type; // // Max iterations: // typedef typename detail::find_arg<arg_list, is_max_series_iterations<mpl::_1>, max_series_iterations<> >::type max_series_iterations_type; typedef typename detail::find_arg<arg_list, is_max_root_iterations<mpl::_1>, max_root_iterations<> >::type max_root_iterations_type; }; // // These full specializations are defined to reduce the amount of // template instantiations that have to take place when using the default // policies, they have quite a large impact on compile times: // template <> struct policy<default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy> { public: typedef domain_error<> domain_error_type; typedef pole_error<> pole_error_type; typedef overflow_error<> overflow_error_type; typedef underflow_error<> underflow_error_type; typedef denorm_error<> denorm_error_type; typedef evaluation_error<> evaluation_error_type; typedef rounding_error<> rounding_error_type; typedef indeterminate_result_error<> indeterminate_result_error_type; #if BOOST_MATH_DIGITS10_POLICY == 0 typedef digits2<> precision_type; #else typedef detail::precision<digits10<>, digits2<> >::type precision_type; #endif typedef promote_float<> promote_float_type; typedef promote_double<> promote_double_type; typedef discrete_quantile<> discrete_quantile_type; typedef assert_undefined<> assert_undefined_type; typedef max_series_iterations<> max_series_iterations_type; typedef max_root_iterations<> max_root_iterations_type; }; template <> struct policy<detail::forwarding_arg1, detail::forwarding_arg2, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy> { public: typedef domain_error<> domain_error_type; typedef pole_error<> pole_error_type; typedef overflow_error<> overflow_error_type; typedef underflow_error<> underflow_error_type; typedef denorm_error<> denorm_error_type; typedef evaluation_error<> evaluation_error_type; typedef rounding_error<> rounding_error_type; typedef indeterminate_result_error<> indeterminate_result_error_type; #if BOOST_MATH_DIGITS10_POLICY == 0 typedef digits2<> precision_type; #else typedef detail::precision<digits10<>, digits2<> >::type precision_type; #endif typedef promote_float<false> promote_float_type; typedef promote_double<false> promote_double_type; typedef discrete_quantile<> discrete_quantile_type; typedef assert_undefined<> assert_undefined_type; typedef max_series_iterations<> max_series_iterations_type; typedef max_root_iterations<> max_root_iterations_type; }; template <class Policy, class A1 = default_policy, class A2 = default_policy, class A3 = default_policy, class A4 = default_policy, class A5 = default_policy, class A6 = default_policy, class A7 = default_policy, class A8 = default_policy, class A9 = default_policy, class A10 = default_policy, class A11 = default_policy, class A12 = default_policy, class A13 = default_policy> struct normalise { private: typedef mpl::list<A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13> arg_list; typedef typename detail::find_arg<arg_list, is_domain_error<mpl::_1>, typename Policy::domain_error_type >::type domain_error_type; typedef typename detail::find_arg<arg_list, is_pole_error<mpl::_1>, typename Policy::pole_error_type >::type pole_error_type; typedef typename detail::find_arg<arg_list, is_overflow_error<mpl::_1>, typename Policy::overflow_error_type >::type overflow_error_type; typedef typename detail::find_arg<arg_list, is_underflow_error<mpl::_1>, typename Policy::underflow_error_type >::type underflow_error_type; typedef typename detail::find_arg<arg_list, is_denorm_error<mpl::_1>, typename Policy::denorm_error_type >::type denorm_error_type; typedef typename detail::find_arg<arg_list, is_evaluation_error<mpl::_1>, typename Policy::evaluation_error_type >::type evaluation_error_type; typedef typename detail::find_arg<arg_list, is_rounding_error<mpl::_1>, typename Policy::rounding_error_type >::type rounding_error_type; typedef typename detail::find_arg<arg_list, is_indeterminate_result_error<mpl::_1>, typename Policy::indeterminate_result_error_type >::type indeterminate_result_error_type; // // Now work out the precision: // typedef typename detail::find_arg<arg_list, is_digits10<mpl::_1>, digits10<> >::type digits10_type; typedef typename detail::find_arg<arg_list, is_digits2<mpl::_1>, typename Policy::precision_type >::type bits_precision_type; typedef typename detail::precision<digits10_type, bits_precision_type>::type precision_type; // // Internal promotion: // typedef typename detail::find_arg<arg_list, is_promote_float<mpl::_1>, typename Policy::promote_float_type >::type promote_float_type; typedef typename detail::find_arg<arg_list, is_promote_double<mpl::_1>, typename Policy::promote_double_type >::type promote_double_type; // // Discrete quantiles: // typedef typename detail::find_arg<arg_list, is_discrete_quantile<mpl::_1>, typename Policy::discrete_quantile_type >::type discrete_quantile_type; // // Mathematically undefined properties: // typedef typename detail::find_arg<arg_list, is_assert_undefined<mpl::_1>, typename Policy::assert_undefined_type >::type assert_undefined_type; // // Max iterations: // typedef typename detail::find_arg<arg_list, is_max_series_iterations<mpl::_1>, typename Policy::max_series_iterations_type>::type max_series_iterations_type; typedef typename detail::find_arg<arg_list, is_max_root_iterations<mpl::_1>, typename Policy::max_root_iterations_type>::type max_root_iterations_type; // // Define a typelist of the policies: // typedef mpl::vector< domain_error_type, pole_error_type, overflow_error_type, underflow_error_type, denorm_error_type, evaluation_error_type, rounding_error_type, indeterminate_result_error_type, precision_type, promote_float_type, promote_double_type, discrete_quantile_type, assert_undefined_type, max_series_iterations_type, max_root_iterations_type> result_list; // // Remove all the policies that are the same as the default: // typedef typename mpl::remove_if<result_list, detail::is_default_policy<mpl::_> >::type reduced_list; // // Pad out the list with defaults: // typedef typename detail::append_N<reduced_list, default_policy, (14 - ::boost::mpl::size<reduced_list>::value)>::type result_type; public: typedef policy< typename mpl::at<result_type, boost::integral_constant<int, 0> >::type, typename mpl::at<result_type, boost::integral_constant<int, 1> >::type, typename mpl::at<result_type, boost::integral_constant<int, 2> >::type, typename mpl::at<result_type, boost::integral_constant<int, 3> >::type, typename mpl::at<result_type, boost::integral_constant<int, 4> >::type, typename mpl::at<result_type, boost::integral_constant<int, 5> >::type, typename mpl::at<result_type, boost::integral_constant<int, 6> >::type, typename mpl::at<result_type, boost::integral_constant<int, 7> >::type, typename mpl::at<result_type, boost::integral_constant<int, 8> >::type, typename mpl::at<result_type, boost::integral_constant<int, 9> >::type, typename mpl::at<result_type, boost::integral_constant<int, 10> >::type, typename mpl::at<result_type, boost::integral_constant<int, 11> >::type, typename mpl::at<result_type, boost::integral_constant<int, 12> >::type > type; }; // // Full specialisation to speed up compilation of the common case: // template <> struct normalise<policy<>, promote_float<false>, promote_double<false>, discrete_quantile<>, assert_undefined<>, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy> { typedef policy<detail::forwarding_arg1, detail::forwarding_arg2> type; }; template <> struct normalise<policy<detail::forwarding_arg1, detail::forwarding_arg2>, promote_float<false>, promote_double<false>, discrete_quantile<>, assert_undefined<>, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy, default_policy> { typedef policy<detail::forwarding_arg1, detail::forwarding_arg2> type; }; inline BOOST_MATH_CONSTEXPR policy<> make_policy() BOOST_NOEXCEPT { return policy<>(); } template <class A1> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1>::type make_policy(const A1&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1>::type result_type; return result_type(); } template <class A1, class A2> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2>::type make_policy(const A1&, const A2&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2>::type result_type; return result_type(); } template <class A1, class A2, class A3> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3>::type make_policy(const A1&, const A2&, const A3&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4>::type make_policy(const A1&, const A2&, const A3&, const A4&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6, class A7> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&, const A7&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&, const A7&, const A8&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&, const A7&, const A8&, const A9&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9, class A10> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&, const A7&, const A8&, const A9&, const A10&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10>::type result_type; return result_type(); } template <class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9, class A10, class A11> inline BOOST_MATH_CONSTEXPR typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10, A11>::type make_policy(const A1&, const A2&, const A3&, const A4&, const A5&, const A6&, const A7&, const A8&, const A9&, const A10&, const A11&) BOOST_NOEXCEPT { typedef typename normalise<policy<>, A1, A2, A3, A4, A5, A6, A7, A8, A9, A10, A11>::type result_type; return result_type(); } // // Traits class to handle internal promotion: // template <class Real, class Policy> struct evaluation { typedef Real type; }; template <class Policy> struct evaluation<float, Policy> { typedef typename mpl::if_<typename Policy::promote_float_type, double, float>::type type; }; template <class Policy> struct evaluation<double, Policy> { typedef typename mpl::if_<typename Policy::promote_double_type, long double, double>::type type; }; #ifdef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS template <class Real> struct basic_digits : public boost::integral_constant<int, 0>{ }; template <> struct basic_digits<float> : public boost::integral_constant<int, FLT_MANT_DIG>{ }; template <> struct basic_digits<double> : public boost::integral_constant<int, DBL_MANT_DIG>{ }; template <> struct basic_digits<long double> : public boost::integral_constant<int, LDBL_MANT_DIG>{ }; template <class Real, class Policy> struct precision { BOOST_STATIC_ASSERT( ::std::numeric_limits<Real>::radix == 2); typedef typename Policy::precision_type precision_type; typedef basic_digits<Real> digits_t; typedef typename mpl::if_< mpl::equal_to<digits_t, boost::integral_constant<int, 0> >, // Possibly unknown precision: precision_type, typename mpl::if_< mpl::or_<mpl::less_equal<digits_t, precision_type>, mpl::less_equal<precision_type, boost::integral_constant<int, 0> > >, // Default case, full precision for RealType: digits2< ::std::numeric_limits<Real>::digits>, // User customised precision: precision_type >::type >::type type; }; template <class Policy> struct precision<float, Policy> { typedef digits2<FLT_MANT_DIG> type; }; template <class Policy> struct precision<double, Policy> { typedef digits2<DBL_MANT_DIG> type; }; template <class Policy> struct precision<long double, Policy> { typedef digits2<LDBL_MANT_DIG> type; }; #else template <class Real, class Policy> struct precision { BOOST_STATIC_ASSERT((::std::numeric_limits<Real>::radix == 2) || ((::std::numeric_limits<Real>::is_specialized == 0) || (::std::numeric_limits<Real>::digits == 0))); #ifndef BOOST_BORLANDC typedef typename Policy::precision_type precision_type; typedef typename mpl::if_c< ((::std::numeric_limits<Real>::is_specialized == 0) || (::std::numeric_limits<Real>::digits == 0)), // Possibly unknown precision: precision_type, typename mpl::if_c< ((::std::numeric_limits<Real>::digits <= precision_type::value) || (Policy::precision_type::value <= 0)), // Default case, full precision for RealType: digits2< ::std::numeric_limits<Real>::digits>, // User customised precision: precision_type >::type >::type type; #else typedef typename Policy::precision_type precision_type; typedef boost::integral_constant<int, ::std::numeric_limits<Real>::digits> digits_t; typedef boost::integral_constant<bool, ::std::numeric_limits<Real>::is_specialized> spec_t; typedef typename mpl::if_< mpl::or_<mpl::equal_to<spec_t, boost::true_type>, mpl::equal_to<digits_t, boost::integral_constant<int, 0> > >, // Possibly unknown precision: precision_type, typename mpl::if_< mpl::or_<mpl::less_equal<digits_t, precision_type>, mpl::less_equal<precision_type, boost::integral_constant<int, 0> > >, // Default case, full precision for RealType: digits2< ::std::numeric_limits<Real>::digits>, // User customised precision: precision_type >::type >::type type; #endif }; #endif #ifdef BOOST_MATH_USE_FLOAT128 template <class Policy> struct precision<BOOST_MATH_FLOAT128_TYPE, Policy> { typedef boost::integral_constant<int, 113> type; }; #endif namespace detail{ template <class T, class Policy> inline BOOST_MATH_CONSTEXPR int digits_imp(boost::true_type const&) BOOST_NOEXCEPT { #ifndef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS BOOST_STATIC_ASSERT( ::std::numeric_limits<T>::is_specialized); #else BOOST_ASSERT(::std::numeric_limits<T>::is_specialized); #endif typedef typename boost::math::policies::precision<T, Policy>::type p_t; return p_t::value; } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR int digits_imp(boost::false_type const&) BOOST_NOEXCEPT { return tools::digits<T>(); } } // namespace detail template <class T, class Policy> inline BOOST_MATH_CONSTEXPR int digits(BOOST_MATH_EXPLICIT_TEMPLATE_TYPE(T)) BOOST_NOEXCEPT { typedef boost::integral_constant<bool, std::numeric_limits<T>::is_specialized > tag_type; return detail::digits_imp<T, Policy>(tag_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR int digits_base10(BOOST_MATH_EXPLICIT_TEMPLATE_TYPE(T)) BOOST_NOEXCEPT { return boost::math::policies::digits<T, Policy>() * 301 / 1000L; } template <class Policy> inline BOOST_MATH_CONSTEXPR unsigned long get_max_series_iterations() BOOST_NOEXCEPT { typedef typename Policy::max_series_iterations_type iter_type; return iter_type::value; } template <class Policy> inline BOOST_MATH_CONSTEXPR unsigned long get_max_root_iterations() BOOST_NOEXCEPT { typedef typename Policy::max_root_iterations_type iter_type; return iter_type::value; } namespace detail{ template <class T, class Digits, class Small, class Default> struct series_factor_calc { static T get() BOOST_MATH_NOEXCEPT(T) { return ldexp(T(1.0), 1 - Digits::value); } }; template <class T, class Digits> struct series_factor_calc<T, Digits, boost::true_type, boost::true_type> { static BOOST_MATH_CONSTEXPR T get() BOOST_MATH_NOEXCEPT(T) { return boost::math::tools::epsilon<T>(); } }; template <class T, class Digits> struct series_factor_calc<T, Digits, boost::true_type, boost::false_type> { static BOOST_MATH_CONSTEXPR T get() BOOST_MATH_NOEXCEPT(T) { return 1 / static_cast<T>(static_cast<boost::uintmax_t>(1u) << (Digits::value - 1)); } }; template <class T, class Digits> struct series_factor_calc<T, Digits, boost::false_type, boost::true_type> { static BOOST_MATH_CONSTEXPR T get() BOOST_MATH_NOEXCEPT(T) { return boost::math::tools::epsilon<T>(); } }; template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T get_epsilon_imp(boost::true_type const&) BOOST_MATH_NOEXCEPT(T) { #ifndef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS BOOST_STATIC_ASSERT( ::std::numeric_limits<T>::is_specialized); BOOST_STATIC_ASSERT( ::std::numeric_limits<T>::radix == 2); #else BOOST_ASSERT(::std::numeric_limits<T>::is_specialized); BOOST_ASSERT(::std::numeric_limits<T>::radix == 2); #endif typedef typename boost::math::policies::precision<T, Policy>::type p_t; typedef boost::integral_constant<bool, p_t::value <= std::numeric_limits<boost::uintmax_t>::digits> is_small_int; typedef boost::integral_constant<bool, p_t::value >= std::numeric_limits<T>::digits> is_default_value; return series_factor_calc<T, p_t, is_small_int, is_default_value>::get(); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T get_epsilon_imp(boost::false_type const&) BOOST_MATH_NOEXCEPT(T) { return tools::epsilon<T>(); } } // namespace detail template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T get_epsilon(BOOST_MATH_EXPLICIT_TEMPLATE_TYPE(T)) BOOST_MATH_NOEXCEPT(T) { typedef boost::integral_constant<bool, (std::numeric_limits<T>::is_specialized && (std::numeric_limits<T>::radix == 2)) > tag_type; return detail::get_epsilon_imp<T, Policy>(tag_type()); } namespace detail{ template <class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9, class A10, class A11> char test_is_policy(const policy<A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11>*); double test_is_policy(...); template <class P> struct is_policy_imp { BOOST_STATIC_CONSTANT(bool, value = (sizeof(::boost::math::policies::detail::test_is_policy(static_cast<P*>(0))) == 1)); }; } template <class P> struct is_policy : public boost::integral_constant<bool, ::boost::math::policies::detail::is_policy_imp<P>::value> {}; // // Helper traits class for distribution error handling: // template <class Policy> struct constructor_error_check { typedef typename Policy::domain_error_type domain_error_type; typedef typename mpl::if_c< (domain_error_type::value == throw_on_error) || (domain_error_type::value == user_error) || (domain_error_type::value == errno_on_error), boost::true_type, boost::false_type>::type type; }; template <class Policy> struct method_error_check { typedef typename Policy::domain_error_type domain_error_type; typedef typename mpl::if_c< (domain_error_type::value == throw_on_error) && (domain_error_type::value != user_error), boost::false_type, boost::true_type>::type type; }; // // Does the Policy ever throw on error? // template <class Policy> struct is_noexcept_error_policy { typedef typename Policy::domain_error_type t1; typedef typename Policy::pole_error_type t2; typedef typename Policy::overflow_error_type t3; typedef typename Policy::underflow_error_type t4; typedef typename Policy::denorm_error_type t5; typedef typename Policy::evaluation_error_type t6; typedef typename Policy::rounding_error_type t7; typedef typename Policy::indeterminate_result_error_type t8; BOOST_STATIC_CONSTANT(bool, value = ((t1::value != throw_on_error) && (t1::value != user_error) && (t2::value != throw_on_error) && (t2::value != user_error) && (t3::value != throw_on_error) && (t3::value != user_error) && (t4::value != throw_on_error) && (t4::value != user_error) && (t5::value != throw_on_error) && (t5::value != user_error) && (t6::value != throw_on_error) && (t6::value != user_error) && (t7::value != throw_on_error) && (t7::value != user_error) && (t8::value != throw_on_error) && (t8::value != user_error))); }; }}} // namespaces #endif // BOOST_MATH_POLICY_HPP PK 7�!\�X} } error_handling.hppnu �[��� // Copyright John Maddock 2007. // Copyright Paul A. Bristow 2007. // Use, modification and distribution are subject to the // Boost Software License, Version 1.0. (See accompanying file // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_MATH_POLICY_ERROR_HANDLING_HPP #define BOOST_MATH_POLICY_ERROR_HANDLING_HPP #include <stdexcept> #include <iomanip> #include <string> #include <cstring> #include <typeinfo> #include <cerrno> #include <boost/config/no_tr1/complex.hpp> #include <boost/config/no_tr1/cmath.hpp> #include <stdexcept> #include <boost/math/tools/config.hpp> #include <boost/math/policies/policy.hpp> #include <boost/math/tools/precision.hpp> #include <boost/throw_exception.hpp> #include <boost/cstdint.hpp> #ifdef BOOST_MSVC # pragma warning(push) // Quiet warnings in boost/format.hpp # pragma warning(disable: 4996) // _SCL_SECURE_NO_DEPRECATE # pragma warning(disable: 4512) // assignment operator could not be generated. # pragma warning(disable: 4127) // conditional expression is constant // And warnings in error handling: # pragma warning(disable: 4702) // unreachable code. // Note that this only occurs when the compiler can deduce code is unreachable, // for example when policy macros are used to ignore errors rather than throw. #endif #include <sstream> namespace boost{ namespace math{ class evaluation_error : public std::runtime_error { public: evaluation_error(const std::string& s) : std::runtime_error(s){} }; class rounding_error : public std::runtime_error { public: rounding_error(const std::string& s) : std::runtime_error(s){} }; namespace policies{ // // Forward declarations of user error handlers, // it's up to the user to provide the definition of these: // template <class T> T user_domain_error(const char* function, const char* message, const T& val); template <class T> T user_pole_error(const char* function, const char* message, const T& val); template <class T> T user_overflow_error(const char* function, const char* message, const T& val); template <class T> T user_underflow_error(const char* function, const char* message, const T& val); template <class T> T user_denorm_error(const char* function, const char* message, const T& val); template <class T> T user_evaluation_error(const char* function, const char* message, const T& val); template <class T, class TargetType> T user_rounding_error(const char* function, const char* message, const T& val, const TargetType& t); template <class T> T user_indeterminate_result_error(const char* function, const char* message, const T& val); namespace detail { template <class T> std::string prec_format(const T& val) { typedef typename boost::math::policies::precision<T, boost::math::policies::policy<> >::type prec_type; std::stringstream ss; if(prec_type::value) { int prec = 2 + (prec_type::value * 30103UL) / 100000UL; ss << std::setprecision(prec); } ss << val; return ss.str(); } inline void replace_all_in_string(std::string& result, const char* what, const char* with) { std::string::size_type pos = 0; std::string::size_type slen = std::strlen(what); std::string::size_type rlen = std::strlen(with); while((pos = result.find(what, pos)) != std::string::npos) { result.replace(pos, slen, with); pos += rlen; } } template <class T> inline const char* name_of() { #ifndef BOOST_NO_RTTI return typeid(T).name(); #else return "unknown"; #endif } template <> inline const char* name_of<float>(){ return "float"; } template <> inline const char* name_of<double>(){ return "double"; } template <> inline const char* name_of<long double>(){ return "long double"; } #ifdef BOOST_MATH_USE_FLOAT128 template <> inline const char* name_of<BOOST_MATH_FLOAT128_TYPE>() { return "__float128"; } #endif template <class E, class T> void raise_error(const char* pfunction, const char* message) { if(pfunction == 0) pfunction = "Unknown function operating on type %1%"; if(message == 0) message = "Cause unknown"; std::string function(pfunction); std::string msg("Error in function "); #ifndef BOOST_NO_RTTI replace_all_in_string(function, "%1%", boost::math::policies::detail::name_of<T>()); #else replace_all_in_string(function, "%1%", "Unknown"); #endif msg += function; msg += ": "; msg += message; E e(msg); boost::throw_exception(e); } template <class E, class T> void raise_error(const char* pfunction, const char* pmessage, const T& val) { if(pfunction == 0) pfunction = "Unknown function operating on type %1%"; if(pmessage == 0) pmessage = "Cause unknown: error caused by bad argument with value %1%"; std::string function(pfunction); std::string message(pmessage); std::string msg("Error in function "); #ifndef BOOST_NO_RTTI replace_all_in_string(function, "%1%", boost::math::policies::detail::name_of<T>()); #else replace_all_in_string(function, "%1%", "Unknown"); #endif msg += function; msg += ": "; std::string sval = prec_format(val); replace_all_in_string(message, "%1%", sval.c_str()); msg += message; E e(msg); boost::throw_exception(e); } template <class T> inline T raise_domain_error( const char* function, const char* message, const T& val, const ::boost::math::policies::domain_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::domain_error, T>(function, message, val); // we never get here: return std::numeric_limits<T>::quiet_NaN(); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_domain_error( const char* , const char* , const T& , const ::boost::math::policies::domain_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return std::numeric_limits<T>::quiet_NaN(); } template <class T> inline T raise_domain_error( const char* , const char* , const T& , const ::boost::math::policies::domain_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = EDOM; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return std::numeric_limits<T>::quiet_NaN(); } template <class T> inline T raise_domain_error( const char* function, const char* message, const T& val, const ::boost::math::policies::domain_error< ::boost::math::policies::user_error>&) { return user_domain_error(function, message, val); } template <class T> inline T raise_pole_error( const char* function, const char* message, const T& val, const ::boost::math::policies::pole_error< ::boost::math::policies::throw_on_error>&) { return boost::math::policies::detail::raise_domain_error(function, message, val, ::boost::math::policies::domain_error< ::boost::math::policies::throw_on_error>()); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_pole_error( const char* function, const char* message, const T& val, const ::boost::math::policies::pole_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { return ::boost::math::policies::detail::raise_domain_error(function, message, val, ::boost::math::policies::domain_error< ::boost::math::policies::ignore_error>()); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_pole_error( const char* function, const char* message, const T& val, const ::boost::math::policies::pole_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { return ::boost::math::policies::detail::raise_domain_error(function, message, val, ::boost::math::policies::domain_error< ::boost::math::policies::errno_on_error>()); } template <class T> inline T raise_pole_error( const char* function, const char* message, const T& val, const ::boost::math::policies::pole_error< ::boost::math::policies::user_error>&) { return user_pole_error(function, message, val); } template <class T> inline T raise_overflow_error( const char* function, const char* message, const ::boost::math::policies::overflow_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::overflow_error, T>(function, message ? message : "numeric overflow"); // We should never get here: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline T raise_overflow_error( const char* function, const char* message, const T& val, const ::boost::math::policies::overflow_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::overflow_error, T>(function, message ? message : "numeric overflow", val); // We should never get here: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_overflow_error( const char* , const char* , const ::boost::math::policies::overflow_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_overflow_error( const char* , const char* , const T&, const ::boost::math::policies::overflow_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline T raise_overflow_error( const char* , const char* , const ::boost::math::policies::overflow_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline T raise_overflow_error( const char* , const char* , const T&, const ::boost::math::policies::overflow_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return std::numeric_limits<T>::has_infinity ? std::numeric_limits<T>::infinity() : boost::math::tools::max_value<T>(); } template <class T> inline T raise_overflow_error( const char* function, const char* message, const ::boost::math::policies::overflow_error< ::boost::math::policies::user_error>&) { return user_overflow_error(function, message, std::numeric_limits<T>::infinity()); } template <class T> inline T raise_overflow_error( const char* function, const char* message, const T& val, const ::boost::math::policies::overflow_error< ::boost::math::policies::user_error>&) { std::string m(message ? message : ""); std::string sval = prec_format(val); replace_all_in_string(m, "%1%", sval.c_str()); return user_overflow_error(function, m.c_str(), std::numeric_limits<T>::infinity()); } template <class T> inline T raise_underflow_error( const char* function, const char* message, const ::boost::math::policies::underflow_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::underflow_error, T>(function, message ? message : "numeric underflow"); // We should never get here: return 0; } template <class T> inline BOOST_MATH_CONSTEXPR T raise_underflow_error( const char* , const char* , const ::boost::math::policies::underflow_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return T(0); } template <class T> inline T raise_underflow_error( const char* /* function */, const char* /* message */, const ::boost::math::policies::underflow_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return T(0); } template <class T> inline T raise_underflow_error( const char* function, const char* message, const ::boost::math::policies::underflow_error< ::boost::math::policies::user_error>&) { return user_underflow_error(function, message, T(0)); } template <class T> inline T raise_denorm_error( const char* function, const char* message, const T& /* val */, const ::boost::math::policies::denorm_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::underflow_error, T>(function, message ? message : "denormalised result"); // we never get here: return T(0); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_denorm_error( const char* , const char* , const T& val, const ::boost::math::policies::denorm_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return val; } template <class T> inline T raise_denorm_error( const char* , const char* , const T& val, const ::boost::math::policies::denorm_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return val; } template <class T> inline T raise_denorm_error( const char* function, const char* message, const T& val, const ::boost::math::policies::denorm_error< ::boost::math::policies::user_error>&) { return user_denorm_error(function, message, val); } template <class T> inline T raise_evaluation_error( const char* function, const char* message, const T& val, const ::boost::math::policies::evaluation_error< ::boost::math::policies::throw_on_error>&) { raise_error<boost::math::evaluation_error, T>(function, message, val); // we never get here: return T(0); } template <class T> inline BOOST_MATH_CONSTEXPR T raise_evaluation_error( const char* , const char* , const T& val, const ::boost::math::policies::evaluation_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return val; } template <class T> inline T raise_evaluation_error( const char* , const char* , const T& val, const ::boost::math::policies::evaluation_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = EDOM; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return val; } template <class T> inline T raise_evaluation_error( const char* function, const char* message, const T& val, const ::boost::math::policies::evaluation_error< ::boost::math::policies::user_error>&) { return user_evaluation_error(function, message, val); } template <class T, class TargetType> inline TargetType raise_rounding_error( const char* function, const char* message, const T& val, const TargetType&, const ::boost::math::policies::rounding_error< ::boost::math::policies::throw_on_error>&) { raise_error<boost::math::rounding_error, T>(function, message, val); // we never get here: return TargetType(0); } template <class T, class TargetType> inline BOOST_MATH_CONSTEXPR TargetType raise_rounding_error( const char* , const char* , const T& val, const TargetType&, const ::boost::math::policies::rounding_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: BOOST_STATIC_ASSERT(std::numeric_limits<TargetType>::is_specialized); return val > 0 ? (std::numeric_limits<TargetType>::max)() : (std::numeric_limits<TargetType>::is_integer ? (std::numeric_limits<TargetType>::min)() : -(std::numeric_limits<TargetType>::max)()); } template <class T, class TargetType> inline TargetType raise_rounding_error( const char* , const char* , const T& val, const TargetType&, const ::boost::math::policies::rounding_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: BOOST_STATIC_ASSERT(std::numeric_limits<TargetType>::is_specialized); return val > 0 ? (std::numeric_limits<TargetType>::max)() : (std::numeric_limits<TargetType>::is_integer ? (std::numeric_limits<TargetType>::min)() : -(std::numeric_limits<TargetType>::max)()); } template <class T> inline T raise_rounding_error( const char* , const char* , const T& val, const T&, const ::boost::math::policies::rounding_error< ::boost::math::policies::errno_on_error>&) BOOST_MATH_NOEXCEPT(T) { errno = ERANGE; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return val > 0 ? boost::math::tools::max_value<T>() : -boost::math::tools::max_value<T>(); } template <class T, class TargetType> inline TargetType raise_rounding_error( const char* function, const char* message, const T& val, const TargetType& t, const ::boost::math::policies::rounding_error< ::boost::math::policies::user_error>&) { return user_rounding_error(function, message, val, t); } template <class T, class R> inline T raise_indeterminate_result_error( const char* function, const char* message, const T& val, const R& , const ::boost::math::policies::indeterminate_result_error< ::boost::math::policies::throw_on_error>&) { raise_error<std::domain_error, T>(function, message, val); // we never get here: return std::numeric_limits<T>::quiet_NaN(); } template <class T, class R> inline BOOST_MATH_CONSTEXPR T raise_indeterminate_result_error( const char* , const char* , const T& , const R& result, const ::boost::math::policies::indeterminate_result_error< ::boost::math::policies::ignore_error>&) BOOST_MATH_NOEXCEPT(T) { // This may or may not do the right thing, but the user asked for the error // to be ignored so here we go anyway: return result; } template <class T, class R> inline T raise_indeterminate_result_error( const char* , const char* , const T& , const R& result, const ::boost::math::policies::indeterminate_result_error< ::boost::math::policies::errno_on_error>&) { errno = EDOM; // This may or may not do the right thing, but the user asked for the error // to be silent so here we go anyway: return result; } template <class T, class R> inline T raise_indeterminate_result_error( const char* function, const char* message, const T& val, const R& , const ::boost::math::policies::indeterminate_result_error< ::boost::math::policies::user_error>&) { return user_indeterminate_result_error(function, message, val); } } // namespace detail template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_domain_error(const char* function, const char* message, const T& val, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::domain_error_type policy_type; return detail::raise_domain_error( function, message ? message : "Domain Error evaluating function at %1%", val, policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_pole_error(const char* function, const char* message, const T& val, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::pole_error_type policy_type; return detail::raise_pole_error( function, message ? message : "Evaluation of function at pole %1%", val, policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_overflow_error(const char* function, const char* message, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::overflow_error_type policy_type; return detail::raise_overflow_error<T>( function, message ? message : "Overflow Error", policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_overflow_error(const char* function, const char* message, const T& val, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::overflow_error_type policy_type; return detail::raise_overflow_error( function, message ? message : "Overflow evaluating function at %1%", val, policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_underflow_error(const char* function, const char* message, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::underflow_error_type policy_type; return detail::raise_underflow_error<T>( function, message ? message : "Underflow Error", policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_denorm_error(const char* function, const char* message, const T& val, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::denorm_error_type policy_type; return detail::raise_denorm_error<T>( function, message ? message : "Denorm Error", val, policy_type()); } template <class T, class Policy> inline BOOST_MATH_CONSTEXPR T raise_evaluation_error(const char* function, const char* message, const T& val, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::evaluation_error_type policy_type; return detail::raise_evaluation_error( function, message ? message : "Internal Evaluation Error, best value so far was %1%", val, policy_type()); } template <class T, class TargetType, class Policy> inline BOOST_MATH_CONSTEXPR TargetType raise_rounding_error(const char* function, const char* message, const T& val, const TargetType& t, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::rounding_error_type policy_type; return detail::raise_rounding_error( function, message ? message : "Value %1% can not be represented in the target integer type.", val, t, policy_type()); } template <class T, class R, class Policy> inline BOOST_MATH_CONSTEXPR T raise_indeterminate_result_error(const char* function, const char* message, const T& val, const R& result, const Policy&) BOOST_NOEXCEPT_IF(is_noexcept_error_policy<Policy>::value && BOOST_MATH_IS_FLOAT(T)) { typedef typename Policy::indeterminate_result_error_type policy_type; return detail::raise_indeterminate_result_error( function, message ? message : "Indeterminate result with value %1%", val, result, policy_type()); } // // checked_narrowing_cast: // namespace detail { template <class R, class T, class Policy> inline bool check_overflow(T val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { BOOST_MATH_STD_USING if(fabs(val) > tools::max_value<R>()) { boost::math::policies::detail::raise_overflow_error<R>(function, 0, pol); *result = static_cast<R>(val); return true; } return false; } template <class R, class T, class Policy> inline bool check_overflow(std::complex<T> val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { typedef typename R::value_type r_type; r_type re, im; bool r = check_overflow<r_type>(val.real(), &re, function, pol); r = check_overflow<r_type>(val.imag(), &im, function, pol) || r; *result = R(re, im); return r; } template <class R, class T, class Policy> inline bool check_underflow(T val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { if((val != 0) && (static_cast<R>(val) == 0)) { *result = static_cast<R>(boost::math::policies::detail::raise_underflow_error<R>(function, 0, pol)); return true; } return false; } template <class R, class T, class Policy> inline bool check_underflow(std::complex<T> val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { typedef typename R::value_type r_type; r_type re, im; bool r = check_underflow<r_type>(val.real(), &re, function, pol); r = check_underflow<r_type>(val.imag(), &im, function, pol) || r; *result = R(re, im); return r; } template <class R, class T, class Policy> inline bool check_denorm(T val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { BOOST_MATH_STD_USING if((fabs(val) < static_cast<T>(tools::min_value<R>())) && (static_cast<R>(val) != 0)) { *result = static_cast<R>(boost::math::policies::detail::raise_denorm_error<R>(function, 0, static_cast<R>(val), pol)); return true; } return false; } template <class R, class T, class Policy> inline bool check_denorm(std::complex<T> val, R* result, const char* function, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && (Policy::value != throw_on_error) && (Policy::value != user_error)) { typedef typename R::value_type r_type; r_type re, im; bool r = check_denorm<r_type>(val.real(), &re, function, pol); r = check_denorm<r_type>(val.imag(), &im, function, pol) || r; *result = R(re, im); return r; } // Default instantiations with ignore_error policy. template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_overflow(T /* val */, R* /* result */, const char* /* function */, const overflow_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_overflow(std::complex<T> /* val */, R* /* result */, const char* /* function */, const overflow_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_underflow(T /* val */, R* /* result */, const char* /* function */, const underflow_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_underflow(std::complex<T> /* val */, R* /* result */, const char* /* function */, const underflow_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_denorm(T /* val */, R* /* result*/, const char* /* function */, const denorm_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } template <class R, class T> inline BOOST_MATH_CONSTEXPR bool check_denorm(std::complex<T> /* val */, R* /* result*/, const char* /* function */, const denorm_error<ignore_error>&) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T)) { return false; } } // namespace detail template <class R, class Policy, class T> inline R checked_narrowing_cast(T val, const char* function) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(R) && BOOST_MATH_IS_FLOAT(T) && is_noexcept_error_policy<Policy>::value) { typedef typename Policy::overflow_error_type overflow_type; typedef typename Policy::underflow_error_type underflow_type; typedef typename Policy::denorm_error_type denorm_type; // // Most of what follows will evaluate to a no-op: // R result = 0; if(detail::check_overflow<R>(val, &result, function, overflow_type())) return result; if(detail::check_underflow<R>(val, &result, function, underflow_type())) return result; if(detail::check_denorm<R>(val, &result, function, denorm_type())) return result; return static_cast<R>(val); } template <class T, class Policy> inline void check_series_iterations(const char* function, boost::uintmax_t max_iter, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(T) && is_noexcept_error_policy<Policy>::value) { if(max_iter >= policies::get_max_series_iterations<Policy>()) raise_evaluation_error<T>( function, "Series evaluation exceeded %1% iterations, giving up now.", static_cast<T>(static_cast<double>(max_iter)), pol); } template <class T, class Policy> inline void check_root_iterations(const char* function, boost::uintmax_t max_iter, const Policy& pol) BOOST_NOEXCEPT_IF(BOOST_MATH_IS_FLOAT(T) && is_noexcept_error_policy<Policy>::value) { if(max_iter >= policies::get_max_root_iterations<Policy>()) raise_evaluation_error<T>( function, "Root finding evaluation exceeded %1% iterations, giving up now.", static_cast<T>(static_cast<double>(max_iter)), pol); } } //namespace policies namespace detail{ // // Simple helper function to assist in returning a pair from a single value, // that value usually comes from one of the error handlers above: // template <class T> std::pair<T, T> pair_from_single(const T& val) BOOST_MATH_NOEXCEPT(T) { return std::make_pair(val, val); } } #ifdef BOOST_MSVC # pragma warning(pop) #endif }} // namespaces boost/math #endif // BOOST_MATH_POLICY_ERROR_HANDLING_HPP PK %,"\����, �, relate/direction.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands. // Use, modification and distribution is subject to the Boost Software License, // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at // http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_DIRECTION_HPP #define BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_DIRECTION_HPP #include <cstddef> #include <string> #include <boost/concept_check.hpp> #include <boost/geometry/arithmetic/determinant.hpp> #include <boost/geometry/strategies/side_info.hpp> #include <boost/geometry/util/math.hpp> #include <boost/geometry/util/select_calculation_type.hpp> #include <boost/geometry/util/select_most_precise.hpp> namespace boost { namespace geometry { namespace policies { namespace relate { struct direction_type { // NOTE: "char" will be replaced by enum in future version inline direction_type(side_info const& s, char h, int ha, int hb, int da = 0, int db = 0, bool op = false) : how(h) , opposite(op) , how_a(ha) , how_b(hb) , dir_a(da) , dir_b(db) , sides(s) { arrival[0] = ha; arrival[1] = hb; } inline direction_type(char h, bool op, int ha = 0, int hb = 0) : how(h) , opposite(op) , how_a(ha) , how_b(hb) , dir_a(0) , dir_b(0) { arrival[0] = ha; arrival[1] = hb; } // TODO: replace this // NOTE: "char" will be replaced by enum in future version // "How" is the intersection formed? char how; // Is it opposite (for collinear/equal cases) bool opposite; // Information on how A arrives at intersection, how B arrives at intersection // 1: arrives at intersection // -1: starts from intersection int how_a; int how_b; // Direction: how is A positioned from B // 1: points left, seen from IP // -1: points right, seen from IP // In case of intersection: B's TO direction // In case that B's TO direction is at A: B's from direction // In collinear cases: it is 0 int dir_a; // Direction of A-s TO from IP int dir_b; // Direction of B-s TO from IP // New information side_info sides; // THIS IS EQUAL TO arrival_a, arrival_b - they probably can go now we have robust fractions int arrival[2]; // 1=arrival, -1=departure, 0=neutral; == how_a//how_b // About arrival[0] (== arrival of a2 w.r.t. b) for COLLINEAR cases // Arrival 1: a1--------->a2 (a arrives within b) // b1----->b2 // Arrival 1: (a in b) // // Arrival -1: a1--------->a2 (a does not arrive within b) // b1----->b2 // Arrival -1: (b in a) a_1-------------a_2 // b_1---b_2 // Arrival 0: a1------->a2 (a arrives at TO-border of b) // b1--->b2 }; struct segments_direction { typedef direction_type return_type; template < typename Segment1, typename Segment2, typename SegmentIntersectionInfo > static inline return_type segments_crosses(side_info const& sides, SegmentIntersectionInfo const& , Segment1 const& , Segment2 const& ) { bool const ra0 = sides.get<0,0>() == 0; bool const ra1 = sides.get<0,1>() == 0; bool const rb0 = sides.get<1,0>() == 0; bool const rb1 = sides.get<1,1>() == 0; return // opposite and same starting point (FROM) ra0 && rb0 ? calculate_side<1>(sides, 'f', -1, -1) // opposite and point to each other (TO) : ra1 && rb1 ? calculate_side<0>(sides, 't', 1, 1) // not opposite, forming an angle, first a then b, // directed either both left, or both right // Check side of B2 from A. This is not calculated before : ra1 && rb0 ? angle<1>(sides, 'a', 1, -1) // not opposite, forming a angle, first b then a, // directed either both left, or both right : ra0 && rb1 ? angle<0>(sides, 'a', -1, 1) // b starts from interior of a : rb0 ? starts_from_middle(sides, 'B', 0, -1) // a starts from interior of b (#39) : ra0 ? starts_from_middle(sides, 'A', -1, 0) // b ends at interior of a, calculate direction of A from IP : rb1 ? b_ends_at_middle(sides) // a ends at interior of b : ra1 ? a_ends_at_middle(sides) // normal intersection : calculate_side<1>(sides, 'i', -1, -1) ; } template <typename Ratio> static inline int arrival_value(Ratio const& r_from, Ratio const& r_to) { // a1--------->a2 // b1----->b2 // a departs: -1 // a1--------->a2 // b1----->b2 // a arrives: 1 // a1--------->a2 // b1----->b2 // both arrive there -> r-to = 1/1, or 0/1 (on_segment) // First check the TO (for arrival), then FROM (for departure) return r_to.in_segment() ? 1 : r_to.on_segment() ? 0 : r_from.on_segment() ? -1 : -1 ; } template <typename Ratio> static inline void analyze(Ratio const& r, int& in_segment_count, int& on_end_count, int& outside_segment_count) { if (r.on_end()) { on_end_count++; } else if (r.in_segment()) { in_segment_count++; } else { outside_segment_count++; } } static inline int arrival_from_position_value(int /*v_from*/, int v_to) { return v_to == 2 ? 1 : v_to == 1 || v_to == 3 ? 0 //: v_from >= 1 && v_from <= 3 ? -1 : -1; // NOTE: this should be an equivalent of the above for the other order /* (v_from < 3 && v_to > 3) || (v_from > 3 && v_to < 3) ? 1 : v_from == 3 || v_to == 3 ? 0 : -1;*/ } static inline void analyse_position_value(int pos_val, int & in_segment_count, int & on_end_count, int & outside_segment_count) { if ( pos_val == 1 || pos_val == 3 ) { on_end_count++; } else if ( pos_val == 2 ) { in_segment_count++; } else { outside_segment_count++; } } template <typename Segment1, typename Segment2, typename Ratio> static inline return_type segments_collinear( Segment1 const& , Segment2 const& , bool opposite, int a1_wrt_b, int a2_wrt_b, int b1_wrt_a, int b2_wrt_a, Ratio const& /*ra_from_wrt_b*/, Ratio const& /*ra_to_wrt_b*/, Ratio const& /*rb_from_wrt_a*/, Ratio const& /*rb_to_wrt_a*/) { return_type r('c', opposite); // IMPORTANT: the order of conditions is different as in intersection_points.hpp // We assign A in 0 and B in 1 r.arrival[0] = arrival_from_position_value(a1_wrt_b, a2_wrt_b); r.arrival[1] = arrival_from_position_value(b1_wrt_a, b2_wrt_a); // Analyse them int a_in_segment_count = 0; int a_on_end_count = 0; int a_outside_segment_count = 0; int b_in_segment_count = 0; int b_on_end_count = 0; int b_outside_segment_count = 0; analyse_position_value(a1_wrt_b, a_in_segment_count, a_on_end_count, a_outside_segment_count); analyse_position_value(a2_wrt_b, a_in_segment_count, a_on_end_count, a_outside_segment_count); analyse_position_value(b1_wrt_a, b_in_segment_count, b_on_end_count, b_outside_segment_count); analyse_position_value(b2_wrt_a, b_in_segment_count, b_on_end_count, b_outside_segment_count); if (a_on_end_count == 1 && b_on_end_count == 1 && a_outside_segment_count == 1 && b_outside_segment_count == 1) { // This is a collinear touch // --------> A (or B) // <---------- B (or A) // We adapt the "how" // TODO: how was to be refactored anyway, if (! opposite) { r.how = 'a'; } else { r.how = r.arrival[0] == 0 ? 't' : 'f'; } } else if (a_on_end_count == 2 && b_on_end_count == 2) { r.how = 'e'; } return r; } template <typename Segment> static inline return_type degenerate(Segment const& , bool) { return return_type('0', false); } template <typename Segment, typename Ratio> static inline return_type one_degenerate(Segment const& , Ratio const& , bool) { // To be decided return return_type('0', false); } static inline return_type disjoint() { return return_type('d', false); } static inline return_type error(std::string const&) { // Return "E" to denote error // This will throw an error in get_turn_info // TODO: change to enum or similar return return_type('E', false); } private : template <std::size_t I> static inline return_type calculate_side(side_info const& sides, char how, int how_a, int how_b) { int const dir = sides.get<1, I>() == 1 ? 1 : -1; return return_type(sides, how, how_a, how_b, -dir, dir); } template <std::size_t I> static inline return_type angle(side_info const& sides, char how, int how_a, int how_b) { int const dir = sides.get<1, I>() == 1 ? 1 : -1; return return_type(sides, how, how_a, how_b, dir, dir); } static inline return_type starts_from_middle(side_info const& sides, char which, int how_a, int how_b) { // Calculate ARROW of b segment w.r.t. s1 int dir = sides.get<1, 1>() == 1 ? 1 : -1; // From other perspective, then reverse bool const is_a = which == 'A'; if (is_a) { dir = -dir; } return return_type(sides, 's', how_a, how_b, is_a ? dir : -dir, ! is_a ? dir : -dir); } // To be harmonized static inline return_type a_ends_at_middle(side_info const& sides) { // Ending at the middle, one ARRIVES, the other one is NEUTRAL // (because it both "arrives" and "departs" there) int const dir = sides.get<1, 1>() == 1 ? 1 : -1; return return_type(sides, 'm', 1, 0, dir, dir); } static inline return_type b_ends_at_middle(side_info const& sides) { int const dir = sides.get<0, 1>() == 1 ? 1 : -1; return return_type(sides, 'm', 0, 1, dir, dir); } }; }} // namespace policies::relate }} // namespace boost::geometry #endif // BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_DIRECTION_HPP PK %,"\<�) ) relate/intersection_points.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands. // This file was modified by Oracle on 2016. // Modifications copyright (c) 2016 Oracle and/or its affiliates. // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle // Use, modification and distribution is subject to the Boost Software License, // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at // http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POINTS_HPP #define BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POINTS_HPP #include <algorithm> #include <string> #include <boost/geometry/algorithms/detail/assign_indexed_point.hpp> #include <boost/geometry/core/access.hpp> #include <boost/geometry/core/assert.hpp> #include <boost/geometry/strategies/side_info.hpp> namespace boost { namespace geometry { namespace policies { namespace relate { /*! \brief Policy calculating the intersection points themselves */ template < typename ReturnType > struct segments_intersection_points { typedef ReturnType return_type; template < typename Segment1, typename Segment2, typename SegmentIntersectionInfo > static inline return_type segments_crosses(side_info const&, SegmentIntersectionInfo const& sinfo, Segment1 const& s1, Segment2 const& s2) { return_type result; result.count = 1; sinfo.calculate(result.intersections[0], s1, s2); // Temporary - this should go later result.fractions[0].assign(sinfo); return result; } template <typename Segment1, typename Segment2, typename Ratio> static inline return_type segments_collinear( Segment1 const& a, Segment2 const& b, bool /*opposite*/, int a1_wrt_b, int a2_wrt_b, int b1_wrt_a, int b2_wrt_a, Ratio const& ra_from_wrt_b, Ratio const& ra_to_wrt_b, Ratio const& rb_from_wrt_a, Ratio const& rb_to_wrt_a) { return_type result; unsigned int index = 0, count_a = 0, count_b = 0; Ratio on_a[2]; // The conditions "index < 2" are necessary for non-robust handling, // if index would be 2 this indicate an (currently uncatched) error // IMPORTANT: the order of conditions is different as in direction.hpp if (a1_wrt_b >= 1 && a1_wrt_b <= 3 // ra_from_wrt_b.on_segment() && index < 2) { // a1--------->a2 // b1----->b2 // // ra1 (relative to b) is between 0/1: // -> First point of A is intersection point detail::assign_point_from_index<0>(a, result.intersections[index]); result.fractions[index].assign(Ratio::zero(), ra_from_wrt_b); on_a[index] = Ratio::zero(); index++; count_a++; } if (b1_wrt_a == 2 //rb_from_wrt_a.in_segment() && index < 2) { // We take the first intersection point of B // a1--------->a2 // b1----->b2 // But only if it is not located on A // a1--------->a2 // b1----->b2 rb_from_wrt_a == 0/1 -> a already taken detail::assign_point_from_index<0>(b, result.intersections[index]); result.fractions[index].assign(rb_from_wrt_a, Ratio::zero()); on_a[index] = rb_from_wrt_a; index++; count_b++; } if (a2_wrt_b >= 1 && a2_wrt_b <= 3 //ra_to_wrt_b.on_segment() && index < 2) { // Similarly, second IP (here a2) // a1--------->a2 // b1----->b2 detail::assign_point_from_index<1>(a, result.intersections[index]); result.fractions[index].assign(Ratio::one(), ra_to_wrt_b); on_a[index] = Ratio::one(); index++; count_a++; } if (b2_wrt_a == 2 // rb_to_wrt_a.in_segment() && index < 2) { detail::assign_point_from_index<1>(b, result.intersections[index]); result.fractions[index].assign(rb_to_wrt_a, Ratio::one()); on_a[index] = rb_to_wrt_a; index++; count_b++; } // TEMPORARY // If both are from b, and b is reversed w.r.t. a, we swap IP's // to align them w.r.t. a // get_turn_info still relies on some order (in some collinear cases) if (index == 2 && on_a[1] < on_a[0]) { std::swap(result.fractions[0], result.fractions[1]); std::swap(result.intersections[0], result.intersections[1]); } result.count = index; return result; } static inline return_type disjoint() { return return_type(); } static inline return_type error(std::string const&) { return return_type(); } // Both degenerate template <typename Segment> static inline return_type degenerate(Segment const& segment, bool) { return_type result; result.count = 1; set<0>(result.intersections[0], get<0, 0>(segment)); set<1>(result.intersections[0], get<0, 1>(segment)); return result; } // One degenerate template <typename Segment, typename Ratio> static inline return_type one_degenerate(Segment const& degenerate_segment, Ratio const& ratio, bool a_degenerate) { return_type result; result.count = 1; set<0>(result.intersections[0], get<0, 0>(degenerate_segment)); set<1>(result.intersections[0], get<0, 1>(degenerate_segment)); if (a_degenerate) { // IP lies on ratio w.r.t. segment b result.fractions[0].assign(Ratio::zero(), ratio); } else { result.fractions[0].assign(ratio, Ratio::zero()); } return result; } }; }} // namespace policies::relate }} // namespace boost::geometry #endif // BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POINTS_HPP PK %,"\���b b relate/intersection_policy.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2007-2020 Barend Gehrels, Amsterdam, the Netherlands. // This file was modified by Oracle on 2020. // Modifications copyright (c) 2020 Oracle and/or its affiliates. // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle // Use, modification and distribution is subject to the Boost Software License, // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at // http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POLICY_HPP #define BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POLICY_HPP #include <string> #include <tuple> #include <boost/geometry/policies/relate/direction.hpp> #include <boost/geometry/policies/relate/intersection_points.hpp> #include <boost/geometry/strategies/side_info.hpp> namespace boost { namespace geometry { namespace policies { namespace relate { template <typename IntersectionPointsReturnType> struct segments_intersection_policy { private: typedef policies::relate::segments_intersection_points < IntersectionPointsReturnType > pts_policy; typedef policies::relate::segments_direction dir_policy; public: struct return_type { typedef typename pts_policy::return_type intersection_points_type; typedef typename dir_policy::return_type direction_type; return_type(intersection_points_type const& pts_result, direction_type const& dir_result) : intersection_points(pts_result) , direction(dir_result) {} intersection_points_type intersection_points; direction_type direction; }; template <typename Segment1, typename Segment2, typename SegmentIntersectionInfo> static inline return_type segments_crosses(side_info const& sides, SegmentIntersectionInfo const& sinfo, Segment1 const& s1, Segment2 const& s2) { return return_type ( pts_policy::segments_crosses(sides, sinfo, s1, s2), dir_policy::segments_crosses(sides, sinfo, s1, s2) ); } template <typename Segment1, typename Segment2, typename Ratio> static inline return_type segments_collinear( Segment1 const& segment1, Segment2 const& segment2, bool opposite, int pa1, int pa2, int pb1, int pb2, Ratio const& ra1, Ratio const& ra2, Ratio const& rb1, Ratio const& rb2) { return return_type ( pts_policy::segments_collinear(segment1, segment2, opposite, pa1, pa2, pb1, pb2, ra1, ra2, rb1, rb2), dir_policy::segments_collinear(segment1, segment2, opposite, pa1, pa2, pb1, pb2, ra1, ra2, rb1, rb2) ); } template <typename Segment> static inline return_type degenerate(Segment const& segment, bool a_degenerate) { return return_type ( pts_policy::degenerate(segment, a_degenerate), dir_policy::degenerate(segment, a_degenerate) ); } template <typename Segment, typename Ratio> static inline return_type one_degenerate(Segment const& segment, Ratio const& ratio, bool a_degenerate) { return return_type ( pts_policy::one_degenerate(segment, ratio, a_degenerate), dir_policy::one_degenerate(segment, ratio, a_degenerate) ); } static inline return_type disjoint() { return return_type ( pts_policy::disjoint(), dir_policy::disjoint() ); } static inline return_type error(std::string const& msg) { return return_type ( pts_policy::error(msg), dir_policy::error(msg) ); } }; }} // namespace policies::relate }} // namespace boost::geometry #endif // BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_POLICY_HPP PK %,"\O�� � relate/intersection_ratios.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2007-2014 Barend Gehrels, Amsterdam, the Netherlands. // Use, modification and distribution is subject to the Boost Software License, // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at // http://www.boost.org/LICENSE_1_0.txt) #ifndef BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_RATIOS_HPP #define BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_RATIOS_HPP #include <algorithm> #include <string> #include <boost/concept_check.hpp> #include <boost/numeric/conversion/cast.hpp> #include <boost/geometry/algorithms/detail/assign_indexed_point.hpp> #include <boost/geometry/core/access.hpp> #include <boost/geometry/strategies/side_info.hpp> namespace boost { namespace geometry { namespace policies { namespace relate { /*! \brief Policy returning segment ratios \note Template argument FractionType should be a fraction_type<SegmentRatio> */ template < typename FractionType > struct segments_intersection_ratios { typedef FractionType return_type; template < typename Segment1, typename Segment2, typename SegmentIntersectionInfo > static inline return_type segments_crosses(side_info const&, SegmentIntersectionInfo const& sinfo, Segment1 const& , Segment2 const& ) { return_type result; result.assign(sinfo); return result; } template <typename Segment1, typename Segment2, typename Ratio> static inline return_type segments_collinear( Segment1 const& , Segment2 const& , Ratio const& ra_from_wrt_b, Ratio const& ra_to_wrt_b, Ratio const& rb_from_wrt_a, Ratio const& rb_to_wrt_a) { // We have only one result, for (potentially) two IP's, // so we take a first one return_type result; if (ra_from_wrt_b.on_segment()) { result.assign(Ratio::zero(), ra_from_wrt_b); } else if (rb_from_wrt_a.in_segment()) { result.assign(rb_from_wrt_a, Ratio::zero()); } else if (ra_to_wrt_b.on_segment()) { result.assign(Ratio::one(), ra_to_wrt_b); } else if (rb_to_wrt_a.in_segment()) { result.assign(rb_to_wrt_a, Ratio::one()); } return result; } static inline return_type disjoint() { return return_type(); } static inline return_type error(std::string const&) { return return_type(); } template <typename Segment> static inline return_type degenerate(Segment const& segment, bool) { return return_type(); } template <typename Segment, typename Ratio> static inline return_type one_degenerate(Segment const& , Ratio const& ratio, bool a_degenerate) { return_type result; if (a_degenerate) { // IP lies on ratio w.r.t. segment b result.assign(Ratio::zero(), ratio); } else { result.assign(ratio, Ratio::zero()); } return result; } }; }} // namespace policies::relate }} // namespace boost::geometry #endif // BOOST_GEOMETRY_GEOMETRY_POLICIES_RELATE_INTERSECTION_RATIOS_HPP PK %,"\��o�( ( is_valid/default_policy.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2015, Oracle and/or its affiliates. // Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle // Licensed under the Boost Software License version 1.0. // http://www.boost.org/users/license.html #ifndef BOOST_GEOMETRY_POLICIES_IS_VALID_DEFAULT_POLICY_HPP #define BOOST_GEOMETRY_POLICIES_IS_VALID_DEFAULT_POLICY_HPP #include <boost/geometry/algorithms/validity_failure_type.hpp> namespace boost { namespace geometry { template <bool AllowDuplicates = true, bool AllowSpikes = true> class is_valid_default_policy { protected: static inline bool is_valid(validity_failure_type failure) { return failure == no_failure || (AllowDuplicates && failure == failure_duplicate_points); } static inline bool is_valid(validity_failure_type failure, bool is_linear) { return is_valid(failure) || (is_linear && AllowSpikes && failure == failure_spikes); } public: template <validity_failure_type Failure> static inline bool apply() { return is_valid(Failure); } template <validity_failure_type Failure, typename Data> static inline bool apply(Data const&) { return is_valid(Failure); } template <validity_failure_type Failure, typename Data1, typename Data2> static inline bool apply(Data1 const& data1, Data2 const&) { return is_valid(Failure, data1); } }; }} // namespace boost::geometry #endif // BOOST_GEOMETRY_POLICIES_IS_VALID_DEFAULT_POLICY_HPP PK %,"\�`�ff f is_valid/failure_type_policy.hppnu �[��� // Boost.Geometry (aka GGL, Generic Geometry Library) // Copyright (c) 2015, Oracle and/or its affiliates. // Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle // Licensed under the Boost Software License version 1.0. // http://www.boost.org/users/license.html #ifndef BOOST_GEOMETRY_POLICIES_IS_VALID_FAILURE_TYPE_POLICY_HPP #define BOOST_GEOMETRY_POLICIES_IS_VALID_FAILURE_TYPE_POLICY_HPP #include <boost/geometry/algorithms/validity_failure_type.hpp> namespace boost { namespace geometry { // policy that simply keeps (and can return) the failure type template <bool AllowDuplicates = true, bool AllowSpikes = true> class failure_type_policy { private: static inline validity_failure_type transform_failure_type(validity_failure_type failure) { if (AllowDuplicates && failure == failure_duplicate_points) { return no_failure; } return failure; } static inline validity_failure_type transform_failure_type(validity_failure_type failure, bool is_linear) { if (is_linear && AllowSpikes && failure == failure_spikes) { return no_failure; } return transform_failure_type(failure); } public: failure_type_policy() : m_failure(no_failure) {} template <validity_failure_type Failure> inline bool apply() { m_failure = transform_failure_type(Failure); return m_failure == no_failure; } template <validity_failure_type Failure, typename Data> inline bool apply(Data const&) { return apply<Failure>(); } template <validity_failure_type Failure, typename Data1, typename Data2> inline bool apply(Data1 const& data1, Data2 const&) { m_failure = transform_failure_type(Failure, data1); return m_failure == no_failure; } validity_failure_type failure() const { return m_failure; } private: validity_failure_type m_failure; }; }} // namespace boost::geometry #endif // BOOST_GEOMETRY_POLICIES_IS_VALID_FAILURE_TYPE_POLICY_HPP PK %,"\�"�g "