Beispiel #1
0
static void
place_children_rect(struct lstopo_output *loutput, hwloc_obj_t parent,
		    unsigned kind, unsigned border, unsigned separator,
		    unsigned *width, unsigned *height)
{
  unsigned numsubobjs = 0, obj_totwidth = 0, obj_totheight = 0;
  unsigned area = 0;
  unsigned rows, columns;
  unsigned totwidth, totheight; /* total children array size, without borders */
  unsigned rowwidth; /* current row width */
  unsigned maxheight; /* max height for current row */
  int found, i;
  hwloc_obj_t child = NULL;
  int ncstate;

  /* Total area for subobjects */
  while ((child=next_child(loutput, parent, kind, child, &ncstate)) != NULL) {
    struct lstopo_obj_userdata *clud = child->userdata;
    numsubobjs++;
    obj_totwidth += clud->width + separator;
    obj_totheight += clud->height + separator;
    area += (clud->width + separator) * (clud->height + separator);
  }

  /* Try to find a fitting rectangle */
  found = 0;
  for (rows = (unsigned) (float) floor(sqrt(numsubobjs));
       rows >= (unsigned) (float) ceil(pow(numsubobjs, 0.33)) && rows > 1;
       rows--) {
    columns = numsubobjs / rows;
    if (columns > 1 && columns * rows == numsubobjs) {
      found = 1;
      break;
    }
  }

  if (!found) {
    /* Average object size */
    unsigned obj_avgwidth = obj_totwidth / numsubobjs;
    unsigned obj_avgheight = obj_totheight / numsubobjs;
    /* Ideal total height for spreading that area with RATIO */
    float idealtotheight = (float) sqrt(area/RATIO);
    float under_ratio, over_ratio;
    /* approximation of number of rows */
    rows = (unsigned) (idealtotheight / obj_avgheight);
    columns = rows ? (numsubobjs + rows - 1) / rows : 1;
    /* Ratio obtained by underestimation */
    under_ratio = (float) (columns * obj_avgwidth) / (rows * obj_avgheight);
    /* try to overestimate too */
    rows++;
    columns = (numsubobjs + rows - 1) / rows;
    /* Ratio obtained by overestimation */
    over_ratio = (float) (columns * obj_avgwidth) / (rows * obj_avgheight);
    /* Did we actually preferred underestimation? (good row/column fit or good ratio) */
    if (rows > 1 && prefer_ratio(under_ratio, over_ratio)) {
      rows--;
      columns = (numsubobjs + rows - 1) / rows;
    }
  }

  rowwidth = 0;
  maxheight = 0;
  totwidth = 0;
  totheight = 0;
  for(i = 0, child = next_child(loutput, parent, kind, NULL, &ncstate);
      child;
      i++, child = next_child(loutput, parent, kind, child, &ncstate)) {
    struct lstopo_obj_userdata *clud = child->userdata;
    /* Newline? */
    if (i && i%columns == 0) {
      /* Update total width using new row */
      if (rowwidth > totwidth)
	totwidth = rowwidth;
      rowwidth = 0;
      /* Update total height */
      totheight += maxheight + separator;
      maxheight = 0;
    }
    /* Add new child */
    clud->xrel = rowwidth + border;
    clud->yrel = totheight + border;
    rowwidth += clud->width + separator;
    if (clud->height > maxheight)
      maxheight = clud->height;
  }
  /* Update total width using last row */
  if (rowwidth > totwidth)
    totwidth = rowwidth;
  /* Remove spurious separator on the right */
  totwidth -= separator;
  /* Update total height using last row */
  totheight += maxheight; /* no separator */

  *width = totwidth + 2*border;
  *height = totheight + 2*border;
}
Beispiel #2
0
static int
prefer_vert(struct lstopo_output *loutput, hwloc_obj_t level, unsigned depth, unsigned x, unsigned y, unsigned separator)
{
  hwloc_topology_t topology = loutput->topology;
  float horiz_ratio, vert_ratio;
  unsigned textwidth = 0;
  unsigned mywidth = 0, myheight = 0;
  unsigned totwidth, *retwidth = &totwidth, totheight, *retheight = &totheight;
  RECURSE_HORIZ(level, &null_draw_methods, separator, 0);
  horiz_ratio = (float)totwidth / totheight;
  RECURSE_VERT(level, &null_draw_methods, separator, 0);
  vert_ratio = (float)totwidth / totheight;
  return loutput->force_orient[level->type] == LSTOPO_ORIENT_VERT || (loutput->force_orient[level->type] != LSTOPO_ORIENT_HORIZ && prefer_ratio(vert_ratio, horiz_ratio));
}