@Override
  public boolean prepareCreateTemplate(Long pxeServerId, UserVm vm, String templateUrl) {
    List<NicVO> nics = _nicDao.listByVmId(vm.getId());
    if (nics.size() != 1) {
      throw new CloudRuntimeException("Wrong nic number " + nics.size() + " of vm " + vm.getId());
    }

    /* use last host id when VM stopped */
    Long hostId = (vm.getHostId() == null ? vm.getLastHostId() : vm.getHostId());
    HostVO host = _hostDao.findById(hostId);
    DataCenterVO dc = _dcDao.findById(host.getDataCenterId());
    NicVO nic = nics.get(0);
    String mask = nic.getNetmask();
    String mac = nic.getMacAddress();
    String ip = nic.getIp4Address();
    String gateway = nic.getGateway();
    String dns = dc.getDns1();
    if (dns == null) {
      dns = dc.getDns2();
    }

    try {
      prepareCreateTemplateCommand cmd =
          new prepareCreateTemplateCommand(ip, mac, mask, gateway, dns, templateUrl);
      Answer ans = _agentMgr.send(pxeServerId, cmd);
      return ans.getResult();
    } catch (Exception e) {
      s_logger.debug("Prepare for creating baremetal template failed", e);
      return false;
    }
  }
  @DB
  public void work() {
    if (s_logger.isTraceEnabled()) {
      s_logger.trace("Checking the database");
    }
    final SecurityGroupWorkVO work = _workDao.take(_serverId);
    if (work == null) {
      if (s_logger.isTraceEnabled()) {
        s_logger.trace("Security Group work: no work found");
      }
      return;
    }
    Long userVmId = work.getInstanceId();
    if (work.getStep() == Step.Done) {
      if (s_logger.isDebugEnabled()) {
        s_logger.debug(
            "Security Group work: found a job in done state, rescheduling for vm: " + userVmId);
      }
      ArrayList<Long> affectedVms = new ArrayList<Long>();
      affectedVms.add(userVmId);
      scheduleRulesetUpdateToHosts(affectedVms, false, _timeBetweenCleanups * 1000l);
      return;
    }
    UserVm vm = null;
    Long seqnum = null;
    s_logger.debug("Working on " + work);
    final Transaction txn = Transaction.currentTxn();
    txn.start();
    boolean locked = false;
    try {
      vm = _userVMDao.acquireInLockTable(work.getInstanceId());
      if (vm == null) {
        vm = _userVMDao.findById(work.getInstanceId());
        if (vm == null) {
          s_logger.info("VM " + work.getInstanceId() + " is removed");
          locked = true;
          return;
        }
        s_logger.warn("Unable to acquire lock on vm id=" + userVmId);
        return;
      }
      locked = true;
      Long agentId = null;
      VmRulesetLogVO log = _rulesetLogDao.findByVmId(userVmId);
      if (log == null) {
        s_logger.warn("Cannot find log record for vm id=" + userVmId);
        return;
      }
      seqnum = log.getLogsequence();

      if (vm != null && vm.getState() == State.Running) {
        Map<PortAndProto, Set<String>> rules = generateRulesForVM(userVmId);
        agentId = vm.getHostId();
        if (agentId != null) {
          SecurityIngressRulesCmd cmd =
              generateRulesetCmd(
                  vm.getInstanceName(),
                  vm.getPrivateIpAddress(),
                  vm.getPrivateMacAddress(),
                  vm.getId(),
                  generateRulesetSignature(rules),
                  seqnum,
                  rules);
          Commands cmds = new Commands(cmd);
          try {
            _agentMgr.send(agentId, cmds, _answerListener);
          } catch (AgentUnavailableException e) {
            s_logger.debug(
                "Unable to send updates for vm: " + userVmId + "(agentid=" + agentId + ")");
            _workDao.updateStep(work.getInstanceId(), seqnum, Step.Done);
          }
        }
      }
    } finally {
      if (locked) {
        _userVMDao.releaseFromLockTable(userVmId);
        _workDao.updateStep(work.getId(), Step.Done);
      }
      txn.commit();
    }
  }
  @Override
  public List<LbDestination> getExistingDestinations(long lbId) {
    List<LbDestination> dstList = new ArrayList<LbDestination>();
    List<LoadBalancerVMMapVO> lbVmMaps = _lb2VmMapDao.listByLoadBalancerId(lbId);
    LoadBalancerVO lb = _lbDao.findById(lbId);

    String dstIp = null;
    for (LoadBalancerVMMapVO lbVmMap : lbVmMaps) {
      UserVm vm = _vmDao.findById(lbVmMap.getInstanceId());
      Nic nic = _nicDao.findByInstanceIdAndNetworkIdIncludingRemoved(lb.getNetworkId(), vm.getId());
      dstIp = nic.getIp4Address();
      LbDestination lbDst =
          new LbDestination(
              lb.getDefaultPortStart(), lb.getDefaultPortEnd(), dstIp, lbVmMap.isRevoke());
      dstList.add(lbDst);
    }
    return dstList;
  }
  @Override
  @DB
  @ActionEvent(
      eventType = EventTypes.EVENT_ASSIGN_TO_LOAD_BALANCER_RULE,
      eventDescription = "assigning to load balancer",
      async = true)
  public boolean assignToLoadBalancer(long loadBalancerId, List<Long> instanceIds) {
    UserContext ctx = UserContext.current();
    Account caller = ctx.getCaller();

    LoadBalancerVO loadBalancer = _lbDao.findById(loadBalancerId);
    if (loadBalancer == null) {
      throw new InvalidParameterValueException(
          "Failed to assign to load balancer "
              + loadBalancerId
              + ", the load balancer was not found.");
    }

    List<LoadBalancerVMMapVO> mappedInstances =
        _lb2VmMapDao.listByLoadBalancerId(loadBalancerId, false);
    Set<Long> mappedInstanceIds = new HashSet<Long>();
    for (LoadBalancerVMMapVO mappedInstance : mappedInstances) {
      mappedInstanceIds.add(Long.valueOf(mappedInstance.getInstanceId()));
    }

    List<UserVm> vmsToAdd = new ArrayList<UserVm>();

    for (Long instanceId : instanceIds) {
      if (mappedInstanceIds.contains(instanceId)) {
        throw new InvalidParameterValueException(
            "VM " + instanceId + " is already mapped to load balancer.");
      }

      UserVm vm = _vmDao.findById(instanceId);
      if (vm == null || vm.getState() == State.Destroyed || vm.getState() == State.Expunging) {
        throw new InvalidParameterValueException("Invalid instance id: " + instanceId);
      }

      _rulesMgr.checkRuleAndUserVm(loadBalancer, vm, caller);

      if (vm.getAccountId() != loadBalancer.getAccountId()) {
        throw new PermissionDeniedException(
            "Cannot add virtual machines that do not belong to the same owner.");
      }

      // Let's check to make sure the vm has a nic in the same network as the load balancing rule.
      List<? extends Nic> nics = _networkMgr.getNics(vm.getId());
      Nic nicInSameNetwork = null;
      for (Nic nic : nics) {
        if (nic.getNetworkId() == loadBalancer.getNetworkId()) {
          nicInSameNetwork = nic;
          break;
        }
      }

      if (nicInSameNetwork == null) {
        throw new InvalidParameterValueException(
            "VM " + instanceId + " cannot be added because it doesn't belong in the same network.");
      }

      if (s_logger.isDebugEnabled()) {
        s_logger.debug("Adding " + vm + " to the load balancer pool");
      }
      vmsToAdd.add(vm);
    }

    Transaction txn = Transaction.currentTxn();
    txn.start();

    for (UserVm vm : vmsToAdd) {
      LoadBalancerVMMapVO map = new LoadBalancerVMMapVO(loadBalancer.getId(), vm.getId(), false);
      map = _lb2VmMapDao.persist(map);
    }
    txn.commit();

    try {
      loadBalancer.setState(FirewallRule.State.Add);
      _lbDao.persist(loadBalancer);
      applyLoadBalancerConfig(loadBalancerId);
    } catch (ResourceUnavailableException e) {
      s_logger.warn("Unable to apply the load balancer config because resource is unavaliable.", e);
      return false;
    }

    return true;
  }
示例#5
0
  @Override
  public void create() throws ResourceAllocationException {
    try {
      // Verify that all objects exist before passing them to the service
      Account owner = _accountService.getActiveAccountById(getEntityOwnerId());

      DataCenter zone = _configService.getZone(zoneId);
      if (zone == null) {
        throw new InvalidParameterValueException("Unable to find zone by id=" + zoneId);
      }

      ServiceOffering serviceOffering = _configService.getServiceOffering(serviceOfferingId);
      if (serviceOffering == null) {
        throw new InvalidParameterValueException(
            "Unable to find service offering: " + serviceOfferingId);
      }

      VirtualMachineTemplate template = _templateService.getTemplate(templateId);
      // Make sure a valid template ID was specified
      if (template == null) {
        throw new InvalidParameterValueException("Unable to use template " + templateId);
      }

      if (diskOfferingId != null) {
        DiskOffering diskOffering = _configService.getDiskOffering(diskOfferingId);
        if (diskOffering == null) {
          throw new InvalidParameterValueException(
              "Unable to find disk offering " + diskOfferingId);
        }
      }

      UserVm vm = null;
      if (getHypervisor() == HypervisorType.BareMetal) {
        vm = _bareMetalVmService.createVirtualMachine(this);
      } else {
        if (zone.getNetworkType() == NetworkType.Basic) {
          if (getNetworkIds() != null) {
            throw new InvalidParameterValueException("Can't specify network Ids in Basic zone");
          } else {
            vm =
                _userVmService.createBasicSecurityGroupVirtualMachine(
                    zone,
                    serviceOffering,
                    template,
                    getSecurityGroupIdList(),
                    owner,
                    name,
                    displayName,
                    diskOfferingId,
                    size,
                    group,
                    getHypervisor(),
                    userData,
                    sshKeyPairName,
                    getIpToNetworkMap(),
                    ipAddress,
                    keyboard);
          }
        } else {
          if (zone.isSecurityGroupEnabled()) {
            vm =
                _userVmService.createAdvancedSecurityGroupVirtualMachine(
                    zone,
                    serviceOffering,
                    template,
                    getNetworkIds(),
                    getSecurityGroupIdList(),
                    owner,
                    name,
                    displayName,
                    diskOfferingId,
                    size,
                    group,
                    getHypervisor(),
                    userData,
                    sshKeyPairName,
                    getIpToNetworkMap(),
                    ipAddress,
                    keyboard);
          } else {
            if (getSecurityGroupIdList() != null && !getSecurityGroupIdList().isEmpty()) {
              throw new InvalidParameterValueException(
                  "Can't create vm with security groups; security group feature is not enabled per zone");
            }
            vm =
                _userVmService.createAdvancedVirtualMachine(
                    zone,
                    serviceOffering,
                    template,
                    getNetworkIds(),
                    owner,
                    name,
                    displayName,
                    diskOfferingId,
                    size,
                    group,
                    getHypervisor(),
                    userData,
                    sshKeyPairName,
                    getIpToNetworkMap(),
                    ipAddress,
                    keyboard);
          }
        }
      }

      if (vm != null) {
        setEntityId(vm.getId());
      } else {
        throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to deploy vm");
      }
    } catch (InsufficientCapacityException ex) {
      s_logger.info(ex);
      s_logger.trace(ex);
      throw new ServerApiException(BaseCmd.INSUFFICIENT_CAPACITY_ERROR, ex.getMessage());
    } catch (ResourceUnavailableException ex) {
      s_logger.warn("Exception: ", ex);
      throw new ServerApiException(BaseCmd.RESOURCE_UNAVAILABLE_ERROR, ex.getMessage());
    } catch (ConcurrentOperationException ex) {
      s_logger.warn("Exception: ", ex);
      throw new ServerApiException(BaseCmd.INTERNAL_ERROR, ex.getMessage());
    }
  }