1 /* 2 3 This file defines part of the initialization of PETSc 4 5 This file uses regular malloc and free because it cannot known 6 what malloc is being used until it has already processed the input. 7 */ 8 9 #include <petscsys.h> /*I "petscsys.h" I*/ 10 #include <petsc/private/petscimpl.h> 11 #include <petscvalgrind.h> 12 #include <petscviewer.h> 13 #if defined(PETSC_USE_LOG) 14 PETSC_INTERN PetscErrorCode PetscLogInitialize(void); 15 #endif 16 17 #if defined(PETSC_HAVE_SYS_SYSINFO_H) 18 #include <sys/sysinfo.h> 19 #endif 20 #if defined(PETSC_HAVE_UNISTD_H) 21 #include <unistd.h> 22 #endif 23 #if defined(PETSC_HAVE_CUDA) 24 #include <cuda_runtime.h> 25 PETSC_EXTERN PetscErrorCode PetscCUBLASInitializeHandle(void); 26 PETSC_EXTERN PetscErrorCode PetscCUSOLVERDnInitializeHandle(void); 27 #endif 28 29 #if defined(PETSC_HAVE_VIENNACL) 30 PETSC_EXTERN PetscErrorCode PetscViennaCLInit(); 31 #endif 32 33 /* ------------------------Nasty global variables -------------------------------*/ 34 /* 35 Indicates if PETSc started up MPI, or it was 36 already started before PETSc was initialized. 37 */ 38 PetscBool PetscBeganMPI = PETSC_FALSE; 39 PetscBool PetscInitializeCalled = PETSC_FALSE; 40 PetscBool PetscFinalizeCalled = PETSC_FALSE; 41 PetscBool PetscCUDAInitialized = PETSC_FALSE; 42 43 PetscMPIInt PetscGlobalRank = -1; 44 PetscMPIInt PetscGlobalSize = -1; 45 46 #if defined(PETSC_HAVE_COMPLEX) 47 #if defined(PETSC_COMPLEX_INSTANTIATE) 48 template <> class std::complex<double>; /* instantiate complex template class */ 49 #endif 50 #if !defined(PETSC_HAVE_MPI_C_DOUBLE_COMPLEX) 51 MPI_Datatype MPIU_C_DOUBLE_COMPLEX; 52 MPI_Datatype MPIU_C_COMPLEX; 53 #endif 54 55 /*MC 56 PETSC_i - the imaginary number i 57 58 Synopsis: 59 #include <petscsys.h> 60 PetscComplex PETSC_i; 61 62 Level: beginner 63 64 Note: 65 Complex numbers are automatically available if PETSc located a working complex implementation 66 67 .seealso: PetscRealPart(), PetscImaginaryPart(), PetscRealPartComplex(), PetscImaginaryPartComplex() 68 M*/ 69 PetscComplex PETSC_i; 70 #endif 71 #if defined(PETSC_USE_REAL___FLOAT128) 72 MPI_Datatype MPIU___FLOAT128 = 0; 73 #if defined(PETSC_HAVE_COMPLEX) 74 MPI_Datatype MPIU___COMPLEX128 = 0; 75 #endif 76 #elif defined(PETSC_USE_REAL___FP16) 77 MPI_Datatype MPIU___FP16 = 0; 78 #endif 79 MPI_Datatype MPIU_2SCALAR = 0; 80 #if defined(PETSC_USE_64BIT_INDICES) 81 MPI_Datatype MPIU_2INT = 0; 82 #endif 83 MPI_Datatype MPIU_BOOL; 84 MPI_Datatype MPIU_ENUM; 85 MPI_Datatype MPIU_FORTRANADDR; 86 MPI_Datatype MPIU_SIZE_T; 87 88 /* 89 Function that is called to display all error messages 90 */ 91 PetscErrorCode (*PetscErrorPrintf)(const char [],...) = PetscErrorPrintfDefault; 92 PetscErrorCode (*PetscHelpPrintf)(MPI_Comm,const char [],...) = PetscHelpPrintfDefault; 93 PetscErrorCode (*PetscVFPrintf)(FILE*,const char[],va_list) = PetscVFPrintfDefault; 94 /* 95 This is needed to turn on/off GPU synchronization 96 */ 97 PetscBool PetscViennaCLSynchronize = PETSC_FALSE; 98 PetscBool PetscCUDASynchronize = PETSC_FALSE; 99 100 /* ------------------------------------------------------------------------------*/ 101 /* 102 Optional file where all PETSc output from various prints is saved 103 */ 104 PETSC_INTERN FILE *petsc_history; 105 FILE *petsc_history = NULL; 106 107 PetscErrorCode PetscOpenHistoryFile(const char filename[],FILE **fd) 108 { 109 PetscErrorCode ierr; 110 PetscMPIInt rank,size; 111 char pfile[PETSC_MAX_PATH_LEN],pname[PETSC_MAX_PATH_LEN],fname[PETSC_MAX_PATH_LEN],date[64]; 112 char version[256]; 113 114 PetscFunctionBegin; 115 ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); 116 if (!rank) { 117 char arch[10]; 118 int err; 119 120 ierr = PetscGetArchType(arch,10);CHKERRQ(ierr); 121 ierr = PetscGetDate(date,64);CHKERRQ(ierr); 122 ierr = PetscGetVersion(version,256);CHKERRQ(ierr); 123 ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); 124 if (filename) { 125 ierr = PetscFixFilename(filename,fname);CHKERRQ(ierr); 126 } else { 127 ierr = PetscGetHomeDirectory(pfile,240);CHKERRQ(ierr); 128 ierr = PetscStrcat(pfile,"/.petschistory");CHKERRQ(ierr); 129 ierr = PetscFixFilename(pfile,fname);CHKERRQ(ierr); 130 } 131 132 *fd = fopen(fname,"a"); 133 if (!fd) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_FILE_OPEN,"Cannot open file: %s",fname); 134 135 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"---------------------------------------------------------\n");CHKERRQ(ierr); 136 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"%s %s\n",version,date);CHKERRQ(ierr); 137 ierr = PetscGetProgramName(pname,PETSC_MAX_PATH_LEN);CHKERRQ(ierr); 138 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"%s on a %s, %d proc. with options:\n",pname,arch,size);CHKERRQ(ierr); 139 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"---------------------------------------------------------\n");CHKERRQ(ierr); 140 141 err = fflush(*fd); 142 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 143 } 144 PetscFunctionReturn(0); 145 } 146 147 PETSC_INTERN PetscErrorCode PetscCloseHistoryFile(FILE **fd) 148 { 149 PetscErrorCode ierr; 150 PetscMPIInt rank; 151 char date[64]; 152 int err; 153 154 PetscFunctionBegin; 155 ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); 156 if (!rank) { 157 ierr = PetscGetDate(date,64);CHKERRQ(ierr); 158 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"---------------------------------------------------------\n");CHKERRQ(ierr); 159 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"Finished at %s\n",date);CHKERRQ(ierr); 160 ierr = PetscFPrintf(PETSC_COMM_SELF,*fd,"---------------------------------------------------------\n");CHKERRQ(ierr); 161 err = fflush(*fd); 162 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 163 err = fclose(*fd); 164 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fclose() failed on file"); 165 } 166 PetscFunctionReturn(0); 167 } 168 169 /* ------------------------------------------------------------------------------*/ 170 171 /* 172 This is ugly and probably belongs somewhere else, but I want to 173 be able to put a true MPI abort error handler with command line args. 174 175 This is so MPI errors in the debugger will leave all the stack 176 frames. The default MP_Abort() cleans up and exits thus providing no useful information 177 in the debugger hence we call abort() instead of MPI_Abort(). 178 */ 179 180 void Petsc_MPI_AbortOnError(MPI_Comm *comm,PetscMPIInt *flag,...) 181 { 182 PetscFunctionBegin; 183 (*PetscErrorPrintf)("MPI error %d\n",*flag); 184 abort(); 185 } 186 187 void Petsc_MPI_DebuggerOnError(MPI_Comm *comm,PetscMPIInt *flag,...) 188 { 189 PetscErrorCode ierr; 190 191 PetscFunctionBegin; 192 (*PetscErrorPrintf)("MPI error %d\n",*flag); 193 ierr = PetscAttachDebugger(); 194 if (ierr) MPI_Abort(*comm,*flag); /* hopeless so get out */ 195 } 196 197 #if defined(PETSC_HAVE_CUDA) 198 /*@C 199 PetscCUDAInitialize - Initializes the CUDA device and cuBLAS on the device 200 201 Logically collective 202 203 Input Parameter: 204 comm - the MPI communicator that will utilize the CUDA devices 205 206 Options Database: 207 + -cuda_initialize <default yes,no> - do the initialization in PetscInitialize(). If -cuda_initialize no is used then the default initialization is done automatically 208 when the first CUDA call is made unless you call PetscCUDAInitialize() before any CUDA operations are performed 209 . -cuda_view - view information about the CUDA devices 210 . -cuda_synchronize - wait at the end of asynchronize CUDA calls so that their time gets credited to the current event; default with -log_view 211 - -cuda_set_device <gpu> - integer number of the device 212 213 Level: beginner 214 215 Notes: 216 Initializing cuBLAS takes about 1/2 second there it is done by default in PetscInitialize() before logging begins 217 218 @*/ 219 PetscErrorCode PetscCUDAInitialize(MPI_Comm comm) 220 { 221 PetscErrorCode ierr; 222 PetscInt deviceOpt = 0; 223 PetscBool cuda_view_flag = PETSC_FALSE,flg; 224 struct cudaDeviceProp prop; 225 int devCount,device,devicecnt; 226 cudaError_t err = cudaSuccess; 227 PetscMPIInt rank,size; 228 229 PetscFunctionBegin; 230 /* 231 If collecting logging information, by default, wait for GPU to complete its operations 232 before returning to the CPU in order to get accurate timings of each event 233 */ 234 ierr = PetscOptionsHasName(NULL,NULL,"-log_summary",&PetscCUDASynchronize);CHKERRQ(ierr); 235 if (!PetscCUDASynchronize) { 236 ierr = PetscOptionsHasName(NULL,NULL,"-log_view",&PetscCUDASynchronize);CHKERRQ(ierr); 237 } 238 239 ierr = PetscOptionsBegin(comm,NULL,"CUDA options","Sys");CHKERRQ(ierr); 240 ierr = PetscOptionsInt("-cuda_set_device","Set all MPI ranks to use the specified CUDA device",NULL,deviceOpt,&deviceOpt,&flg);CHKERRQ(ierr); 241 device = (int)deviceOpt; 242 ierr = PetscOptionsBool("-cuda_synchronize","Wait for the GPU to complete operations before returning to the CPU",NULL,PetscCUDASynchronize,&PetscCUDASynchronize,NULL);CHKERRQ(ierr); 243 ierr = PetscOptionsDeprecated("-cuda_show_devices","-cuda_view","3.12",NULL);CHKERRQ(ierr); 244 ierr = PetscOptionsName("-cuda_view","Display CUDA device information and assignments",NULL,&cuda_view_flag);CHKERRQ(ierr); 245 ierr = PetscOptionsEnd();CHKERRQ(ierr); 246 if (!PetscCUDAInitialized) { 247 ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr); 248 249 if (size>1 && !flg) { 250 /* check to see if we force multiple ranks to hit the same GPU */ 251 /* we're not using the same GPU on multiple MPI threads. So try to allocated different GPUs to different processes */ 252 253 /* First get the device count */ 254 err = cudaGetDeviceCount(&devCount); 255 if (err != cudaSuccess) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SYS,"error in cudaGetDeviceCount %s",cudaGetErrorString(err)); 256 257 /* next determine the rank and then set the device via a mod */ 258 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 259 device = rank % devCount; 260 } 261 err = cudaSetDevice(device); 262 if (err != cudaSuccess) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SYS,"error in cudaSetDevice %s",cudaGetErrorString(err)); 263 264 /* set the device flags so that it can map host memory */ 265 err = cudaSetDeviceFlags(cudaDeviceMapHost); 266 if (err != cudaSuccess) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SYS,"error in cudaSetDeviceFlags %s",cudaGetErrorString(err)); 267 268 ierr = PetscCUBLASInitializeHandle();CHKERRQ(ierr); 269 ierr = PetscCUSOLVERDnInitializeHandle();CHKERRQ(ierr); 270 PetscCUDAInitialized = PETSC_TRUE; 271 } 272 if (cuda_view_flag) { 273 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 274 err = cudaGetDeviceCount(&devCount); 275 if (err != cudaSuccess) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SYS,"error in cudaGetDeviceCount %s",cudaGetErrorString(err)); 276 for (devicecnt = 0; devicecnt < devCount; ++devicecnt) { 277 err = cudaGetDeviceProperties(&prop,devicecnt); 278 if (err != cudaSuccess) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SYS,"error in cudaGetDeviceProperties %s",cudaGetErrorString(err)); 279 ierr = PetscPrintf(comm, "CUDA device %d: %s\n", devicecnt, prop.name);CHKERRQ(ierr); 280 } 281 ierr = PetscSynchronizedPrintf(comm,"[%d] Using CUDA device %d.\n",rank,device);CHKERRQ(ierr); 282 ierr = PetscSynchronizedFlush(comm,PETSC_STDOUT);CHKERRQ(ierr); 283 } 284 PetscFunctionReturn(0); 285 } 286 #endif 287 288 /*@C 289 PetscEnd - Calls PetscFinalize() and then ends the program. This is useful if one 290 wishes a clean exit somewhere deep in the program. 291 292 Collective on PETSC_COMM_WORLD 293 294 Options Database Keys are the same as for PetscFinalize() 295 296 Level: advanced 297 298 Note: 299 See PetscInitialize() for more general runtime options. 300 301 .seealso: PetscInitialize(), PetscOptionsView(), PetscMallocDump(), PetscMPIDump(), PetscFinalize() 302 @*/ 303 PetscErrorCode PetscEnd(void) 304 { 305 PetscFunctionBegin; 306 PetscFinalize(); 307 exit(0); 308 return 0; 309 } 310 311 PetscBool PetscOptionsPublish = PETSC_FALSE; 312 PETSC_INTERN PetscErrorCode PetscSetUseHBWMalloc_Private(void); 313 PETSC_INTERN PetscBool petscsetmallocvisited; 314 static char emacsmachinename[256]; 315 316 PetscErrorCode (*PetscExternalVersionFunction)(MPI_Comm) = 0; 317 PetscErrorCode (*PetscExternalHelpFunction)(MPI_Comm) = 0; 318 319 /*@C 320 PetscSetHelpVersionFunctions - Sets functions that print help and version information 321 before the PETSc help and version information is printed. Must call BEFORE PetscInitialize(). 322 This routine enables a "higher-level" package that uses PETSc to print its messages first. 323 324 Input Parameter: 325 + help - the help function (may be NULL) 326 - version - the version function (may be NULL) 327 328 Level: developer 329 330 @*/ 331 PetscErrorCode PetscSetHelpVersionFunctions(PetscErrorCode (*help)(MPI_Comm),PetscErrorCode (*version)(MPI_Comm)) 332 { 333 PetscFunctionBegin; 334 PetscExternalHelpFunction = help; 335 PetscExternalVersionFunction = version; 336 PetscFunctionReturn(0); 337 } 338 339 #if defined(PETSC_USE_LOG) 340 PETSC_INTERN PetscBool PetscObjectsLog; 341 #endif 342 343 PETSC_INTERN PetscErrorCode PetscOptionsCheckInitial_Private(void) 344 { 345 char string[64],mname[PETSC_MAX_PATH_LEN],*f; 346 MPI_Comm comm = PETSC_COMM_WORLD; 347 PetscBool flg1 = PETSC_FALSE,flg2 = PETSC_FALSE,flg3 = PETSC_FALSE,flag; 348 PetscErrorCode ierr; 349 PetscReal si; 350 PetscInt intensity; 351 int i; 352 PetscMPIInt rank; 353 char version[256],helpoptions[256]; 354 #if defined(PETSC_USE_LOG) 355 PetscViewerFormat format; 356 PetscBool flg4 = PETSC_FALSE; 357 #endif 358 #if defined(PETSC_HAVE_CUDA) 359 PetscBool initCuda = PETSC_TRUE; 360 #endif 361 362 PetscFunctionBegin; 363 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 364 365 #if !defined(PETSC_HAVE_THREADSAFETY) 366 if (!(PETSC_RUNNING_ON_VALGRIND)) { 367 /* 368 Setup the memory management; support for tracing malloc() usage 369 */ 370 PetscBool mdebug = PETSC_FALSE, eachcall = PETSC_FALSE, initializenan = PETSC_FALSE, mlog = PETSC_FALSE; 371 372 #if defined(PETSC_USE_DEBUG) 373 mdebug = PETSC_TRUE; 374 initializenan = PETSC_TRUE; 375 ierr = PetscOptionsHasName(NULL,NULL,"-malloc_test",&flg1);CHKERRQ(ierr); 376 #else 377 /* don't warn about unused option */ 378 ierr = PetscOptionsHasName(NULL,NULL,"-malloc_test",&flg1);CHKERRQ(ierr); 379 flg1 = PETSC_FALSE; 380 #endif 381 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc_debug",&flg2,&flg3);CHKERRQ(ierr); 382 if (flg1 || flg2) { 383 mdebug = PETSC_TRUE; 384 eachcall = PETSC_TRUE; 385 initializenan = PETSC_TRUE; 386 } else if (flg3 && !flg2) { 387 mdebug = PETSC_FALSE; 388 eachcall = PETSC_FALSE; 389 initializenan = PETSC_FALSE; 390 } 391 392 ierr = PetscOptionsHasName(NULL,NULL,"-malloc_view",&mlog);CHKERRQ(ierr); 393 if (mlog) { 394 mdebug = PETSC_TRUE; 395 } 396 /* the next line is deprecated */ 397 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc",&mdebug,NULL);CHKERRQ(ierr); 398 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc_dump",&mdebug,NULL);CHKERRQ(ierr); 399 ierr = PetscOptionsGetBool(NULL,NULL,"-log_view_memory",&mdebug,NULL);CHKERRQ(ierr); 400 if (mdebug) { 401 ierr = PetscMallocSetDebug(eachcall,initializenan);CHKERRQ(ierr); 402 } 403 if (mlog) { 404 PetscReal logthreshold = 0; 405 ierr = PetscOptionsGetReal(NULL,NULL,"-malloc_view_threshold",&logthreshold,NULL);CHKERRQ(ierr); 406 ierr = PetscMallocViewSet(logthreshold);CHKERRQ(ierr); 407 } 408 } 409 410 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc_coalesce",&flg1,&flg2);CHKERRQ(ierr); 411 if (flg2) {ierr = PetscMallocSetCoalesce(flg1);CHKERRQ(ierr);} 412 flg1 = PETSC_FALSE; 413 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc_hbw",&flg1,NULL);CHKERRQ(ierr); 414 /* ignore this option if malloc is already set */ 415 if (flg1 && !petscsetmallocvisited) {ierr = PetscSetUseHBWMalloc_Private();CHKERRQ(ierr);} 416 417 flg1 = PETSC_FALSE; 418 ierr = PetscOptionsGetBool(NULL,NULL,"-malloc_info",&flg1,NULL);CHKERRQ(ierr); 419 if (!flg1) { 420 flg1 = PETSC_FALSE; 421 ierr = PetscOptionsGetBool(NULL,NULL,"-memory_view",&flg1,NULL);CHKERRQ(ierr); 422 } 423 if (flg1) { 424 ierr = PetscMemorySetGetMaximumUsage();CHKERRQ(ierr); 425 } 426 #endif 427 428 #if defined(PETSC_USE_LOG) 429 ierr = PetscOptionsHasName(NULL,NULL,"-objects_dump",&PetscObjectsLog);CHKERRQ(ierr); 430 #endif 431 432 /* 433 Set the display variable for graphics 434 */ 435 ierr = PetscSetDisplay();CHKERRQ(ierr); 436 437 /* 438 Print the PETSc version information 439 */ 440 ierr = PetscOptionsHasName(NULL,NULL,"-v",&flg1);CHKERRQ(ierr); 441 ierr = PetscOptionsHasName(NULL,NULL,"-version",&flg2);CHKERRQ(ierr); 442 ierr = PetscOptionsHasHelp(NULL,&flg3);CHKERRQ(ierr); 443 if (flg1 || flg2 || flg3) { 444 445 /* 446 Print "higher-level" package version message 447 */ 448 if (PetscExternalVersionFunction) { 449 ierr = (*PetscExternalVersionFunction)(comm);CHKERRQ(ierr); 450 } 451 452 ierr = PetscGetVersion(version,256);CHKERRQ(ierr); 453 ierr = (*PetscHelpPrintf)(comm,"--------------------------------------------------------------------------\n");CHKERRQ(ierr); 454 ierr = (*PetscHelpPrintf)(comm,"%s\n",version);CHKERRQ(ierr); 455 ierr = (*PetscHelpPrintf)(comm,"%s",PETSC_AUTHOR_INFO);CHKERRQ(ierr); 456 ierr = (*PetscHelpPrintf)(comm,"See docs/changes/index.html for recent updates.\n");CHKERRQ(ierr); 457 ierr = (*PetscHelpPrintf)(comm,"See docs/faq.html for problems.\n");CHKERRQ(ierr); 458 ierr = (*PetscHelpPrintf)(comm,"See docs/manualpages/index.html for help. \n");CHKERRQ(ierr); 459 ierr = (*PetscHelpPrintf)(comm,"Libraries linked from %s\n",PETSC_LIB_DIR);CHKERRQ(ierr); 460 ierr = (*PetscHelpPrintf)(comm,"--------------------------------------------------------------------------\n");CHKERRQ(ierr); 461 } 462 463 /* 464 Print "higher-level" package help message 465 */ 466 if (flg3) { 467 if (PetscExternalHelpFunction) { 468 ierr = (*PetscExternalHelpFunction)(comm);CHKERRQ(ierr); 469 } 470 } 471 472 ierr = PetscOptionsGetString(NULL,NULL,"-help",helpoptions,sizeof(helpoptions),&flg1);CHKERRQ(ierr); 473 if (flg1) { 474 ierr = PetscStrcmp(helpoptions,"intro",&flg2);CHKERRQ(ierr); 475 if (flg2) { 476 ierr = PetscOptionsDestroyDefault();CHKERRQ(ierr); 477 ierr = PetscFreeMPIResources();CHKERRQ(ierr); 478 ierr = MPI_Finalize();CHKERRQ(ierr); 479 exit(0); 480 } 481 } 482 483 /* 484 Setup the error handling 485 */ 486 flg1 = PETSC_FALSE; 487 ierr = PetscOptionsGetBool(NULL,NULL,"-on_error_abort",&flg1,NULL);CHKERRQ(ierr); 488 if (flg1) { 489 ierr = MPI_Comm_set_errhandler(comm,MPI_ERRORS_ARE_FATAL);CHKERRQ(ierr); 490 ierr = PetscPushErrorHandler(PetscAbortErrorHandler,0);CHKERRQ(ierr); 491 } 492 flg1 = PETSC_FALSE; 493 ierr = PetscOptionsGetBool(NULL,NULL,"-on_error_mpiabort",&flg1,NULL);CHKERRQ(ierr); 494 if (flg1) { ierr = PetscPushErrorHandler(PetscMPIAbortErrorHandler,0);CHKERRQ(ierr);} 495 flg1 = PETSC_FALSE; 496 ierr = PetscOptionsGetBool(NULL,NULL,"-mpi_return_on_error",&flg1,NULL);CHKERRQ(ierr); 497 if (flg1) { 498 ierr = MPI_Comm_set_errhandler(comm,MPI_ERRORS_RETURN);CHKERRQ(ierr); 499 } 500 flg1 = PETSC_FALSE; 501 ierr = PetscOptionsGetBool(NULL,NULL,"-no_signal_handler",&flg1,NULL);CHKERRQ(ierr); 502 if (!flg1) {ierr = PetscPushSignalHandler(PetscSignalHandlerDefault,(void*)0);CHKERRQ(ierr);} 503 flg1 = PETSC_FALSE; 504 ierr = PetscOptionsGetBool(NULL,NULL,"-fp_trap",&flg1,&flag);CHKERRQ(ierr); 505 if (flag) {ierr = PetscSetFPTrap((PetscFPTrap)flg1);CHKERRQ(ierr);} 506 ierr = PetscOptionsGetInt(NULL,NULL,"-check_pointer_intensity",&intensity,&flag);CHKERRQ(ierr); 507 if (flag) {ierr = PetscCheckPointerSetIntensity(intensity);CHKERRQ(ierr);} 508 509 /* 510 Setup debugger information 511 */ 512 ierr = PetscSetDefaultDebugger();CHKERRQ(ierr); 513 ierr = PetscOptionsGetString(NULL,NULL,"-on_error_attach_debugger",string,64,&flg1);CHKERRQ(ierr); 514 if (flg1) { 515 MPI_Errhandler err_handler; 516 517 ierr = PetscSetDebuggerFromString(string);CHKERRQ(ierr); 518 ierr = MPI_Comm_create_errhandler(Petsc_MPI_DebuggerOnError,&err_handler);CHKERRQ(ierr); 519 ierr = MPI_Comm_set_errhandler(comm,err_handler);CHKERRQ(ierr); 520 ierr = PetscPushErrorHandler(PetscAttachDebuggerErrorHandler,0);CHKERRQ(ierr); 521 } 522 ierr = PetscOptionsGetString(NULL,NULL,"-debug_terminal",string,64,&flg1);CHKERRQ(ierr); 523 if (flg1) { ierr = PetscSetDebugTerminal(string);CHKERRQ(ierr); } 524 ierr = PetscOptionsGetString(NULL,NULL,"-start_in_debugger",string,64,&flg1);CHKERRQ(ierr); 525 ierr = PetscOptionsGetString(NULL,NULL,"-stop_for_debugger",string,64,&flg2);CHKERRQ(ierr); 526 if (flg1 || flg2) { 527 PetscMPIInt size; 528 PetscInt lsize,*nodes; 529 MPI_Errhandler err_handler; 530 /* 531 we have to make sure that all processors have opened 532 connections to all other processors, otherwise once the 533 debugger has stated it is likely to receive a SIGUSR1 534 and kill the program. 535 */ 536 ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr); 537 if (size > 2) { 538 PetscMPIInt dummy = 0; 539 MPI_Status status; 540 for (i=0; i<size; i++) { 541 if (rank != i) { 542 ierr = MPI_Send(&dummy,1,MPI_INT,i,109,comm);CHKERRQ(ierr); 543 } 544 } 545 for (i=0; i<size; i++) { 546 if (rank != i) { 547 ierr = MPI_Recv(&dummy,1,MPI_INT,i,109,comm,&status);CHKERRQ(ierr); 548 } 549 } 550 } 551 /* check if this processor node should be in debugger */ 552 ierr = PetscMalloc1(size,&nodes);CHKERRQ(ierr); 553 lsize = size; 554 ierr = PetscOptionsGetIntArray(NULL,NULL,"-debugger_nodes",nodes,&lsize,&flag);CHKERRQ(ierr); 555 if (flag) { 556 for (i=0; i<lsize; i++) { 557 if (nodes[i] == rank) { flag = PETSC_FALSE; break; } 558 } 559 } 560 if (!flag) { 561 ierr = PetscSetDebuggerFromString(string);CHKERRQ(ierr); 562 ierr = PetscPushErrorHandler(PetscAbortErrorHandler,0);CHKERRQ(ierr); 563 if (flg1) { 564 ierr = PetscAttachDebugger();CHKERRQ(ierr); 565 } else { 566 ierr = PetscStopForDebugger();CHKERRQ(ierr); 567 } 568 ierr = MPI_Comm_create_errhandler(Petsc_MPI_AbortOnError,&err_handler);CHKERRQ(ierr); 569 ierr = MPI_Comm_set_errhandler(comm,err_handler);CHKERRQ(ierr); 570 } 571 ierr = PetscFree(nodes);CHKERRQ(ierr); 572 } 573 574 ierr = PetscOptionsGetString(NULL,NULL,"-on_error_emacs",emacsmachinename,128,&flg1);CHKERRQ(ierr); 575 if (flg1 && !rank) {ierr = PetscPushErrorHandler(PetscEmacsClientErrorHandler,emacsmachinename);CHKERRQ(ierr);} 576 577 /* 578 Setup profiling and logging 579 */ 580 #if defined(PETSC_USE_INFO) 581 { 582 char logname[PETSC_MAX_PATH_LEN]; logname[0] = 0; 583 ierr = PetscOptionsGetString(NULL,NULL,"-info",logname,250,&flg1);CHKERRQ(ierr); 584 if (flg1 && logname[0]) { 585 ierr = PetscInfoAllow(PETSC_TRUE,logname);CHKERRQ(ierr); 586 } else if (flg1) { 587 ierr = PetscInfoAllow(PETSC_TRUE,NULL);CHKERRQ(ierr); 588 } 589 } 590 #endif 591 #if defined(PETSC_USE_LOG) 592 mname[0] = 0; 593 ierr = PetscOptionsGetString(NULL,NULL,"-history",mname,PETSC_MAX_PATH_LEN,&flg1);CHKERRQ(ierr); 594 if (flg1) { 595 if (mname[0]) { 596 ierr = PetscOpenHistoryFile(mname,&petsc_history);CHKERRQ(ierr); 597 } else { 598 ierr = PetscOpenHistoryFile(NULL,&petsc_history);CHKERRQ(ierr); 599 } 600 } 601 602 ierr = PetscOptionsGetBool(NULL,NULL,"-log_sync",&PetscLogSyncOn,NULL);CHKERRQ(ierr); 603 604 #if defined(PETSC_HAVE_MPE) 605 flg1 = PETSC_FALSE; 606 ierr = PetscOptionsHasName(NULL,NULL,"-log_mpe",&flg1);CHKERRQ(ierr); 607 if (flg1) {ierr = PetscLogMPEBegin();CHKERRQ(ierr);} 608 #endif 609 flg1 = PETSC_FALSE; 610 flg3 = PETSC_FALSE; 611 ierr = PetscOptionsGetBool(NULL,NULL,"-log_all",&flg1,NULL);CHKERRQ(ierr); 612 ierr = PetscOptionsHasName(NULL,NULL,"-log_summary",&flg3);CHKERRQ(ierr); 613 if (flg1) { ierr = PetscLogAllBegin();CHKERRQ(ierr); } 614 else if (flg3) { ierr = PetscLogDefaultBegin();CHKERRQ(ierr);} 615 616 ierr = PetscOptionsGetString(NULL,NULL,"-log_trace",mname,250,&flg1);CHKERRQ(ierr); 617 if (flg1) { 618 char name[PETSC_MAX_PATH_LEN],fname[PETSC_MAX_PATH_LEN]; 619 FILE *file; 620 if (mname[0]) { 621 PetscSNPrintf(name,PETSC_MAX_PATH_LEN,"%s.%d",mname,rank); 622 ierr = PetscFixFilename(name,fname);CHKERRQ(ierr); 623 file = fopen(fname,"w"); 624 if (!file) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_FILE_OPEN,"Unable to open trace file: %s",fname); 625 } else file = PETSC_STDOUT; 626 ierr = PetscLogTraceBegin(file);CHKERRQ(ierr); 627 } 628 629 ierr = PetscOptionsGetViewer(comm,NULL,NULL,"-log_view",NULL,&format,&flg4);CHKERRQ(ierr); 630 if (flg4) { 631 if (format == PETSC_VIEWER_ASCII_XML) { 632 ierr = PetscLogNestedBegin();CHKERRQ(ierr); 633 } else { 634 ierr = PetscLogDefaultBegin();CHKERRQ(ierr); 635 } 636 } 637 if (flg4 && format == PETSC_VIEWER_ASCII_XML) { 638 PetscReal threshold = PetscRealConstant(0.01); 639 ierr = PetscOptionsGetReal(NULL,NULL,"-log_threshold",&threshold,&flg1);CHKERRQ(ierr); 640 if (flg1) {ierr = PetscLogSetThreshold((PetscLogDouble)threshold,NULL);CHKERRQ(ierr);} 641 } 642 #endif 643 644 ierr = PetscOptionsGetBool(NULL,NULL,"-saws_options",&PetscOptionsPublish,NULL);CHKERRQ(ierr); 645 646 #if defined(PETSC_HAVE_CUDA) 647 ierr = PetscOptionsBegin(comm,NULL,"CUDA initialize","Sys");CHKERRQ(ierr); 648 ierr = PetscOptionsBool("-cuda_initialize","Initialize the CUDA devices and cuBLAS during PetscInitialize()",NULL,initCuda,&initCuda,NULL);CHKERRQ(ierr); 649 ierr = PetscOptionsEnd();CHKERRQ(ierr); 650 if (initCuda) {ierr = PetscCUDAInitialize(PETSC_COMM_WORLD);CHKERRQ(ierr);} 651 #endif 652 653 /* 654 Print basic help message 655 */ 656 ierr = PetscOptionsHasHelp(NULL,&flg1);CHKERRQ(ierr); 657 if (flg1) { 658 ierr = (*PetscHelpPrintf)(comm,"Options for all PETSc programs:\n");CHKERRQ(ierr); 659 ierr = (*PetscHelpPrintf)(comm," -help: prints help method for each option\n");CHKERRQ(ierr); 660 ierr = (*PetscHelpPrintf)(comm," -on_error_abort: cause an abort when an error is detected. Useful \n ");CHKERRQ(ierr); 661 ierr = (*PetscHelpPrintf)(comm," only when run in the debugger\n");CHKERRQ(ierr); 662 ierr = (*PetscHelpPrintf)(comm," -on_error_attach_debugger [gdb,dbx,xxgdb,ups,noxterm]\n");CHKERRQ(ierr); 663 ierr = (*PetscHelpPrintf)(comm," start the debugger in new xterm\n");CHKERRQ(ierr); 664 ierr = (*PetscHelpPrintf)(comm," unless noxterm is given\n");CHKERRQ(ierr); 665 ierr = (*PetscHelpPrintf)(comm," -start_in_debugger [gdb,dbx,xxgdb,ups,noxterm]\n");CHKERRQ(ierr); 666 ierr = (*PetscHelpPrintf)(comm," start all processes in the debugger\n");CHKERRQ(ierr); 667 ierr = (*PetscHelpPrintf)(comm," -on_error_emacs <machinename>\n");CHKERRQ(ierr); 668 ierr = (*PetscHelpPrintf)(comm," emacs jumps to error file\n");CHKERRQ(ierr); 669 ierr = (*PetscHelpPrintf)(comm," -debugger_nodes [n1,n2,..] Nodes to start in debugger\n");CHKERRQ(ierr); 670 ierr = (*PetscHelpPrintf)(comm," -debugger_pause [m] : delay (in seconds) to attach debugger\n");CHKERRQ(ierr); 671 ierr = (*PetscHelpPrintf)(comm," -stop_for_debugger : prints message on how to attach debugger manually\n");CHKERRQ(ierr); 672 ierr = (*PetscHelpPrintf)(comm," waits the delay for you to attach\n");CHKERRQ(ierr); 673 ierr = (*PetscHelpPrintf)(comm," -display display: Location where X window graphics and debuggers are displayed\n");CHKERRQ(ierr); 674 ierr = (*PetscHelpPrintf)(comm," -no_signal_handler: do not trap error signals\n");CHKERRQ(ierr); 675 ierr = (*PetscHelpPrintf)(comm," -mpi_return_on_error: MPI returns error code, rather than abort on internal error\n");CHKERRQ(ierr); 676 ierr = (*PetscHelpPrintf)(comm," -fp_trap: stop on floating point exceptions\n");CHKERRQ(ierr); 677 ierr = (*PetscHelpPrintf)(comm," note on IBM RS6000 this slows run greatly\n");CHKERRQ(ierr); 678 ierr = (*PetscHelpPrintf)(comm," -malloc_dump <optional filename>: dump list of unfreed memory at conclusion\n");CHKERRQ(ierr); 679 ierr = (*PetscHelpPrintf)(comm," -malloc: use PETSc error checking malloc (deprecated, use -malloc_debug)\n");CHKERRQ(ierr); 680 ierr = (*PetscHelpPrintf)(comm," -malloc no: don't use PETSc error checking malloc (deprecated, use -malloc_debug no)\n");CHKERRQ(ierr); 681 ierr = (*PetscHelpPrintf)(comm," -malloc_info: prints total memory usage\n");CHKERRQ(ierr); 682 ierr = (*PetscHelpPrintf)(comm," -malloc_view <optional filename>: keeps log of all memory allocations, displays in PetscFinalize()\n");CHKERRQ(ierr); 683 ierr = (*PetscHelpPrintf)(comm," -malloc_debug <true or false>: enables or disables extended checking for memory corruption\n");CHKERRQ(ierr); 684 ierr = (*PetscHelpPrintf)(comm," -options_view: dump list of options inputted\n");CHKERRQ(ierr); 685 ierr = (*PetscHelpPrintf)(comm," -options_left: dump list of unused options\n");CHKERRQ(ierr); 686 ierr = (*PetscHelpPrintf)(comm," -options_left no: don't dump list of unused options\n");CHKERRQ(ierr); 687 ierr = (*PetscHelpPrintf)(comm," -tmp tmpdir: alternative /tmp directory\n");CHKERRQ(ierr); 688 ierr = (*PetscHelpPrintf)(comm," -shared_tmp: tmp directory is shared by all processors\n");CHKERRQ(ierr); 689 ierr = (*PetscHelpPrintf)(comm," -not_shared_tmp: each processor has separate tmp directory\n");CHKERRQ(ierr); 690 ierr = (*PetscHelpPrintf)(comm," -memory_view: print memory usage at end of run\n");CHKERRQ(ierr); 691 #if defined(PETSC_USE_LOG) 692 ierr = (*PetscHelpPrintf)(comm," -get_total_flops: total flops over all processors\n");CHKERRQ(ierr); 693 ierr = (*PetscHelpPrintf)(comm," -log_view [:filename:[format]]: logging objects and events\n");CHKERRQ(ierr); 694 ierr = (*PetscHelpPrintf)(comm," -log_trace [filename]: prints trace of all PETSc calls\n");CHKERRQ(ierr); 695 #if defined(PETSC_HAVE_MPE) 696 ierr = (*PetscHelpPrintf)(comm," -log_mpe: Also create logfile viewable through Jumpshot\n");CHKERRQ(ierr); 697 #endif 698 ierr = (*PetscHelpPrintf)(comm," -info <optional filename>: print informative messages about the calculations\n");CHKERRQ(ierr); 699 #endif 700 ierr = (*PetscHelpPrintf)(comm," -v: prints PETSc version number and release date\n");CHKERRQ(ierr); 701 ierr = (*PetscHelpPrintf)(comm," -options_file <file>: reads options from file\n");CHKERRQ(ierr); 702 ierr = (*PetscHelpPrintf)(comm," -petsc_sleep n: sleeps n seconds before running program\n");CHKERRQ(ierr); 703 ierr = (*PetscHelpPrintf)(comm,"-----------------------------------------------\n");CHKERRQ(ierr); 704 } 705 706 #if defined(PETSC_HAVE_POPEN) 707 { 708 char machine[128]; 709 ierr = PetscOptionsGetString(NULL,NULL,"-popen_machine",machine,128,&flg1);CHKERRQ(ierr); 710 if (flg1) { 711 ierr = PetscPOpenSetMachine(machine);CHKERRQ(ierr); 712 } 713 } 714 #endif 715 716 ierr = PetscOptionsGetReal(NULL,NULL,"-petsc_sleep",&si,&flg1);CHKERRQ(ierr); 717 if (flg1) { 718 ierr = PetscSleep(si);CHKERRQ(ierr); 719 } 720 721 ierr = PetscOptionsGetString(NULL,NULL,"-info_exclude",mname,PETSC_MAX_PATH_LEN,&flg1);CHKERRQ(ierr); 722 if (flg1) { 723 ierr = PetscStrstr(mname,"null",&f);CHKERRQ(ierr); 724 if (f) { 725 ierr = PetscInfoDeactivateClass(0);CHKERRQ(ierr); 726 } 727 } 728 729 #if defined(PETSC_HAVE_VIENNACL) 730 ierr = PetscOptionsHasName(NULL,NULL,"-log_summary",&flg3);CHKERRQ(ierr); 731 if (!flg3) { 732 ierr = PetscOptionsHasName(NULL,NULL,"-log_view",&flg3);CHKERRQ(ierr); 733 } 734 ierr = PetscOptionsGetBool(NULL,NULL,"-viennacl_synchronize",&flg3,NULL);CHKERRQ(ierr); 735 PetscViennaCLSynchronize = flg3; 736 ierr = PetscViennaCLInit();CHKERRQ(ierr); 737 #endif 738 739 /* 740 Creates the logging data structures; this is enabled even if logging is not turned on 741 This is the last thing we do before returning to the user code to prevent having the 742 logging numbers contaminated by any startup time associated with MPI and the GPUs 743 */ 744 #if defined(PETSC_USE_LOG) 745 ierr = PetscLogInitialize();CHKERRQ(ierr); 746 #endif 747 748 PetscFunctionReturn(0); 749 } 750