Mercurial > illumos > illumos-gate
changeset 3317:e378dabfd171
6503812 poold not rebalancing very well
author | garypen |
---|---|
date | Fri, 22 Dec 2006 00:49:41 -0800 |
parents | cacdd08716df |
children | fcaac7018af6 |
files | usr/src/cmd/pools/poold/com/sun/solaris/domain/pools/Objective.java |
diffstat | 1 files changed, 62 insertions(+), 61 deletions(-) [+] |
line wrap: on
line diff
--- a/usr/src/cmd/pools/poold/com/sun/solaris/domain/pools/Objective.java Thu Dec 21 20:43:10 2006 -0800 +++ b/usr/src/cmd/pools/poold/com/sun/solaris/domain/pools/Objective.java Fri Dec 22 00:49:41 2006 -0800 @@ -2,9 +2,8 @@ * CDDL HEADER START * * The contents of this file are subject to the terms of the - * Common Development and Distribution License, Version 1.0 only - * (the "License"). You may not use this file except in compliance - * with the License. + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. @@ -19,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2004 Sun Microsystems, Inc. All rights reserved. + * Copyright 2006 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. * * ident "%Z%%M% %I% %E% SMI" @@ -153,7 +153,7 @@ public void setExpression(Expression exp) { this.exp = exp; - } + } /** * Get the objective's expression. @@ -162,7 +162,7 @@ { return (exp); } - + /** * A factory method which returns a created objective which is * associated with the supplied expression. The type and the @@ -325,9 +325,9 @@ static final String name = "wt-load"; /** - * The list of calculations made during examination. + * The map of calculations made during examination. */ - List calcList; + Map calcMap; /** * Determine whether an objective is satisfied. If the @@ -356,7 +356,7 @@ Monitor mon = solver.getMonitor(); Value val = new Value("type", "pset"); List valueList = new LinkedList(); - calcList = new LinkedList(); + calcMap = new HashMap(); valueList.add(val); List resList = conf.getResources(valueList); @@ -372,10 +372,10 @@ try { Calculation calc = new Calculation(res, CPUs, - mon.getUtilization(res), - res.getLongProperty("pset.min"), - res.getLongProperty("pset.max")); - calcList.add(calc); + mon.getUtilization(res), + res.getLongProperty("pset.min"), + res.getLongProperty("pset.max")); + calcMap.put(res, calc); } catch (StaleMonitorException sme) { Poold.MON_LOG.log(Severity.INFO, res.toString() + @@ -384,10 +384,11 @@ "available statistics."); } } - Iterator itCalc = calcList.iterator(); + Iterator itCalc = calcMap.values().iterator(); while (itCalc.hasNext()) { Calculation calc = (Calculation) itCalc.next(); - if (calc.getShare() != calc.comp.size()) { + if (calc.getShare() != calc.comp.size() && + calc.getShare() >= calc.min) { Poold.MON_LOG.log(Severity.INFO, elem.toString() + " utilization objective not satisfied " + @@ -454,17 +455,13 @@ * @param max The maximum qty of resource for this set */ public Calculation(Resource res, List comp, double util, - long min, long max) + long min, long max) { this.res = res; this.comp = comp; this.min = min; this.max = max; this.util = (util / 100) * comp.size(); - if (this.util < min) - this.util = min; - if (this.util > max) - this.util = max; Calculation.totalUtil += this.util; Calculation.resQ += comp.size(); } @@ -475,8 +472,8 @@ */ long getShare() { - if (totalUtil == 0) - return (min); + if (util == 0) + return (0); return (Math.round((util / totalUtil) * resQ)); } @@ -494,14 +491,14 @@ return (buf.toString()); } } - + /** * Calculates the value of a configuration in terms of this * objective. * * In the examination step, calculations of each resource's * current and desired share were made. The moves can thus be - * assessed in terms of their desired impact upon the desired + * assessed in terms of their impact upon the desired * share. The current difference from desired is already * known, so each move will serve to reduce or increase that * difference. Moves that increase the difference have a @@ -518,6 +515,7 @@ throws PoolsException { double ret = 0; + Poold.OPT_LOG.log(Severity.DEBUG, "Calculating objective type: " + name); /* @@ -526,38 +524,42 @@ */ if (move.getQty() == 0) return (0); - Iterator itCalc = calcList.iterator(); - while (itCalc.hasNext()) { - Calculation calc = (Calculation) itCalc.next(); - long diff = calc.comp.size() - calc.getShare(); - if (Math.abs(diff) > 1) { - double delta = 1 - - (move.getQty() / (double)Math.abs(diff)); + /* + * Find the calculations that represent the source and + * target of the move. + */ + Calculation src = (Calculation) calcMap.get(move.getFrom()); + Calculation tgt = (Calculation) calcMap.get(move.getTo()); - if (calc.res.equals(move.getFrom())) { - if (diff > 0) - ret += delta; - else - ret -= delta; - } else if (calc.res.equals(move.getTo())) { - if (diff > 0) - ret -= delta; - else - ret += delta; - } - } else { - if (calc.res.equals(move.getFrom())) - ret += diff; - else if (calc.res.equals(move.getTo())) - ret -= diff; - } - - } /* - * Normalize + * Use the calculation details to determine the "gap" + * i.e. number of discrete resources (for a processor + * set these are CPUs), between the desired quantity in + * the set which the calculations represent. Do this + * both before and after the proposed move. + * + * The maximum possible improvement is equal to the + * total number of resources for each set participating + * in the calculation. Since there are two sets we + * know the maximum possible improvement is resQ * 2. + * + * Divide the aggregated change in gap across participating + * sets by the maximum possible improvement to obtain + * a value which scores the move and which is normalised + * between -1 <= ret <= 1. */ - ret /= 2; + long oldGap = Math.abs(src.getShare() - + src.comp.size()); + long newGap = Math.abs(src.getShare() - + (src.comp.size() - move.getQty())); + ret = oldGap - newGap; + oldGap = Math.abs(tgt.getShare() - + tgt.comp.size()); + newGap = Math.abs(tgt.getShare() - + (tgt.comp.size() + move.getQty())); + ret += oldGap - newGap; + ret /= ((double) Calculation.resQ * 2); Poold.MON_LOG.log(Severity.DEBUG, "ret: " + ret); return (ret); @@ -609,7 +611,7 @@ { this.ldom = ldom; } - + /** * Calculates the value of a configuration in terms of this * objective. @@ -676,7 +678,7 @@ if (elem.equals(move.getFrom())) contains.removeAll(cm.getComponents()); - else + else contains.addAll(cm.getComponents()); /* * Recalculate lgrps to take account of new components @@ -705,7 +707,7 @@ * * @throws PoolsException if there is an error accessing the * CPUs. - */ + */ private double calcQ(List contains, Set groups) throws PoolsException { Iterator groupIt = groups.iterator(); @@ -735,7 +737,7 @@ } q /= groups.size(); return (q); - } + } } /** @@ -843,7 +845,7 @@ (zone & StatisticOperations.ZONET) == StatisticOperations.ZONELT) return (false); - + if (kve.getOp() == KVOpExpression.GT && (zone & StatisticOperations.ZONET) == StatisticOperations.ZONEGT) @@ -861,7 +863,7 @@ checkShort(mon, elem, val); return (false); } - + /** * Calculates the value of a configuration in terms of this * objective. @@ -907,7 +909,7 @@ try { double val, gap; StatisticList sl; - + if (elem.equals(move.getFrom())) { val = gapSolver.getMonitor(). getUtilization(move.getFrom()); @@ -1001,7 +1003,7 @@ boolean checkOne = true; int checkOnePos = 0; boolean doCheckOne = false; - + Iterator itZones = zoneList.iterator(); while (itZones.hasNext()) { int zone = ((Integer) itZones.next()).intValue(); @@ -1030,5 +1032,4 @@ zoneList.clear(); } } - }