Cloudsim 3.0.3中任务到VM的映射

来源:互联网 发布:超星网络教学平台 编辑:程序博客网 时间:2024/06/01 09:17

本文准备介绍Cloudsim中云任务(Cloudlet)到虚拟机(Vm)的映射的实现方法,为相关扩展实验和二次开发提供启发。


先说两个CloudSim机制上的发现:

1、真实云环境(如IaaS)中,VM和主机是密不可分的,没有host怎么创建VM呢?而且VM的资源(尤其是处理器性能)与主机应该是绑定关系,例如2核的VM在host-A上是2*2.5Ghz,在host-B上可能就是2*3Ghz。但是,在Cloudsim中,VM更加像非常独立的实体,它在实例化时就有确定的内存大小、带宽以及MIPS。

2、真实云环境的VM在空闲时,仅占用少量资源(某些时候可以选择忽略)。但是根据我的实验发现,在CloudSim中,VM一旦submit并分配给某个host,这个host的资源会被立刻占用,即使VM上根本没有Cloudlet运行。比如没有运行任务Cloudlet的VM1分配给host-A,host-A的可用MIPS就减少了2*2.5=5Ghz。


现在回到正题,CloudSim中Cloudlet->VM的映射是由DataCenterBroker对象完成的,DCBroker首先提供了最直接的方法:

public void bindCloudletToVm(int cloudletId, int vmId) {
CloudletList.getById(getCloudletList(), cloudletId).setVmId(vmId);
}

该方法将ID为cloudletId的任务指定分配给ID为vmId的虚拟机(就是调用Cloudlet对象.setVmId(vmId))。该方法需要编程者主动调用,比如example2中就在main方法中主动调用bindCloudletToVm来绑定已提交的两对Cloudlet和Vm(这个提交就是填充列表而已,各种绑定操作是在CloudSim.startSimulation()之后才进行)


同时,DCBroker还提供了自带的Cloudlet列表->VM列表的绑定逻辑,用于将剩下的Cloudlet绑定到VM上(编程者未绑定的那些),该实现在protected void submitCloudlets()方法中:

protected void submitCloudlets(){

  int vmIndex = 0;
  for (Cloudlet cloudlet : getCloudletList()) {
Vm vm;
// if user didn't bind this cloudlet and it has not been executed yet
if (cloudlet.getVmId() == -1) {
vm = getVmsCreatedList().get(vmIndex);
} else { // submit to the specific vm
vm = VmList.getById(getVmsCreatedList(), cloudlet.getVmId());

......

}

......

vmIndex = (vmIndex + 1) % getVmsCreatedList().size();

  }// end for

}

可以看出,该方法主要逻辑是检查列表中每个Cloudlet是否已经有主,如果没有,则使用轮转法完成分配。


所以,如果想实现自定义任务绑定,可以自行编写CloudletList->VmList的映射函数,以某种方式完成任务列表中的所有Cloudlet的绑定工作。然后在模拟程序中,vm列表和cloudlet列表提交之后调用该自定义函数,即可完成所有任务的绑定(这样自然就不需要自带的轮转法代劳了)。

下面我采用一种改进型轮转法来绑定任务,长任务尽量优先分配到高性能VM上。

import java.util.Collections;

import java.util.Comparator 

public void bindCloudletsToVmsRRImproved() 

int vmNum=vmList.size(); 
int cloudletNum=cloudletList.size(); 

// 任务按指令长度降序,Vm按性能降序,需要导入包 java.util.Collections 

Collections.sort(cloudletList, new CloudletComparator()); 
  Collections.sort(vmList, new VmComparator());

int idx=0; 

for(int i=0;i<cloudletNum;i++) {

 //将任务绑定到指定 id 的虚拟机,按Round-Robin轮转法 

 bindCloudletToVm(vmList.get(idx).getId(), cloudletList.get(i).getCloudletId()) 
 idx=(idx+1)%vmNum; //循环遍历虚拟机 

}

//根据指令长度降序排列任务,需要导入包 java.util.Comparator 
private class CloudletComparator implements Comparator<Cloudlet>{ 
public int compare(Cloudlet cl1,Cloudlet cl2){ 
return (int)(c12.getCloudletLength()-cl1. getCloudletLength()); 


 
//根据执行速度降序排列虚拟机 
private class VmComparator implements Comparator<Vm>{ 
 @Override 
 public int compare(Vm vm1, Vm vm2) { 
 return (int) (vm2.getMips() - vm1.getMips()); 
 } 

阅读全文
1 0
原创粉丝点击