int
SCOTCH_dgraphOrderGather (
const SCOTCH_Dgraph * const     grafptr,          /*+ Not used             +*/
const SCOTCH_Dordering * const  dordptr,          /*+ Distributed ordering +*/
SCOTCH_Ordering * const         cordptr)          /*+ Centralized ordering +*/
{
  LibOrder *          libcordptr;                 /* Pointer to ordering */

  if ((cordptr != NULL) && ((void *) cordptr != (void *) dordptr)) { /* If potential root process */
    libcordptr = (LibOrder *) cordptr;            /* Get centralized ordering                     */

    if (dorderGather ((Dorder *) dordptr, &libcordptr->o) != 0)
      return (1);

    if (libcordptr->permtab != NULL)              /* Build direct permutation if wanted */
      orderPeri (libcordptr->o.peritab, libcordptr->o.baseval, libcordptr->o.vnodnbr, libcordptr->permtab, libcordptr->o.baseval);
    if (libcordptr->rangtab != NULL)              /* Build range array if column block data wanted */
      orderRang (&libcordptr->o, libcordptr->rangtab);
    if (libcordptr->treetab != NULL)              /* Build separator tree array if wanted */
      orderTree (&libcordptr->o, libcordptr->treetab);
    if (libcordptr->cblkptr != NULL)              /* Set number of column blocks if wanted */
      *(libcordptr->cblkptr) = libcordptr->o.cblknbr;

    return (0);
  }
  else
    return (dorderGather ((Dorder *) dordptr, NULL));
}
int
SCOTCH_meshOrderComputeList (
SCOTCH_Mesh * const         meshptr,              /*+ Mesh to order                   +*/
SCOTCH_Ordering * const     ordeptr,              /*+ Ordering to compute             +*/
const SCOTCH_Num            listnbr,              /*+ Number of vertices in list      +*/
const SCOTCH_Num * const    listtab,              /*+ List of vertex indices to order +*/
SCOTCH_Strat * const        stratptr)             /*+ Ordering strategy               +*/
{
  LibOrder *          libordeptr;                 /* Pointer to ordering             */
  Mesh *              srcmeshptr;                 /* Pointer to source mesh          */
  Hmesh               srcmeshdat;                 /* Halo source mesh structure      */
  VertList            srclistdat;                 /* Subgraph vertex list            */
  VertList *          srclistptr;                 /* Pointer to subgraph vertex list */
  const Strat *       ordstratptr;                /* Pointer to ordering strategy    */

  srcmeshptr = (Mesh *) meshptr;

#ifdef SCOTCH_DEBUG_MESH2
  if (meshCheck (srcmeshptr) != 0) {
    errorPrint ("SCOTCH_meshOrderComputeList: invalid input mesh");
    return     (1);
  }
#endif /* SCOTCH_DEBUG_MESH2 */

  if (*((Strat **) stratptr) == NULL)             /* Set default ordering strategy if necessary */
    SCOTCH_stratMeshOrderBuild (stratptr, SCOTCH_STRATQUALITY, 0.1);

  ordstratptr = *((Strat **) stratptr);
  if (ordstratptr->tabl != &hmeshorderststratab) {
    errorPrint ("SCOTCH_meshOrderComputeList: not a mesh ordering strategy");
    return     (1);
  }

  memCpy (&srcmeshdat.m, srcmeshptr, sizeof (Mesh)); /* Copy non-halo mesh data  */
  srcmeshdat.m.flagval &= ~MESHFREETABS;          /* Do not allow to free arrays */
  srcmeshdat.vehdtax    = srcmeshdat.m.vendtax;   /* End of non-halo vertices    */
  srcmeshdat.veihnbr    = 0;                      /* No halo isolated elements   */
  srcmeshdat.vnohnbr    = srcmeshdat.m.vnodnbr;   /* All nodes are non-halo      */
  srcmeshdat.vnohnnd    = srcmeshdat.m.vnodnnd;   /* No halo present             */
  srcmeshdat.vnhlsum    = srcmeshdat.m.vnlosum;   /* Sum of node vertex weights  */
  srcmeshdat.enohnbr    = srcmeshdat.m.edgenbr;   /* All edges are non-halo      */
  srcmeshdat.levlnum    = 0;                      /* Start from level zero       */

  libordeptr         = (LibOrder *) ordeptr;      /* Get ordering      */
  srclistdat.vnumnbr = (Gnum)   listnbr;          /* Build vertex list */
  srclistdat.vnumtab = (Gnum *) listtab;
  srclistptr = ((srclistdat.vnumnbr == 0) ||
                (srclistdat.vnumnbr == srcmeshdat.m.vnodnbr))
               ? NULL : &srclistdat;              /* Is the list really necessary */
  if (srclistptr != NULL) {
    errorPrint ("SCOTCH_meshOrderComputeList: node lists not yet implemented");
    return     (1);
  }

  hmeshOrderSt (&srcmeshdat, &libordeptr->o, 0, &libordeptr->o.cblktre, ordstratptr);

#ifdef SCOTCH_DEBUG_LIBRARY2
  orderCheck (&libordeptr->o);
#endif /* SCOTCH_DEBUG_LIBRARY2 */

  if (libordeptr->permtab != NULL)                 /* Build direct permutation if wanted */
    orderPeri (libordeptr->o.peritab, libordeptr->o.baseval, libordeptr->o.vnodnbr, libordeptr->permtab, libordeptr->o.baseval);
  if (libordeptr->rangtab != NULL)                /* Build range array if column block data wanted */
    orderRang (&libordeptr->o, libordeptr->rangtab);
  if (libordeptr->treetab != NULL)                /* Build separator tree array if wanted */
      orderTree (&libordeptr->o, libordeptr->treetab);
  if (libordeptr->cblkptr != NULL)                /* Set number of column blocks if wanted */
    *(libordeptr->cblkptr) = libordeptr->o.cblknbr;

  meshExit (&srcmeshdat.m);                       /* Free in case mesh had been reordered */

  return (0);
}