On Fri, Feb 10, 2012 at 7:45 PM, Jed Brown <span dir="ltr"><<a href="mailto:jedbrown@mcs.anl.gov">jedbrown@mcs.anl.gov</a>></span> wrote:<br><div class="gmail_quote"><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">

<div class="gmail_quote"><div class="im">On Fri, Feb 10, 2012 at 19:33, Dmitry Karpeev <span dir="ltr"><<a href="mailto:karpeev@mcs.anl.gov" target="_blank">karpeev@mcs.anl.gov</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">


<div>How can there be a single callback, when the two DMs could be of different types?</div><div>I guess it could be done using the double-dispatch mechanism: </div>

<div>DMComputeOperators(DM dmJ, DM dmP, Mat *J, Mat *P) would dispatch based on the types of the two DMs, </div><div>and, if no such method exists, defaulting internally to calling</div><div>DMComputeMatrix(DM dm, Mat *A) for both J and P.</div>


</blockquote><div><br></div></div><div>Or call the user's function which just assembles into the P matrix.</div><div class="im"><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">




<div>I still think that DMComputeMatrix() should be different from DMCreateMatrix() -- the latter just preallocates --</div><div>eliminating the need for DMSetPreallocateOnly().</div></blockquote><div><br></div></div><div>

How many times do we have to explain that DMCreateMatrix() *NEVER* fills in useful values? It has two capabilities: preallocate (just specify number of nonzeros per row) and also setting the column indices. It does both by default because that is better for performance profiling and better to catch setting values outside of the allocated sparsity pattern at the first incident instead of whenever a row overflows. Under no circumstances does it assemble physics and under no circumstances does DMComputeJacobian() allocate a matrix.</div>

</div></blockquote><div><br></div><div>How does this explanation square with the following code from KSPSetUp?</div><div><br></div><div> if (ksp->dmActive && !ksp->setupstage) {</div><div>    /* first time in so build matrix and vector data structures using DM */</div>

<div>    if (!ksp->vec_rhs) {ierr = DMCreateGlobalVector(ksp->dm,&ksp->vec_rhs);CHKERRQ(ierr);}</div><div>    if (!ksp->vec_sol) {ierr = DMCreateGlobalVector(ksp->dm,&ksp->vec_sol);CHKERRQ(ierr);}</div>

<div>    ierr = DMCreateMatrix(ksp->dm,MATAIJ,&A);CHKERRQ(ierr);</div><div>    ierr = KSPSetOperators(ksp,A,A,stflg);CHKERRQ(ierr);  </div><div>    ierr = PetscObjectDereference((PetscObject)A);CHKERRQ(ierr); </div>

<div> }</div><div><br></div><div>Dmitry.</div><div><br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div class="gmail_quote"><div class="im">
<div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div><br></div><div>If the two DMs are of the same type and, say, share a mesh, then the dual dispatch can take advantage of</div>




<div>a corresponding implementation.</div></blockquote></div></div><br><div>The user should always be able to get the callback to do both.</div>
</blockquote></div><br>