diff --git a/src/TNL/Devices/CudaDeviceInfo.cpp b/src/TNL/Devices/CudaDeviceInfo.cpp index 3a4fc166741651c9a0837a60c8142d3d9f449e57..45199ecda1fa986dc68d0fd5386b06c09e8b7ecc 100644 --- a/src/TNL/Devices/CudaDeviceInfo.cpp +++ b/src/TNL/Devices/CudaDeviceInfo.cpp @@ -11,6 +11,7 @@ #ifndef HAVE_CUDA #include <TNL/Devices/CudaDeviceInfo.h> +#include <TNL/Logger.h> namespace TNL { namespace Devices { @@ -106,6 +107,12 @@ getCudaCores( int deviceNum ) return 0; } +void +CudaDeviceInfo:: +writeDeviceInfo( Logger& logger ) +{ +} + } // namespace Devices } // namespace TNL diff --git a/src/TNL/Devices/CudaDeviceInfo.cu b/src/TNL/Devices/CudaDeviceInfo.cu index 9f9e77235f2d70227542eb9790b7459778bf6751..84096561dcb11de412828b07e43403132af493f4 100644 --- a/src/TNL/Devices/CudaDeviceInfo.cu +++ b/src/TNL/Devices/CudaDeviceInfo.cu @@ -13,6 +13,7 @@ #include <unordered_map> #include <TNL/Devices/CudaDeviceInfo.h> +#include <TNL/Logger.h> namespace TNL { namespace Devices { @@ -158,6 +159,35 @@ getCudaCores( int deviceNum ) CudaDeviceInfo::getCudaCoresPerMultiprocessors( deviceNum ); } +void +CudaDeviceInfo:: +writeDeviceInfo( Logger& logger ) +{ + logger.writeParameter< String >( "CUDA GPU info", String("") ); + // TODO: Printing all devices does not make sense until TNL can actually + // use more than one device for computations. Printing only the active + // device for now... +// int devices = getNumberOfDevices(); +// writeParameter< int >( "Number of devices", devices, 1 ); +// for( int i = 0; i < devices; i++ ) +// { +// logger.writeParameter< int >( "Device no.", i, 1 ); + int i = getActiveDevice(); + logger.writeParameter< String >( "Name", getDeviceName( i ), 2 ); + String deviceArch = String( getArchitectureMajor( i ) ) + "." + + String( getArchitectureMinor( i ) ); + logger.writeParameter< String >( "Architecture", deviceArch, 2 ); + logger.writeParameter< int >( "CUDA cores", getCudaCores( i ), 2 ); + double clockRate = ( double ) getClockRate( i ) / 1.0e3; + logger.writeParameter< double >( "Clock rate (in MHz)", clockRate, 2 ); + double globalMemory = ( double ) getGlobalMemory( i ) / 1.0e9; + logger.writeParameter< double >( "Global memory (in GB)", globalMemory, 2 ); + double memoryClockRate = ( double ) getMemoryClockRate( i ) / 1.0e3; + logger.writeParameter< double >( "Memory clock rate (in Mhz)", memoryClockRate, 2 ); + logger.writeParameter< bool >( "ECC enabled", getECCEnabled( i ), 2 ); +// } +} + } // namespace Devices } // namespace TNL diff --git a/src/TNL/Devices/CudaDeviceInfo.h b/src/TNL/Devices/CudaDeviceInfo.h index 545556d837a7f4c826cfdbfa154d726a56db9b09..b658e917703f8d97a7caca76c8055a845670506d 100644 --- a/src/TNL/Devices/CudaDeviceInfo.h +++ b/src/TNL/Devices/CudaDeviceInfo.h @@ -15,6 +15,9 @@ #include <TNL/String.h> namespace TNL { + +class Logger; + namespace Devices { class CudaDeviceInfo @@ -47,8 +50,8 @@ class CudaDeviceInfo static int getCudaCores( int deviceNum ); + static void writeDeviceInfo( Logger& logger ); }; } // namespace Devices } // namespace TNL - diff --git a/src/TNL/Devices/Host.cpp b/src/TNL/Devices/Host.cpp index a4a40e96af43b1cbd96493bc3a0c14aec43e4b30..db56392bcb6ad8218e7f3a45f3d1173eae541d94 100644 --- a/src/TNL/Devices/Host.cpp +++ b/src/TNL/Devices/Host.cpp @@ -20,9 +20,11 @@ #include <omp.h> #endif +#include <TNL/tnlConfig.h> #include <TNL/Devices/Host.h> #include <TNL/Config/ConfigDescription.h> #include <TNL/Config/ParameterContainer.h> +#include <TNL/Logger.h> namespace TNL { namespace Devices { @@ -90,6 +92,8 @@ Host::getCurrentTime( const char* format ) int Host::getNumberOfProcessors( void ) { + if( numberOfProcessors == 0 ) + parseCPUInfo(); return numberOfProcessors; } @@ -103,18 +107,24 @@ Host::getOnlineCPUs( void ) int Host::getNumberOfCores( int cpu_id ) { + if( CPUCores == 0 ) + parseCPUInfo(); return CPUCores; } int Host::getNumberOfThreads( int cpu_id ) { + if( CPUThreads == 0 ) + parseCPUInfo(); return CPUThreads; } String Host::getCPUModelName( int cpu_id ) { + if( CPUModelName == "" ) + parseCPUInfo(); return CPUModelName; } @@ -157,6 +167,35 @@ Host::getCPUCacheSizes( int cpu_id ) return sizes; } +void +Host:: +writeDeviceInfo( Logger& logger ) +{ + logger.writeParameter< String >( "Host name:", getHostname() ); + logger.writeParameter< String >( "System:", getSystemName() ); + logger.writeParameter< String >( "Release:", getSystemRelease() ); + logger.writeParameter< String >( "Architecture:", getArchitecture() ); + logger.writeParameter< char* >( "TNL Compiler:", ( char* ) TNL_CPP_COMPILER_NAME ); + // FIXME: generalize for multi-socket systems, here we consider only the first found CPU + const int cpu_id = 0; + const int threads = getNumberOfThreads( cpu_id ); + const int cores = getNumberOfCores( cpu_id ); + int threadsPerCore = 0; + if( cores > 0 ) + threadsPerCore = threads / cores; + logger.writeParameter< String >( "CPU info", String("") ); + logger.writeParameter< String >( "Model name:", getCPUModelName( cpu_id ), 1 ); + logger.writeParameter< int >( "Cores:", cores, 1 ); + logger.writeParameter< int >( "Threads per core:", threadsPerCore, 1 ); + logger.writeParameter< String >( "Max clock rate (in MHz):", getCPUMaxFrequency( cpu_id ) / 1000, 1 ); + CacheSizes cacheSizes = getCPUCacheSizes( cpu_id ); + String cacheInfo = String( cacheSizes.L1data ) + ", " + + String( cacheSizes.L1instruction ) + ", " + + String( cacheSizes.L2 ) + ", " + + String( cacheSizes.L3 ); + logger.writeParameter< String >( "Cache (L1d, L1i, L2, L3):", cacheInfo, 1 ); +} + void Host::parseCPUInfo( void ) { diff --git a/src/TNL/Devices/Host.h b/src/TNL/Devices/Host.h index 4bc622efb2836a320e7a0c9f105987824c1579bc..6c5c8a869321e24c4c4d19fc66ef4d7aea72b345 100644 --- a/src/TNL/Devices/Host.h +++ b/src/TNL/Devices/Host.h @@ -21,6 +21,8 @@ namespace Config { class ParameterContainer; } +class Logger; + namespace Devices { struct CacheSizes { @@ -50,6 +52,8 @@ class Host static int getCPUMaxFrequency( int cpu_id ); static CacheSizes getCPUCacheSizes( int cpu_id ); + static void writeDeviceInfo( Logger& logger ); + static size_t getFreeMemory(); static void disableOMP(); diff --git a/src/TNL/Logger.cpp b/src/TNL/Logger.cpp index 5a10205db06478e913f7308a03cb58b87bd25cfb..6287cc3b3337c8ec78ca4039e404e8a316f192f2 100644 --- a/src/TNL/Logger.cpp +++ b/src/TNL/Logger.cpp @@ -10,7 +10,6 @@ #include <iomanip> #include <TNL/Logger.h> -#include <TNL/tnlConfig.h> #include <TNL/Devices/Host.h> #include <TNL/Devices/CudaDeviceInfo.h> @@ -45,53 +44,9 @@ void Logger :: writeSeparator() bool Logger :: writeSystemInformation( const Config::ParameterContainer& parameters ) { - writeParameter< String >( "Host name:", Devices::Host::getHostname() ); - writeParameter< String >( "Architecture:", Devices::Host::getArchitecture() ); - // FIXME: generalize for multi-socket systems, here we consider only the first found CPU - const int cpu_id = 0; - const int threads = Devices::Host::getNumberOfThreads( cpu_id ); - const int cores = Devices::Host::getNumberOfCores( cpu_id ); - int threadsPerCore = threads / cores; - writeParameter< String >( "CPU info", String("") ); - writeParameter< String >( "Model name:", Devices::Host::getCPUModelName( cpu_id ), 1 ); - writeParameter< int >( "Cores:", cores, 1 ); - writeParameter< int >( "Threads per core:", threadsPerCore, 1 ); - writeParameter< String >( "Max clock rate (in MHz):", Devices::Host::getCPUMaxFrequency( cpu_id ) / 1000, 1 ); - Devices::CacheSizes cacheSizes = Devices::Host::getCPUCacheSizes( cpu_id ); - String cacheInfo = String( cacheSizes.L1data ) + ", " - + String( cacheSizes.L1instruction ) + ", " - + String( cacheSizes.L2 ) + ", " - + String( cacheSizes.L3 ); - writeParameter< String >( "Cache (L1d, L1i, L2, L3):", cacheInfo, 1 ); + Devices::Host::writeDeviceInfo( *this ); if( parameters.getParameter< String >( "device" ) == "cuda" ) - { - writeParameter< String >( "CUDA GPU info", String("") ); - // TODO: Printing all devices does not make sense, but in the future TNL - // might use more than one device for computations. Printing only - // the active device for now... -// int devices = Devices::CudaDeviceInfo::getNumberOfDevices(); -// writeParameter< int >( "Number of devices", devices, 1 ); -// for( int i = 0; i < devices; i++ ) -// { -// writeParameter< int >( "Device no.", i, 1 ); - int i = Devices::CudaDeviceInfo::getActiveDevice(); - writeParameter< String >( "Name", Devices::CudaDeviceInfo::getDeviceName( i ), 2 ); - String deviceArch = String( Devices::CudaDeviceInfo::getArchitectureMajor( i ) ) + "." + - String( Devices::CudaDeviceInfo::getArchitectureMinor( i ) ); - writeParameter< String >( "Architecture", deviceArch, 2 ); - writeParameter< int >( "CUDA cores", Devices::CudaDeviceInfo::getCudaCores( i ), 2 ); - double clockRate = ( double ) Devices::CudaDeviceInfo::getClockRate( i ) / 1.0e3; - writeParameter< double >( "Clock rate (in MHz)", clockRate, 2 ); - double globalMemory = ( double ) Devices::CudaDeviceInfo::getGlobalMemory( i ) / 1.0e9; - writeParameter< double >( "Global memory (in GB)", globalMemory, 2 ); - double memoryClockRate = ( double ) Devices::CudaDeviceInfo::getMemoryClockRate( i ) / 1.0e3; - writeParameter< double >( "Memory clock rate (in Mhz)", memoryClockRate, 2 ); - writeParameter< bool >( "ECC enabled", Devices::CudaDeviceInfo::getECCEnabled( i ), 2 ); -// } - } - writeParameter< String >( "System:", Devices::Host::getSystemName() ); - writeParameter< String >( "Release:", Devices::Host::getSystemRelease() ); - writeParameter< char* >( "TNL Compiler:", ( char* ) TNL_CPP_COMPILER_NAME ); + Devices::CudaDeviceInfo::writeDeviceInfo( *this ); return true; } @@ -102,29 +57,28 @@ void Logger :: writeCurrentTime( const char* label ) #ifdef TEMPLATE_EXPLICIT_INSTANTIATION template void Logger::writeParameter< char* >( const String&, - const String&, - const Config::ParameterContainer&, - int ); + const String&, + const Config::ParameterContainer&, + int ); template void Logger::writeParameter< double >( const String&, - const String&, - const Config::ParameterContainer&, - int ); -template void Logger::writeParameter< int >( const String&, const String&, const Config::ParameterContainer&, int ); +template void Logger::writeParameter< int >( const String&, + const String&, + const Config::ParameterContainer&, + int ); // TODO: fix this //template void Logger :: WriteParameter< char* >( const char*, -// const char*&, -// int ); +// const char*&, +// int ); template void Logger::writeParameter< double >( const String&, - const double&, - int ); -template void Logger::writeParameter< int >( const String&, - const int&, + const double&, int ); - +template void Logger::writeParameter< int >( const String&, + const int&, + int ); #endif } // namespace TNL diff --git a/src/TNL/Logger.h b/src/TNL/Logger.h index 90dd927da5547af88ef5b885a2192c449fd3cd74..791398649d8d61f89a984cbb8255bb0be22a69d9 100644 --- a/src/TNL/Logger.h +++ b/src/TNL/Logger.h @@ -26,7 +26,6 @@ class Logger void writeSeparator(); - // TODO: move this to Devices::Host bool writeSystemInformation( const Config::ParameterContainer& parameters ); @@ -59,28 +58,28 @@ namespace TNL { #ifdef TEMPLATE_EXPLICIT_INSTANTIATION extern template void Logger::writeParameter< char* >( const String&, - const String&, - const Config::ParameterContainer&, - int ); + const String&, + const Config::ParameterContainer&, + int ); extern template void Logger::writeParameter< double >( const String&, - const String&, - const Config::ParameterContainer&, - int ); -extern template void Logger::writeParameter< int >( const String&, const String&, const Config::ParameterContainer&, int ); +extern template void Logger::writeParameter< int >( const String&, + const String&, + const Config::ParameterContainer&, + int ); // TODO: fix this //extern template void Logger :: WriteParameter< char* >( const char*, -// const char*&, -// int ); +// const char*&, +// int ); extern template void Logger::writeParameter< double >( const String&, - const double&, - int ); -extern template void Logger::writeParameter< int >( const String&, - const int&, + const double&, int ); +extern template void Logger::writeParameter< int >( const String&, + const int&, + int ); #endif } // namespace TNL