@ -30,7 +30,6 @@
using MathNet.Numerics.Providers.LinearAlgebra ;
using MathNet.Numerics.Providers.LinearAlgebra ;
using System ;
using System ;
using System.IO ;
using System.Threading.Tasks ;
using System.Threading.Tasks ;
namespace MathNet.Numerics
namespace MathNet.Numerics
@ -40,6 +39,8 @@ namespace MathNet.Numerics
/// </summary>
/// </summary>
public static class Control
public static class Control
{
{
const string EnvVarLAProvider = "MathNetNumericsLAProvider" ;
static int _ maxDegreeOfParallelism ;
static int _ maxDegreeOfParallelism ;
static int _ blockSize ;
static int _ blockSize ;
static int _ parallelizeOrder ;
static int _ parallelizeOrder ;
@ -70,63 +71,58 @@ namespace MathNet.Numerics
#else
#else
try
try
{
{
const string name = "MathNetNumericsLAProvider" ;
var value = Environment . GetEnvironmentVariable ( EnvVarLAProvider ) ;
var value = Environment . GetEnvironmentVariable ( name ) ;
switch ( value ! = null ? value . ToUpperInvariant ( ) : string . Empty )
switch ( value ! = null ? value . ToUpperInvariant ( ) : string . Empty )
{
{
#if NATIVE
#if NATIVE
case "MKL" :
case "MKL" :
LinearAlgebraProvider = new Providers . LinearAlgebra . Mkl . MklLinearAlgebraProvider ( ) ;
UseNativeMKL ( ) ;
break ;
break ;
case "CUDA" :
case "CUDA" :
LinearAlgebraProvider = new Providers . LinearAlgebra . Cuda . CudaLinearAlgebraProvider ( ) ;
UseNativeCUDA ( ) ;
break ;
break ;
case "OPENBLAS" :
case "OPENBLAS" :
LinearAlgebraProvider = new Providers . LinearAlgebra . OpenBlas . OpenBlasLinearAlgebraProvider ( ) ;
UseNativeOpenBLAS ( ) ;
break ;
break ;
#endif
#endif
default :
default :
LinearAlgebraProvider = new ManagedLinearAlgebraProvider ( ) ;
if ( ! TryUseNative ( ) )
{
UseManaged ( ) ;
}
break ;
break ;
}
}
}
}
catch
catch
{
{
// We don't care about any failures here at all (because "auto")
// We don't care about any failures here at all (because "auto")
LinearAlgebraProvider = new ManagedLinearAlgebraProvider ( ) ;
UseManaged ( ) ;
}
}
#endif
#endif
}
}
public static void UseSingleThread ( )
{
_ maxDegreeOfParallelism = 1 ;
ThreadSafeRandomNumberGenerators = false ;
LinearAlgebraProvider . InitializeVerify ( ) ;
}
public static void UseMultiThreading ( )
{
_ maxDegreeOfParallelism = Environment . ProcessorCount ;
ThreadSafeRandomNumberGenerators = true ;
LinearAlgebraProvider . InitializeVerify ( ) ;
}
public static void UseManaged ( )
public static void UseManaged ( )
{
{
LinearAlgebraProvider = new ManagedLinearAlgebraProvider ( ) ;
LinearAlgebraProvider = new ManagedLinearAlgebraProvider ( ) ;
}
}
#if NATIVE
#if NATIVE
/// <summary>
/// Use the Intel MKL native provider for linear algebra.
/// Throws if it is not available or failed to initialize, in which case the previous provider is still active.
/// </summary>
public static void UseNativeMKL ( )
public static void UseNativeMKL ( )
{
{
LinearAlgebraProvider = new Providers . LinearAlgebra . Mkl . MklLinearAlgebraProvider ( ) ;
LinearAlgebraProvider = new Providers . LinearAlgebra . Mkl . MklLinearAlgebraProvider ( ) ;
}
}
/// <summary>
/// Use the Intel MKL native provider for linear algebra, with the specified configuration parameters.
/// Throws if it is not available or failed to initialize, in which case the previous provider is still active.
/// </summary>
[CLSCompliant(false)]
[CLSCompliant(false)]
public static void UseNativeMKL (
public static void UseNativeMKL (
Providers . LinearAlgebra . Mkl . MklConsistency consistency = Providers . LinearAlgebra . Mkl . MklConsistency . Auto ,
Providers . LinearAlgebra . Mkl . MklConsistency consistency = Providers . LinearAlgebra . Mkl . MklConsistency . Auto ,
@ -136,17 +132,103 @@ namespace MathNet.Numerics
LinearAlgebraProvider = new Providers . LinearAlgebra . Mkl . MklLinearAlgebraProvider ( consistency , precision , accuracy ) ;
LinearAlgebraProvider = new Providers . LinearAlgebra . Mkl . MklLinearAlgebraProvider ( consistency , precision , accuracy ) ;
}
}
/// <summary>
/// Try to use the Intel MKL native provider for linear algebra.
/// </summary>
/// <returns>
/// True if the provider was found and initialized successfully.
/// False if it failed and the previous provider is still active.
/// </returns>
public static bool TryUseNativeMKL ( )
{
return Try ( UseNativeMKL ) ;
}
/// <summary>
/// Use the Nvidia CUDA native provider for linear algebra.
/// Throws if it is not available or failed to initialize, in which case the previous provider is still active.
/// </summary>
public static void UseNativeCUDA ( )
public static void UseNativeCUDA ( )
{
{
LinearAlgebraProvider = new Providers . LinearAlgebra . Cuda . CudaLinearAlgebraProvider ( ) ;
LinearAlgebraProvider = new Providers . LinearAlgebra . Cuda . CudaLinearAlgebraProvider ( ) ;
}
}
/// <summary>
/// Try to use the Nvidia CUDA native provider for linear algebra.
/// </summary>
/// <returns>
/// True if the provider was found and initialized successfully.
/// False if it failed and the previous provider is still active.
/// </returns>
public static bool TryUseNativeCUDA ( )
{
return Try ( UseNativeCUDA ) ;
}
/// <summary>
/// Use the OpenBLAS native provider for linear algebra.
/// Throws if it is not available or failed to initialize, in which case the previous provider is still active.
/// </summary>
public static void UseNativeOpenBLAS ( )
public static void UseNativeOpenBLAS ( )
{
{
LinearAlgebraProvider = new Providers . LinearAlgebra . OpenBlas . OpenBlasLinearAlgebraProvider ( ) ;
LinearAlgebraProvider = new Providers . LinearAlgebra . OpenBlas . OpenBlasLinearAlgebraProvider ( ) ;
}
}
/// <summary>
/// Try to use the OpenBLAS native provider for linear algebra.
/// </summary>
/// <returns>
/// True if the provider was found and initialized successfully.
/// False if it failed and the previous provider is still active.
/// </returns>
public static bool TryUseNativeOpenBLAS ( )
{
return Try ( UseNativeOpenBLAS ) ;
}
/// <summary>
/// Try to use any available native provider in an undefined order.
/// </summary>
/// <returns>
/// True if one of the native providers was found and successfully initialized.
/// False if it failed and the previous provider is still active.
/// </returns>
public static bool TryUseNative ( )
{
return TryUseNativeCUDA ( ) | | TryUseNativeMKL ( ) | | TryUseNativeOpenBLAS ( ) ;
}
static bool Try ( Action action )
{
try
{
action ( ) ;
return true ;
}
catch
{
// intentionally swallow exceptions here - use the non-try variants if you're interested in why
return false ;
}
}
#endif
#endif
public static void UseSingleThread ( )
{
_ maxDegreeOfParallelism = 1 ;
ThreadSafeRandomNumberGenerators = false ;
LinearAlgebraProvider . InitializeVerify ( ) ;
}
public static void UseMultiThreading ( )
{
_ maxDegreeOfParallelism = Environment . ProcessorCount ;
ThreadSafeRandomNumberGenerators = true ;
LinearAlgebraProvider . InitializeVerify ( ) ;
}
/// <summary>
/// <summary>
/// Gets or sets a value indicating whether the distribution classes check validate each parameter.
/// Gets or sets a value indicating whether the distribution classes check validate each parameter.
/// For the multivariate distributions this could involve an expensive matrix factorization.
/// For the multivariate distributions this could involve an expensive matrix factorization.