Go to the documentation of this file.
41 #if defined(EIGEN_HAS_GPU_FP16) || defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
48 #pragma push_macro("EIGEN_CONSTEXPR")
49 #undef EIGEN_CONSTEXPR
50 #define EIGEN_CONSTEXPR
53 #define F16_PACKET_FUNCTION(PACKET_F, PACKET_F16, METHOD) \
55 EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC EIGEN_UNUSED \
56 PACKET_F16 METHOD<PACKET_F16>(const PACKET_F16& _x) { \
57 return float2half(METHOD<PACKET_F>(half2float(_x))); \
85 #if !defined(EIGEN_HAS_GPU_FP16) || !defined(EIGEN_GPU_COMPILE_PHASE)
88 #if (defined(EIGEN_HAS_GPU_FP16) && !defined(EIGEN_GPU_COMPILE_PHASE))
98 #if defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
108 #elif defined(EIGEN_HAS_HIP_FP16)
111 #elif defined(EIGEN_HAS_CUDA_FP16)
112 #if EIGEN_CUDA_SDK_VER < 90000
115 #endif // defined(EIGEN_HAS_CUDA_FP16)
116 #elif defined(SYCL_DEVICE_ONLY)
128 #if defined(EIGEN_HAS_GPU_FP16)
129 #if defined(EIGEN_HAS_HIP_FP16)
131 #elif defined(EIGEN_HAS_CUDA_FP16)
132 #if EIGEN_CUDA_SDK_VER >= 90000
146 #if !defined(EIGEN_HAS_GPU_FP16) || !defined(EIGEN_GPU_COMPILE_PHASE)
151 #elif defined(EIGEN_HAS_HIP_FP16)
154 #elif defined(EIGEN_HAS_CUDA_FP16)
158 #if defined(EIGEN_CUDA_SDK_VER) && EIGEN_CUDA_SDK_VER < 90000
167 #if defined(EIGEN_HAS_GPU_FP16)
168 #if defined(EIGEN_HAS_HIP_FP16)
170 #elif defined(EIGEN_HAS_CUDA_FP16)
171 #if defined(EIGEN_CUDA_SDK_VER) && EIGEN_CUDA_SDK_VER >= 90000
188 template<
typename RealScalar>
196 #if defined(EIGEN_HAS_GPU_FP16) && !defined(EIGEN_GPU_COMPILE_PHASE)
209 struct numeric_limits<
Eigen::half> {
210 static const bool is_specialized =
true;
211 static const bool is_signed =
true;
212 static const bool is_integer =
false;
213 static const bool is_exact =
false;
214 static const bool has_infinity =
true;
215 static const bool has_quiet_NaN =
true;
216 static const bool has_signaling_NaN =
true;
217 static const float_denorm_style has_denorm = denorm_present;
218 static const bool has_denorm_loss =
false;
219 static const std::float_round_style round_style = std::round_to_nearest;
220 static const bool is_iec559 =
false;
221 static const bool is_bounded =
false;
222 static const bool is_modulo =
false;
223 static const int digits = 11;
224 static const int digits10 = 3;
225 static const int max_digits10 = 5;
226 static const int radix = 2;
227 static const int min_exponent = -13;
228 static const int min_exponent10 = -4;
229 static const int max_exponent = 16;
230 static const int max_exponent10 = 4;
231 static const bool traps =
true;
232 static const bool tinyness_before =
false;
250 struct numeric_limits<const
Eigen::half> : numeric_limits<Eigen::half> {};
252 struct numeric_limits<volatile
Eigen::half> : numeric_limits<Eigen::half> {};
254 struct numeric_limits<const volatile
Eigen::half> : numeric_limits<Eigen::half> {};
259 namespace half_impl {
261 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && \
262 EIGEN_CUDA_ARCH >= 530) || \
263 (defined(EIGEN_HAS_HIP_FP16) && defined(HIP_DEVICE_COMPILE))
267 #define EIGEN_HAS_NATIVE_FP16
275 #if defined(EIGEN_HAS_NATIVE_FP16)
277 #if defined(EIGEN_CUDA_SDK_VER) && EIGEN_CUDA_SDK_VER >= 90000
278 return __hadd(::__half(
a), ::__half(
b));
290 #if defined(EIGEN_CUDA_SDK_VER) && EIGEN_CUDA_SDK_VER >= 90000
293 float num = __half2float(
a);
294 float denom = __half2float(
b);
295 return __float2half(num / denom);
337 #if defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
339 return half(vaddh_f16(
a.x,
b.x));
342 return half(vmulh_f16(
a.x,
b.x));
345 return half(vsubh_f16(
a.x,
b.x));
348 return half(vdivh_f16(
a.x,
b.x));
351 return half(vnegh_f16(
a.x));
354 a = half(vaddh_f16(
a.x,
b.x));
358 a = half(vmulh_f16(
a.x,
b.x));
362 a = half(vsubh_f16(
a.x,
b.x));
366 a = half(vdivh_f16(
a.x,
b.x));
370 return vceqh_f16(
a.x,
b.x);
373 return !vceqh_f16(
a.x,
b.x);
376 return vclth_f16(
a.x,
b.x);
379 return vcleh_f16(
a.x,
b.x);
382 return vcgth_f16(
a.x,
b.x);
385 return vcgeh_f16(
a.x,
b.x);
390 #elif !defined(EIGEN_HAS_NATIVE_FP16) || (EIGEN_COMP_CLANG && !EIGEN_COMP_NVCC) // Emulate support for half floats
392 #if EIGEN_COMP_CLANG && defined(EIGEN_CUDACC)
394 #pragma push_macro("EIGEN_DEVICE_FUNC")
395 #undef EIGEN_DEVICE_FUNC
396 #if defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_HAS_NATIVE_FP16)
397 #define EIGEN_DEVICE_FUNC __host__
398 #else // both host and device need emulated ops.
399 #define EIGEN_DEVICE_FUNC __host__ __device__
406 return half(
float(
a) +
float(
b));
409 return half(
float(
a) *
float(
b));
412 return half(
float(
a) -
float(
b));
415 return half(
float(
a) /
float(
b));
457 #if defined(__clang__) && defined(__CUDA__)
458 #pragma pop_macro("EIGEN_DEVICE_FUNC")
460 #endif // Emulate support for half floats
465 return half(
static_cast<float>(
a) /
static_cast<float>(
b));
479 half original_value =
a;
481 return original_value;
485 half original_value =
a;
487 return original_value;
502 #if defined(EIGEN_HAS_GPU_FP16)
515 #if defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
516 return numext::bit_cast<numext::uint16_t>(
h.x);
517 #elif defined(SYCL_DEVICE_ONLY)
518 return numext::bit_cast<numext::uint16_t>(
h);
530 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 300) || \
531 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
532 __half tmp_ff = __float2half(ff);
535 #elif defined(EIGEN_HAS_FP16_C)
537 h.x = _cvtss_sh(ff, 0);
540 #elif defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
542 h.x =
static_cast<__fp16
>(ff);
550 const float32_bits denorm_magic = { ((127 - 15) + (23 - 10) + 1) << 23 };
551 unsigned int sign_mask = 0x80000000u;
555 unsigned int sign =
f.u & sign_mask;
563 if (
f.u >= f16max.
u) {
564 o.
x = (
f.u > f32infty.
u) ? 0x7e00 : 0x7c00;
566 if (
f.u < (113 << 23)) {
570 f.f += denorm_magic.
f;
575 unsigned int mant_odd = (
f.u >> 13) & 1;
594 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 300) || \
595 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
596 return __half2float(
h);
597 #elif defined(EIGEN_HAS_FP16_C)
598 return _cvtsh_ss(
h.x);
599 #elif defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
600 return static_cast<float>(
h.x);
603 const unsigned int shifted_exp = 0x7c00 << 13;
606 o.
u = (
h.x & 0x7fff) << 13;
607 unsigned int exp = shifted_exp & o.
u;
608 o.
u += (127 - 15) << 23;
611 if (
exp == shifted_exp) {
612 o.
u += (128 - 16) << 23;
613 }
else if (
exp == 0) {
618 o.
u |= (
h.x & 0x8000) << 16;
626 #ifdef EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC
627 return (numext::bit_cast<numext::uint16_t>(
a.x) & 0x7fff) == 0x7c00;
629 return (
a.x & 0x7fff) == 0x7c00;
633 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 530) || \
634 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
636 #elif defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
637 return (numext::bit_cast<numext::uint16_t>(
a.x) & 0x7fff) > 0x7c00;
639 return (
a.x & 0x7fff) > 0x7c00;
647 #if defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
648 return half(vabsh_f16(
a.x));
656 #if (EIGEN_CUDA_SDK_VER >= 80000 && defined EIGEN_CUDA_ARCH && EIGEN_CUDA_ARCH >= 530) || \
657 defined(EIGEN_HIP_DEVICE_COMPILE)
658 return half(hexp(
a));
660 return half(::expf(
float(
a)));
667 #if (defined(EIGEN_HAS_CUDA_FP16) && EIGEN_CUDA_SDK_VER >= 80000 && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 530) || \
668 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
669 return half(::hlog(
a));
671 return half(::logf(
float(
a)));
678 return half(::log10f(
float(
a)));
685 #if (EIGEN_CUDA_SDK_VER >= 80000 && defined EIGEN_CUDA_ARCH && EIGEN_CUDA_ARCH >= 530) || \
686 defined(EIGEN_HIP_DEVICE_COMPILE)
687 return half(hsqrt(
a));
689 return half(::sqrtf(
float(
a)));
693 return half(::powf(
float(
a),
float(
b)));
696 return half(::sinf(
float(
a)));
699 return half(::cosf(
float(
a)));
702 return half(::tanf(
float(
a)));
705 return half(::tanhf(
float(
a)));
708 return half(::asinf(
float(
a)));
711 return half(::acosf(
float(
a)));
714 #if (EIGEN_CUDA_SDK_VER >= 80000 && defined EIGEN_CUDA_ARCH && EIGEN_CUDA_ARCH >= 300) || \
715 defined(EIGEN_HIP_DEVICE_COMPILE)
716 return half(hfloor(
a));
718 return half(::floorf(
float(
a)));
722 #if (EIGEN_CUDA_SDK_VER >= 80000 && defined EIGEN_CUDA_ARCH && EIGEN_CUDA_ARCH >= 300) || \
723 defined(EIGEN_HIP_DEVICE_COMPILE)
724 return half(hceil(
a));
726 return half(::ceilf(
float(
a)));
730 return half(::rintf(
float(
a)));
733 return half(::roundf(
float(
a)));
736 return half(::fmodf(
float(
a),
float(
b)));
740 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 530) || \
741 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
742 return __hlt(
b,
a) ?
b :
a;
744 const float f1 =
static_cast<float>(
a);
745 const float f2 =
static_cast<float>(
b);
750 #if (defined(EIGEN_HAS_CUDA_FP16) && defined(EIGEN_CUDA_ARCH) && EIGEN_CUDA_ARCH >= 530) || \
751 (defined(EIGEN_HAS_HIP_FP16) && defined(EIGEN_HIP_DEVICE_COMPILE))
752 return __hlt(
a,
b) ?
b :
a;
754 const float f1 =
static_cast<float>(
a);
755 const float f2 =
static_cast<float>(
b);
762 os << static_cast<float>(
v);
779 return x + (
y-
x) *
half(
float(std::rand()) /
float(RAND_MAX));
823 #if defined(EIGEN_HAS_GPU_FP16) || defined(EIGEN_HAS_ARM64_FP16_SCALAR_ARITHMETIC)
824 #pragma pop_macro("EIGEN_CONSTEXPR")
830 #if defined(EIGEN_GPU_COMPILE_PHASE)
873 #if (defined(EIGEN_CUDACC) && (!defined(EIGEN_CUDA_ARCH) || EIGEN_CUDA_ARCH >= 300)) \
874 || defined(EIGEN_HIPCC)
876 #if defined(EIGEN_HAS_CUDA_FP16) && EIGEN_CUDA_SDK_VER >= 90000
879 const __half
h = var;
880 return static_cast<Eigen::half>(__shfl_sync(mask,
h, srcLane, width));
884 const __half
h = var;
889 const __half
h = var;
894 const __half
h = var;
895 return static_cast<Eigen::half>(__shfl_xor_sync(mask,
h, laneMask, width));
898 #else // HIP or CUDA SDK < 9.0
901 const int ivar =
static_cast<int>(Eigen::numext::bit_cast<Eigen::numext::uint16_t>(var));
902 return Eigen::numext::bit_cast<Eigen::half>(
static_cast<Eigen::numext::uint16_t>(__shfl(ivar, srcLane, width)));
906 const int ivar =
static_cast<int>(Eigen::numext::bit_cast<Eigen::numext::uint16_t>(var));
911 const int ivar =
static_cast<int>(Eigen::numext::bit_cast<Eigen::numext::uint16_t>(var));
916 const int ivar =
static_cast<int>(Eigen::numext::bit_cast<Eigen::numext::uint16_t>(var));
917 return Eigen::numext::bit_cast<Eigen::half>(
static_cast<Eigen::numext::uint16_t>(__shfl_xor(ivar, laneMask, width)));
920 #endif // HIP vs CUDA
924 #if (defined(EIGEN_CUDACC) && (!defined(EIGEN_CUDA_ARCH) || EIGEN_CUDA_ARCH >= 350)) \
925 || defined(EIGEN_HIPCC)
931 #if EIGEN_HAS_STD_HASH
936 return static_cast<std::size_t>(Eigen::numext::bit_cast<Eigen::numext::uint16_t>(
a));
942 #endif // EIGEN_HALF_H
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half log10(const half &a)
half_impl::__half_raw __half_raw
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half log1p(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator!=(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half & operator*=(half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator==(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half expm1(const half &a)
#define EIGEN_DEVICE_FUNC
Namespace containing all symbols from the Eigen library.
static Eigen::half epsilon()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool() isfinite(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half() min(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half & operator-=(half &a, const half &b)
EIGEN_ALWAYS_INLINE std::ostream & operator<<(std::ostream &os, const half &v)
static Eigen::half infinity()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half pow(const half &a, const half &b)
EIGEN_DEVICE_FUNC half(std::complex< RealScalar > c)
EIGEN_DEVICE_FUNC EIGEN_ALWAYS_INLINE bool() isfinite(const Eigen::bfloat16 &h)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC float half_to_float(__half_raw h)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator--(half &a)
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half lowest()
set noclip points set clip one set noclip two set bar set border lt lw set xdata set ydata set zdata set x2data set y2data set boxwidth set dummy x
EIGEN_DEVICE_FUNC EIGEN_ALWAYS_INLINE bool() isinf(const Eigen::bfloat16 &h)
const EIGEN_DEVICE_FUNC SignReturnType sign() const
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator>(const half &a, const half &b)
static half run(const half &x, const half &y)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half abs(const half &a)
double f2(const Vector2 &x)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator-(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half exp(const half &a)
static Eigen::half round_error()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool() isinf(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half sin(const half &a)
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR half(const __half_raw &h)
ofstream os("timeSchurFactors.csv")
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half dummy_precision()
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR __half_raw()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator*(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half rint(const half &a)
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half epsilon()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator>=(const half &a, const half &b)
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR half()
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR half_base()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC Tgt bit_cast(const Src &src)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half sqrt(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half() max(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC numext::uint16_t raw_half_as_uint16(const __half_raw &h)
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half quiet_NaN()
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half infinity()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator/(const half &a, const half &b)
internal::enable_if< internal::valid_indexed_view_overload< RowIndices, ColIndices >::value &&internal::traits< typename EIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::ReturnAsIndexedView, typename EIGEN_INDEXED_VIEW_METHOD_TYPE< RowIndices, ColIndices >::type >::type operator()(const RowIndices &rowIndices, const ColIndices &colIndices) EIGEN_INDEXED_VIEW_METHOD_CONST
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR half_base(const __half_raw &h)
static Eigen::half signaling_NaN()
static Eigen::half lowest()
#define EIGEN_STRONG_INLINE
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half ceil(const half &a)
EIGEN_DEVICE_FUNC EIGEN_ALWAYS_INLINE bool() isnan(const Eigen::bfloat16 &h)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half round(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator++(half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half tan(const half &a)
#define EIGEN_ALWAYS_INLINE
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator<=(const half &a, const half &b)
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR half(bool b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool operator<(const half &a, const half &b)
Point2(* f)(const Point3 &, OptionalJacobian< 2, 3 >)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half & operator+=(half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool not_equal_strict(const X &x, const Y &y)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half tanh(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half cos(const half &a)
#define EIGEN_NOT_A_MACRO
EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR __half_raw(numext::uint16_t raw)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half operator+(const half &a, const half &b)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half fmod(const half &a, const half &b)
EIGEN_DEVICE_FUNC static EIGEN_CONSTEXPR EIGEN_STRONG_INLINE Eigen::half highest()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half log2(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC EIGEN_CONSTEXPR __half_raw raw_uint16_to_half(numext::uint16_t x)
Array< int, Dynamic, 1 > v
EIGEN_DEVICE_FUNC half(T val)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half floor(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half asin(const half &a)
static Eigen::half quiet_NaN()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half log(const half &a)
static Eigen::half denorm_min()
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC __half_raw float_to_half_rtne(float ff)
EIGEN_DEVICE_FUNC half(float f)
Holds information about the various numeric (i.e. scalar) types allowed by Eigen.
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool equal_strict(const X &x, const Y &y)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC bool() isnan(const half &a)
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half acos(const half &a)
EIGEN_DEFAULT_DENSE_INDEX_TYPE Index
The Index type as used for the API.
EIGEN_STRONG_INLINE EIGEN_DEVICE_FUNC half & operator/=(half &a, const half &b)
gtsam
Author(s):
autogenerated on Sat Nov 16 2024 04:02:23