Do we really want mallocs for EVERY single multiple-dispatch function call in 
PETSc? I suggest not having MatQueryOp() but calling directly 
PetscOpFListFind() (with the MatOpFList argument) and changing 
PetscOpFListAdd/Find() to use variable args directly.

   Finally do we really want string comparisons at all here? Or do we want 
XXXRegister() (for example, MatRegister()) to compute an integer type id to go 
with each char *type_name and do the search off the integer type id instead of 
strings? Thus making PetscOpFListFind() super light weight?

   Barry


PetscErrorCode  MatQueryOp(MPI_Comm comm, PetscVoidFunction* function, const 
char op[], PetscInt numArgs, ...) 
{
  PetscErrorCode ierr;
  va_list        ap;
  PetscInt       i;
  const char     *argType;
  char           **argTypes = PETSC_NULL;

  PetscFunctionBegin;
  va_start(ap,numArgs);
  if (numArgs) {
    ierr = PetscMalloc(sizeof(char*)*numArgs, &argTypes);CHKERRQ(ierr);
  }
  for (i = 0; i < numArgs; ++i) {
    argType = va_arg(ap,const char*);
    ierr = PetscStrallocpy(argType, argTypes+i);CHKERRQ(ierr);
  }
  va_end(ap);
  ierr = PetscOpFListFind(comm, MatOpList, function, op, numArgs, 
argTypes);CHKERRQ(ierr);
  for (i = 0; i < numArgs; ++i) {
    ierr = PetscFree(argTypes[i]);CHKERRQ(ierr);
  }
  ierr = PetscFree(argTypes);CHKERRQ(ierr);
  PetscFunctionReturn(0);
}

Reply via email to