分配下一个可用VM的有效方法

sap*_*Pro 14 java cloud allocation

该方法getNextAvailableVm()以循环方式为特定数据中心分配虚拟机.(此方法返回的整数是分配的机器)

在数据中心中,可能存在具有不同配置集的虚拟机.例如 :

5 VMs with 1024 memory
4 VMs with 512 memory

Total : 9 VMs
Run Code Online (Sandbox Code Playgroud)

对于这个数据中心,与具有512内存的机器相比,具有1024内存的机器将获得任务2次.

因此,此数据中心的计算机将通过getNextAvailableVm()以下方式返回:

0 0 1 1 2 2 3 3 4 4 5 6 7 8
Run Code Online (Sandbox Code Playgroud)

这是当前的方式,机器正在返回.但是有一个问题.

可能存在这样的情况:当一台特定的机器繁忙且无法分配任务时.相反,下一台具有最高内存的机器必须分配任务.我无法实现这一点.

例如 :

0 (allotted first time)
0 (to be allotted the second time)
but if 0 is busy..
allot 1 if 1 is not busy
next circle check if 0 is busy
if not busy allot 0  (only when machine numbered 0 has not handled the requests it is entitled to handle)
if busy, allot the next
Run Code Online (Sandbox Code Playgroud)

cloudSimEventFired 当机器被释放或分配时,将调用以下类中的方法.

    public class TempAlgo extends VmLoadBalancer implements CloudSimEventListener {

    /**
     * Key : Name of the data center
     * Value : List of objects of class 'VmAllocationUIElement'.
     */
    private  Map<String,LinkedList<DepConfAttr>> confMap = new HashMap<String,LinkedList<DepConfAttr>>();
    private Iterator<Integer> availableVms = null;
    private DatacenterController dcc;
    private boolean sorted = false;
    private int currentVM;
    private boolean calledOnce = false;
    private boolean indexChanged = false;
    private LinkedList<Integer> busyList = new LinkedList<Integer>();

    private Map<String,LinkedList<AlgoAttr>> algoMap = new HashMap<String, LinkedList<AlgoAttr>>();
    private Map<String,AlgoHelper> map = new HashMap<String,AlgoHelper>();  
    private Map<String,Integer> vmCountMap = new HashMap<String,Integer>();

    public TempAlgo(DatacenterController dcb) {
        confMap = DepConfList.dcConfMap;
        this.dcc = dcb;
        dcc.addCloudSimEventListener(this);
        if(!this.calledOnce) {
            this.calledOnce = true;
            // Make a new map using dcConfMap that lists 'DataCenter' as a 'key' and 'LinkedList<AlgoAttr>' as 'value'.
            Set<String> keyst =DepConfList.dcConfMap.keySet();
            for(String dataCenter : keyst) {
                LinkedList<AlgoAttr> tmpList = new LinkedList<AlgoAttr>();
                LinkedList<DepConfAttr> list = dcConfMap.get(dataCenter);
                int totalVms = 0;
                for(DepConfAttr o : list) {
                    tmpList.add(new AlgoAttr(o.getVmCount(), o.getMemory()/512, 0));
                    totalVms = totalVms + o.getVmCount();
                }
                Temp_Algo_Static_Var.algoMap.put(dataCenter, tmpList);
                Temp_Algo_Static_Var.vmCountMap.put(dataCenter, totalVms);
            }
            this.algoMap = new HashMap<String, LinkedList<AlgoAttr>>(Temp_Algo_Static_Var.algoMap);
            this.vmCountMap = new HashMap<String,Integer>(Temp_Algo_Static_Var.vmCountMap);
            this.map = new HashMap<String,AlgoHelper>(Temp_Algo_Static_Var.map);
        }
    }

    @Override
    public int getNextAvailableVm() {
        synchronized(this) {
            String dataCenter = this.dcc.getDataCenterName();
            int totalVMs = this.vmCountMap.get(dataCenter);
            AlgoHelper ah = (AlgoHelper)this.map.get(dataCenter);
            int lastIndex = ah.getIndex();
            int lastCount = ah.getLastCount();
            LinkedList<AlgoAttr> list = this.algoMap.get(dataCenter);
            AlgoAttr aAtr = (AlgoAttr)list.get(lastIndex);
            indexChanged = false;
            if(lastCount < totalVMs)  {
                if(aAtr.getRequestAllocated() % aAtr.getWeightCount() == 0) {
                    lastCount = lastCount + 1;
                    this.currentVM = lastCount;
                    if(aAtr.getRequestAllocated() == aAtr.getVmCount() * aAtr.getWeightCount()) {
                        lastIndex++;
                        if(lastIndex != list.size()) {
                            AlgoAttr aAtr_N = (AlgoAttr)list.get(lastIndex);
                            aAtr_N.setRequestAllocated(1);
                            this.indexChanged = true;
                        }
                        if(lastIndex == list.size()) {
                            lastIndex = 0;
                            lastCount = 0;
                            this.currentVM = lastCount;
                            AlgoAttr aAtr_N = (AlgoAttr)list.get(lastIndex);
                            aAtr_N.setRequestAllocated(1);
                            this.indexChanged = true;

                        }
                    }
                }
                if(!this.indexChanged) {
                    aAtr.setRequestAllocated(aAtr.getRequestAllocated() + 1);
                }

                this.map.put(dataCenter, new AlgoHelper(lastIndex, lastCount)); 

                //System.out.println("Current VM : " + this.currentVM + " for data center : " + dataCenter);
                return this.currentVM;
            }}

            System.out.println("--------Before final return statement---------");
            return 0;

    }   

    @Override
    public void cloudSimEventFired(CloudSimEvent e) {
        if(e.getId() == CloudSimEvents.EVENT_CLOUDLET_ALLOCATED_TO_VM) {
            int vmId = (Integer) e.getParameter(Constants.PARAM_VM_ID);
                    busyList.add(vmId);

            System.out.println("+++++++++++++++++++Machine with vmID : " + vmId + " attached");
        }else if(e.getId() == CloudSimEvents.EVENT_VM_FINISHED_CLOUDLET) {
            int vmId = (Integer) e.getParameter(Constants.PARAM_VM_ID);
                            busyList.remove(vmId);
            //System.out.println("+++++++++++++++++++Machine with vmID : " + vmId + " freed");
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

在上面的代码中,所有列表都已经按照最高内存排序.整个想法是通过将更多任务分配给具有更高内存的机器来平衡内存.

每一个机分配分配请求由one.Each组机器递增时间的重计数附加到它,这是通过将计算出的memory_allotted512.

该方法getNextAvailableVm()一次由多个线程调用.对于3个数据中心,3个线程将同时调用getNextAva...()但在不同的类对象上.由this.dcc.getDataCenterName()同一方法中的语句返回的数据中心将根据之前选择的数据中心代理策略返回.

如何确保我当前正在返回的机器是免费的,如果机器不是空闲的,我将分配下一台机器具有最高可用内存.我还必须确保有权处理X任务的机器处理X任务即使那台机器目前很忙.

这是此处使用的数据结构的一般描述:

在此输入图像描述

这个类的代码在github上托管.

这是github上完整项目的链接.

这里使用的大多数数据结构/类都在这个包中

Pet*_*rey 1

也许你对这个问题想得太多了。一个简单的策略是让代理了解所有待处理的任务。每个任务工作人员或线程都向代理请求要处理的新消息/任务。经纪人按照要求的顺序发出工作。这就是 JMS 队列的工作原理。对于可以处理两个任务的 JVM,您可以启动两个线程。

有许多标准 JMS 可以执行此操作,但我建议查看 ActiveMQ,因为它很容易上手。

请注意,在您的情况下,更简单的解决方案是拥有一台具有 8 GB 内存的计算机。您可以花很少的钱(40 - 150 美元,具体取决于供应商)购买 8 GB 的服务器,并且通过共享资源在一个实例中可以更有效地使用它。我假设您正在寻找更大的实例。小于 8 GB 的实例最好直接升级。

如何确保我当前退回的机器是免费的

这是你的场景,如果你不知道如何判断机器是否空闲,我不认为任何人会对你的应用程序有更多的了解。

如果机器不空闲,我会分配下一台具有最高可用内存的机器。

您需要查看空闲机器并选择可用内存最多的机器。除了按照你所说的去做之外,我不明白这里有什么问题。

我还必须确保有权处理 X 个任务的机器确实处理 X 个任务,即使该机器当前很忙。

您需要一个数据源或存储来存储此信息。允许什么在哪里运行。在 JMS 中,您将拥有多个队列,并且仅将某些队列传递给可以处理这些队列的机器。