1 2 #include <petsc/private/viewerimpl.h> /* "petscsys.h" */ 3 #include <petsc/private/pcimpl.h> 4 #include <../src/mat/impls/aij/seq/aij.h> 5 #include <mathematica.h> 6 7 #if defined(PETSC_HAVE__SNPRINTF) && !defined(PETSC_HAVE_SNPRINTF) 8 #define snprintf _snprintf 9 #endif 10 11 PetscViewer PETSC_VIEWER_MATHEMATICA_WORLD_PRIVATE = NULL; 12 static void *mathematicaEnv = NULL; 13 14 static PetscBool PetscViewerMathematicaPackageInitialized = PETSC_FALSE; 15 /*@C 16 PetscViewerMathematicaFinalizePackage - This function destroys everything in the Petsc interface to Mathematica. It is 17 called from PetscFinalize(). 18 19 Level: developer 20 21 .keywords: Petsc, destroy, package, mathematica 22 .seealso: PetscFinalize() 23 @*/ 24 PetscErrorCode PetscViewerMathematicaFinalizePackage(void) 25 { 26 PetscFunctionBegin; 27 if (mathematicaEnv) MLDeinitialize((MLEnvironment) mathematicaEnv); 28 PetscViewerMathematicaPackageInitialized = PETSC_TRUE; 29 PetscFunctionReturn(0); 30 } 31 32 /*@C 33 PetscViewerMathematicaInitializePackage - This function initializes everything in the Petsc interface to Mathematica. It is 34 called from PetscViewerInitializePackage(). 35 36 Level: developer 37 38 .keywords: Petsc, initialize, package 39 .seealso: PetscSysInitializePackage(), PetscInitialize() 40 @*/ 41 PetscErrorCode PetscViewerMathematicaInitializePackage(void) 42 { 43 PetscError ierr; 44 45 PetscFunctionBegin; 46 if (PetscViewerMathematicaPackageInitialized) PetscFunctionReturn(0); 47 PetscViewerMathematicaPackageInitialized = PETSC_TRUE; 48 49 mathematicaEnv = (void*) MLInitialize(0); 50 51 ierr = PetscRegisterFinalize(PetscViewerMathematicaFinalizePackage);CHKERRQ(ierr); 52 PetscFunctionReturn(0); 53 } 54 55 56 PetscErrorCode PetscViewerInitializeMathematicaWorld_Private() 57 { 58 PetscErrorCode ierr; 59 60 PetscFunctionBegin; 61 if (PETSC_VIEWER_MATHEMATICA_WORLD_PRIVATE) PetscFunctionReturn(0); 62 ierr = PetscViewerMathematicaOpen(PETSC_COMM_WORLD, PETSC_DECIDE, NULL, NULL, &PETSC_VIEWER_MATHEMATICA_WORLD_PRIVATE);CHKERRQ(ierr); 63 PetscFunctionReturn(0); 64 } 65 66 static PetscErrorCode PetscViewerDestroy_Mathematica(PetscViewer viewer) 67 { 68 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 69 PetscErrorCode ierr; 70 71 PetscFunctionBegin; 72 MLClose(vmath->link); 73 ierr = PetscFree(vmath->linkname);CHKERRQ(ierr); 74 ierr = PetscFree(vmath->linkhost);CHKERRQ(ierr); 75 ierr = PetscFree(vmath);CHKERRQ(ierr); 76 PetscFunctionReturn(0); 77 } 78 79 PetscErrorCode PetscViewerDestroyMathematica_Private(void) 80 { 81 PetscErrorCode ierr; 82 83 PetscFunctionBegin; 84 if (PETSC_VIEWER_MATHEMATICA_WORLD_PRIVATE) { 85 ierr = PetscViewerDestroy(PETSC_VIEWER_MATHEMATICA_WORLD_PRIVATE);CHKERRQ(ierr); 86 } 87 PetscFunctionReturn(0); 88 } 89 90 PetscErrorCode PetscViewerMathematicaSetupConnection_Private(PetscViewer v) 91 { 92 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) v->data; 93 #if defined(MATHEMATICA_3_0) 94 int argc = 6; 95 char *argv[6]; 96 #else 97 int argc = 5; 98 char *argv[5]; 99 #endif 100 char hostname[256]; 101 long lerr; 102 PetscErrorCode ierr; 103 104 PetscFunctionBegin; 105 /* Link name */ 106 argv[0] = "-linkname"; 107 if (!vmath->linkname) argv[1] = "math -mathlink"; 108 else argv[1] = vmath->linkname; 109 110 /* Link host */ 111 argv[2] = "-linkhost"; 112 if (!vmath->linkhost) { 113 ierr = PetscGetHostName(hostname, 255);CHKERRQ(ierr); 114 argv[3] = hostname; 115 } else argv[3] = vmath->linkhost; 116 117 /* Link mode */ 118 #if defined(MATHEMATICA_3_0) 119 argv[4] = "-linkmode"; 120 switch (vmath->linkmode) { 121 case MATHEMATICA_LINK_CREATE: 122 argv[5] = "Create"; 123 break; 124 case MATHEMATICA_LINK_CONNECT: 125 argv[5] = "Connect"; 126 break; 127 case MATHEMATICA_LINK_LAUNCH: 128 argv[5] = "Launch"; 129 break; 130 } 131 #else 132 switch (vmath->linkmode) { 133 case MATHEMATICA_LINK_CREATE: 134 argv[4] = "-linkcreate"; 135 break; 136 case MATHEMATICA_LINK_CONNECT: 137 argv[4] = "-linkconnect"; 138 break; 139 case MATHEMATICA_LINK_LAUNCH: 140 argv[4] = "-linklaunch"; 141 break; 142 } 143 #endif 144 vmath->link = MLOpenInEnv(mathematicaEnv, argc, argv, &lerr); 145 #endif 146 PetscFunctionReturn(0); 147 } 148 149 PETSC_EXTERN PetscErrorCode PetscViewerCreate_Mathematica(PetscViewer v) 150 { 151 PetscViewer_Mathematica *vmath; 152 PetscErrorCode ierr; 153 154 PetscFunctionBegin; 155 ierr = PetscViewerMathematicaInitializePackage();CHKERRQ(ierr); 156 157 ierr = PetscNewLog(v,&vmath);CHKERRQ(ierr); 158 v->data = (void*) vmath; 159 v->ops->destroy = PetscViewerDestroy_Mathematica; 160 v->ops->flush = 0; 161 ierr = PetscStrallocpy(PETSC_VIEWER_MATHEMATICA, &((PetscObject)v)->type_name);CHKERRQ(ierr); 162 163 vmath->linkname = NULL; 164 vmath->linkhost = NULL; 165 vmath->linkmode = MATHEMATICA_LINK_CONNECT; 166 vmath->graphicsType = GRAPHICS_MOTIF; 167 vmath->plotType = MATHEMATICA_TRIANGULATION_PLOT; 168 vmath->objName = NULL; 169 170 ierr = PetscViewerMathematicaSetFromOptions(v);CHKERRQ(ierr); 171 ierr = PetscViewerMathematicaSetupConnection_Private(v);CHKERRQ(ierr); 172 PetscFunctionReturn(0); 173 } 174 175 static PetscErrorCode PetscViewerMathematicaParseLinkMode(char *modename, LinkMode *mode) 176 { 177 PetscBool isCreate, isConnect, isLaunch; 178 PetscErrorCode ierr; 179 180 PetscFunctionBegin; 181 ierr = PetscStrcasecmp(modename, "Create", &isCreate);CHKERRQ(ierr); 182 ierr = PetscStrcasecmp(modename, "Connect", &isConnect);CHKERRQ(ierr); 183 ierr = PetscStrcasecmp(modename, "Launch", &isLaunch);CHKERRQ(ierr); 184 if (isCreate) *mode = MATHEMATICA_LINK_CREATE; 185 else if (isConnect) *mode = MATHEMATICA_LINK_CONNECT; 186 else if (isLaunch) *mode = MATHEMATICA_LINK_LAUNCH; 187 else SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Invalid Mathematica link mode: %s", modename); 188 PetscFunctionReturn(0); 189 } 190 191 PetscErrorCode PetscViewerMathematicaSetFromOptions(PetscViewer v) 192 { 193 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) v->data; 194 char linkname[256]; 195 char modename[256]; 196 char hostname[256]; 197 char type[256]; 198 PetscInt numPorts; 199 PetscInt *ports; 200 PetscInt numHosts; 201 int h; 202 char **hosts; 203 PetscMPIInt size, rank; 204 PetscBool opt; 205 PetscErrorCode ierr; 206 207 PetscFunctionBegin; 208 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)v), &size);CHKERRQ(ierr); 209 ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)v), &rank);CHKERRQ(ierr); 210 211 /* Get link name */ 212 ierr = PetscOptionsGetString("viewer_", "-math_linkname", linkname, 256, &opt);CHKERRQ(ierr); 213 if (opt) { 214 ierr = PetscViewerMathematicaSetLinkName(v, linkname);CHKERRQ(ierr); 215 } 216 /* Get link port */ 217 numPorts = size; 218 ierr = PetscMalloc1(size, &ports);CHKERRQ(ierr); 219 ierr = PetscOptionsGetIntArray("viewer_", "-math_linkport", ports, &numPorts, &opt);CHKERRQ(ierr); 220 if (opt) { 221 if (numPorts > rank) snprintf(linkname, 255, "%6d", ports[rank]); 222 else snprintf(linkname, 255, "%6d", ports[0]); 223 ierr = PetscViewerMathematicaSetLinkName(v, linkname);CHKERRQ(ierr); 224 } 225 ierr = PetscFree(ports);CHKERRQ(ierr); 226 /* Get link host */ 227 numHosts = size; 228 ierr = PetscMalloc1(size, &hosts);CHKERRQ(ierr); 229 ierr = PetscOptionsGetStringArray("viewer_", "-math_linkhost", hosts, &numHosts, &opt);CHKERRQ(ierr); 230 if (opt) { 231 if (numHosts > rank) { 232 ierr = PetscStrncpy(hostname, hosts[rank], 255);CHKERRQ(ierr); 233 } else { 234 ierr = PetscStrncpy(hostname, hosts[0], 255);CHKERRQ(ierr); 235 } 236 ierr = PetscViewerMathematicaSetLinkHost(v, hostname);CHKERRQ(ierr); 237 } 238 for (h = 0; h < numHosts; h++) { 239 ierr = PetscFree(hosts[h]);CHKERRQ(ierr); 240 } 241 ierr = PetscFree(hosts);CHKERRQ(ierr); 242 /* Get link mode */ 243 ierr = PetscOptionsGetString("viewer_", "-math_linkmode", modename, 256, &opt);CHKERRQ(ierr); 244 if (opt) { 245 LinkMode mode; 246 247 ierr = PetscViewerMathematicaParseLinkMode(modename, &mode);CHKERRQ(ierr); 248 ierr = PetscViewerMathematicaSetLinkMode(v, mode);CHKERRQ(ierr); 249 } 250 /* Get graphics type */ 251 ierr = PetscOptionsGetString("viewer_", "-math_graphics", type, 256, &opt);CHKERRQ(ierr); 252 if (opt) { 253 PetscBool isMotif, isPS, isPSFile; 254 255 ierr = PetscStrcasecmp(type, "Motif", &isMotif);CHKERRQ(ierr); 256 ierr = PetscStrcasecmp(type, "PS", &isPS);CHKERRQ(ierr); 257 ierr = PetscStrcasecmp(type, "PSFile", &isPSFile);CHKERRQ(ierr); 258 if (isMotif) vmath->graphicsType = GRAPHICS_MOTIF; 259 else if (isPS) vmath->graphicsType = GRAPHICS_PS_STDOUT; 260 else if (isPSFile) vmath->graphicsType = GRAPHICS_PS_FILE; 261 } 262 /* Get plot type */ 263 ierr = PetscOptionsGetString("viewer_", "-math_type", type, 256, &opt);CHKERRQ(ierr); 264 if (opt) { 265 PetscBool isTri, isVecTri, isVec, isSurface; 266 267 ierr = PetscStrcasecmp(type, "Triangulation", &isTri);CHKERRQ(ierr); 268 ierr = PetscStrcasecmp(type, "VectorTriangulation", &isVecTri);CHKERRQ(ierr); 269 ierr = PetscStrcasecmp(type, "Vector", &isVec);CHKERRQ(ierr); 270 ierr = PetscStrcasecmp(type, "Surface", &isSurface);CHKERRQ(ierr); 271 if (isTri) vmath->plotType = MATHEMATICA_TRIANGULATION_PLOT; 272 else if (isVecTri) vmath->plotType = MATHEMATICA_VECTOR_TRIANGULATION_PLOT; 273 else if (isVec) vmath->plotType = MATHEMATICA_VECTOR_PLOT; 274 else if (isSurface) vmath->plotType = MATHEMATICA_SURFACE_PLOT; 275 } 276 PetscFunctionReturn(0); 277 } 278 279 PetscErrorCode PetscViewerMathematicaSetLinkName(PetscViewer v, const char *name) 280 { 281 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) v->data; 282 PetscErrorCode ierr; 283 284 PetscFunctionBegin; 285 PetscValidHeaderSpecific(v,PETSC_VIEWER_CLASSID,1); 286 PetscValidCharPointer(name,2); 287 ierr = PetscStrallocpy(name, &vmath->linkname);CHKERRQ(ierr); 288 PetscFunctionReturn(0); 289 } 290 291 PetscErrorCode PetscViewerMathematicaSetLinkPort(PetscViewer v, int port) 292 { 293 char name[16]; 294 PetscErrorCode ierr; 295 296 PetscFunctionBegin; 297 snprintf(name, 16, "%6d", port); 298 ierr = PetscViewerMathematicaSetLinkName(v, name);CHKERRQ(ierr); 299 PetscFunctionReturn(0); 300 } 301 302 PetscErrorCode PetscViewerMathematicaSetLinkHost(PetscViewer v, const char *host) 303 { 304 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) v->data; 305 PetscErrorCode ierr; 306 307 PetscFunctionBegin; 308 PetscValidHeaderSpecific(v,PETSC_VIEWER_CLASSID,1); 309 PetscValidCharPointer(host,2); 310 ierr = PetscStrallocpy(host, &vmath->linkhost);CHKERRQ(ierr); 311 PetscFunctionReturn(0); 312 } 313 314 PetscErrorCode PetscViewerMathematicaSetLinkMode(PetscViewer v, LinkMode mode) 315 { 316 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) v->data; 317 318 PetscFunctionBegin; 319 vmath->linkmode = mode; 320 PetscFunctionReturn(0); 321 } 322 323 /*----------------------------------------- Public Functions --------------------------------------------------------*/ 324 /*@C 325 PetscViewerMathematicaOpen - Communicates with Mathemtica using MathLink. 326 327 Collective on comm 328 329 Input Parameters: 330 + comm - The MPI communicator 331 . port - [optional] The port to connect on, or PETSC_DECIDE 332 . machine - [optional] The machine to run Mathematica on, or NULL 333 - mode - [optional] The connection mode, or NULL 334 335 Output Parameter: 336 . viewer - The Mathematica viewer 337 338 Level: intermediate 339 340 Notes: 341 Most users should employ the following commands to access the 342 Mathematica viewers 343 $ 344 $ PetscViewerMathematicaOpen(MPI_Comm comm, int port, char *machine, char *mode, PetscViewer &viewer) 345 $ MatView(Mat matrix, PetscViewer viewer) 346 $ 347 $ or 348 $ 349 $ PetscViewerMathematicaOpen(MPI_Comm comm, int port, char *machine, char *mode, PetscViewer &viewer) 350 $ VecView(Vec vector, PetscViewer viewer) 351 352 Options Database Keys: 353 + -viewer_math_linkhost <machine> - The host machine for the kernel 354 . -viewer_math_linkname <name> - The full link name for the connection 355 . -viewer_math_linkport <port> - The port for the connection 356 . -viewer_math_mode <mode> - The mode, e.g. Launch, Connect 357 . -viewer_math_type <type> - The plot type, e.g. Triangulation, Vector 358 - -viewer_math_graphics <output> - The output type, e.g. Motif, PS, PSFile 359 360 .keywords: PetscViewer, Mathematica, open 361 362 .seealso: MatView(), VecView() 363 @*/ 364 PetscErrorCode PetscViewerMathematicaOpen(MPI_Comm comm, int port, const char machine[], const char mode[], PetscViewer *v) 365 { 366 PetscErrorCode ierr; 367 368 PetscFunctionBegin; 369 ierr = PetscViewerCreate(comm, v);CHKERRQ(ierr); 370 #if 0 371 LinkMode linkmode; 372 ierr = PetscViewerMathematicaSetLinkPort(*v, port);CHKERRQ(ierr); 373 ierr = PetscViewerMathematicaSetLinkHost(*v, machine);CHKERRQ(ierr); 374 ierr = PetscViewerMathematicaParseLinkMode(mode, &linkmode);CHKERRQ(ierr); 375 ierr = PetscViewerMathematicaSetLinkMode(*v, linkmode);CHKERRQ(ierr); 376 #endif 377 ierr = PetscViewerSetType(*v, PETSC_VIEWER_MATHEMATICA);CHKERRQ(ierr); 378 PetscFunctionReturn(0); 379 } 380 381 /*@C 382 PetscViewerMathematicaGetLink - Returns the link to Mathematica 383 384 Input Parameters: 385 . viewer - The Mathematica viewer 386 . link - The link to Mathematica 387 388 Level: intermediate 389 390 .keywords PetscViewer, Mathematica, link 391 .seealso PetscViewerMathematicaOpen() 392 @*/ 393 PetscErrorCode PetscViewerMathematicaGetLink(PetscViewer viewer, MLINK *link) 394 { 395 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 396 397 PetscFunctionBegin; 398 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID,1); 399 *link = vmath->link; 400 PetscFunctionReturn(0); 401 } 402 403 /*@C 404 PetscViewerMathematicaSkipPackets - Discard packets sent by Mathematica until a certain packet type is received 405 406 Input Parameters: 407 . viewer - The Mathematica viewer 408 . type - The packet type to search for, e.g RETURNPKT 409 410 Level: advanced 411 412 .keywords PetscViewer, Mathematica, packets 413 .seealso PetscViewerMathematicaSetName(), PetscViewerMathematicaGetVector() 414 @*/ 415 PetscErrorCode PetscViewerMathematicaSkipPackets(PetscViewer viewer, int type) 416 { 417 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 418 MLINK link = vmath->link; /* The link to Mathematica */ 419 int pkt; /* The packet type */ 420 421 PetscFunctionBegin; 422 while ((pkt = MLNextPacket(link)) && (pkt != type)) MLNewPacket(link); 423 if (!pkt) { 424 MLClearError(link); 425 SETERRQ(PETSC_COMM_SELF,PETSC_ERR_LIB, (char*) MLErrorMessage(link)); 426 } 427 PetscFunctionReturn(0); 428 } 429 430 /*@C 431 PetscViewerMathematicaGetName - Retrieve the default name for objects communicated to Mathematica 432 433 Input Parameter: 434 . viewer - The Mathematica viewer 435 436 Output Parameter: 437 . name - The name for new objects created in Mathematica 438 439 Level: intermediate 440 441 .keywords PetscViewer, Mathematica, name 442 .seealso PetscViewerMathematicaSetName(), PetscViewerMathematicaClearName() 443 @*/ 444 PetscErrorCode PetscViewerMathematicaGetName(PetscViewer viewer, const char **name) 445 { 446 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 447 448 PetscFunctionBegin; 449 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID,1); 450 PetscValidPointer(name,2); 451 *name = vmath->objName; 452 PetscFunctionReturn(0); 453 } 454 455 /*@C 456 PetscViewerMathematicaSetName - Override the default name for objects communicated to Mathematica 457 458 Input Parameters: 459 . viewer - The Mathematica viewer 460 . name - The name for new objects created in Mathematica 461 462 Level: intermediate 463 464 .keywords PetscViewer, Mathematica, name 465 .seealso PetscViewerMathematicaSetName(), PetscViewerMathematicaClearName() 466 @*/ 467 PetscErrorCode PetscViewerMathematicaSetName(PetscViewer viewer, const char name[]) 468 { 469 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 470 471 PetscFunctionBegin; 472 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID,1); 473 PetscValidPointer(name,2); 474 vmath->objName = name; 475 PetscFunctionReturn(0); 476 } 477 478 /*@C 479 PetscViewerMathematicaClearName - Use the default name for objects communicated to Mathematica 480 481 Input Parameter: 482 . viewer - The Mathematica viewer 483 484 Level: intermediate 485 486 .keywords PetscViewer, Mathematica, name 487 .seealso PetscViewerMathematicaGetName(), PetscViewerMathematicaSetName() 488 @*/ 489 PetscErrorCode PetscViewerMathematicaClearName(PetscViewer viewer) 490 { 491 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 492 493 PetscFunctionBegin; 494 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID,1); 495 vmath->objName = NULL; 496 PetscFunctionReturn(0); 497 } 498 499 /*@C 500 PetscViewerMathematicaGetVector - Retrieve a vector from Mathematica 501 502 Input Parameter: 503 . viewer - The Mathematica viewer 504 505 Output Parameter: 506 . v - The vector 507 508 Level: intermediate 509 510 .keywords PetscViewer, Mathematica, vector 511 .seealso VecView(), PetscViewerMathematicaPutVector() 512 @*/ 513 PetscErrorCode PetscViewerMathematicaGetVector(PetscViewer viewer, Vec v) 514 { 515 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 516 MLINK link; /* The link to Mathematica */ 517 char *name; 518 PetscScalar *mArray,*array; 519 long mSize; 520 int n; 521 PetscErrorCode ierr; 522 523 PetscFunctionBegin; 524 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID,1); 525 PetscValidHeaderSpecific(v, VEC_CLASSID,2); 526 527 /* Determine the object name */ 528 if (!vmath->objName) name = "vec"; 529 else name = (char*) vmath->objName; 530 531 link = vmath->link; 532 ierr = VecGetLocalSize(v, &n);CHKERRQ(ierr); 533 ierr = VecGetArray(v, &array);CHKERRQ(ierr); 534 MLPutFunction(link, "EvaluatePacket", 1); 535 MLPutSymbol(link, name); 536 MLEndPacket(link); 537 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 538 MLGetRealList(link, &mArray, &mSize); 539 if (n != mSize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Incompatible vector sizes %d %d",n,mSize); 540 ierr = PetscMemcpy(array, mArray, mSize * sizeof(double));CHKERRQ(ierr); 541 MLDisownRealList(link, mArray, mSize); 542 ierr = VecRestoreArray(v, &array);CHKERRQ(ierr); 543 PetscFunctionReturn(0); 544 } 545 546 /*@C 547 PetscViewerMathematicaPutVector - Send a vector to Mathematica 548 549 Input Parameters: 550 + viewer - The Mathematica viewer 551 - v - The vector 552 553 Level: intermediate 554 555 .keywords PetscViewer, Mathematica, vector 556 .seealso VecView(), PetscViewerMathematicaGetVector() 557 @*/ 558 PetscErrorCode PetscViewerMathematicaPutVector(PetscViewer viewer, Vec v) 559 { 560 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 561 MLINK link = vmath->link; /* The link to Mathematica */ 562 char *name; 563 PetscScalar *array; 564 int n; 565 PetscErrorCode ierr; 566 567 PetscFunctionBegin; 568 /* Determine the object name */ 569 if (!vmath->objName) name = "vec"; 570 else name = (char*) vmath->objName; 571 572 ierr = VecGetLocalSize(v, &n);CHKERRQ(ierr); 573 ierr = VecGetArray(v, &array);CHKERRQ(ierr); 574 575 /* Send the Vector object */ 576 MLPutFunction(link, "EvaluatePacket", 1); 577 MLPutFunction(link, "Set", 2); 578 MLPutSymbol(link, name); 579 MLPutRealList(link, array, n); 580 MLEndPacket(link); 581 /* Skip packets until ReturnPacket */ 582 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 583 /* Skip ReturnPacket */ 584 MLNewPacket(link); 585 586 ierr = VecRestoreArray(v, &array);CHKERRQ(ierr); 587 PetscFunctionReturn(0); 588 } 589 590 PetscErrorCode PetscViewerMathematicaPutMatrix(PetscViewer viewer, int m, int n, PetscReal *a) 591 { 592 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 593 MLINK link = vmath->link; /* The link to Mathematica */ 594 char *name; 595 PetscErrorCode ierr; 596 597 PetscFunctionBegin; 598 /* Determine the object name */ 599 if (!vmath->objName) name = "mat"; 600 else name = (char*) vmath->objName; 601 602 /* Send the dense matrix object */ 603 MLPutFunction(link, "EvaluatePacket", 1); 604 MLPutFunction(link, "Set", 2); 605 MLPutSymbol(link, name); 606 MLPutFunction(link, "Transpose", 1); 607 MLPutFunction(link, "Partition", 2); 608 MLPutRealList(link, a, m*n); 609 MLPutInteger(link, m); 610 MLEndPacket(link); 611 /* Skip packets until ReturnPacket */ 612 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 613 /* Skip ReturnPacket */ 614 MLNewPacket(link); 615 PetscFunctionReturn(0); 616 } 617 618 PetscErrorCode PetscViewerMathematicaPutCSRMatrix(PetscViewer viewer, int m, int n, int *i, int *j, PetscReal *a) 619 { 620 PetscViewer_Mathematica *vmath = (PetscViewer_Mathematica*) viewer->data; 621 MLINK link = vmath->link; /* The link to Mathematica */ 622 const char *symbol; 623 char *name; 624 PetscBool match; 625 PetscErrorCode ierr; 626 627 PetscFunctionBegin; 628 /* Determine the object name */ 629 if (!vmath->objName) name = "mat"; 630 else name = (char*) vmath->objName; 631 632 /* Make sure Mathematica recognizes sparse matrices */ 633 MLPutFunction(link, "EvaluatePacket", 1); 634 MLPutFunction(link, "Needs", 1); 635 MLPutString(link, "LinearAlgebra`CSRMatrix`"); 636 MLEndPacket(link); 637 /* Skip packets until ReturnPacket */ 638 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 639 /* Skip ReturnPacket */ 640 MLNewPacket(link); 641 642 /* Send the CSRMatrix object */ 643 MLPutFunction(link, "EvaluatePacket", 1); 644 MLPutFunction(link, "Set", 2); 645 MLPutSymbol(link, name); 646 MLPutFunction(link, "CSRMatrix", 5); 647 MLPutInteger(link, m); 648 MLPutInteger(link, n); 649 MLPutFunction(link, "Plus", 2); 650 MLPutIntegerList(link, i, m+1); 651 MLPutInteger(link, 1); 652 MLPutFunction(link, "Plus", 2); 653 MLPutIntegerList(link, j, i[m]); 654 MLPutInteger(link, 1); 655 MLPutRealList(link, a, i[m]); 656 MLEndPacket(link); 657 /* Skip packets until ReturnPacket */ 658 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 659 /* Skip ReturnPacket */ 660 MLNewPacket(link); 661 662 /* Check that matrix is valid */ 663 MLPutFunction(link, "EvaluatePacket", 1); 664 MLPutFunction(link, "ValidQ", 1); 665 MLPutSymbol(link, name); 666 MLEndPacket(link); 667 ierr = PetscViewerMathematicaSkipPackets(viewer, RETURNPKT);CHKERRQ(ierr); 668 MLGetSymbol(link, &symbol); 669 ierr = PetscStrcmp("True", (char*) symbol, &match);CHKERRQ(ierr); 670 if (!match) { 671 MLDisownSymbol(link, symbol); 672 SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB, "Invalid CSR matrix in Mathematica"); 673 } 674 MLDisownSymbol(link, symbol); 675 /* Skip ReturnPacket */ 676 MLNewPacket(link); 677 PetscFunctionReturn(0); 678 } 679 680