[libvirt] [PATCH 1/3] vz: support boot order specification on define domain

Maxim Nestratov mnestratov at virtuozzo.com
Thu Apr 7 09:47:37 UTC 2016


22.03.2016 16:56, Nikolay Shirokovskiy пишет:
> The patch makes some refactoring of the existing code. Current boot order spec code
> makes very simple thing in somewhat obscure way. In case of VMs
> it sets the first hdd as the only bootable device. In case of CTs it
> doesn't touch the boot order at all if one of the filesystems is mounted to root.
> Otherwise like in case of VMs it sets the first hdd as the only bootable
> device and additionally sets this device mount point to root. Refactored
> code makes all this explicit.
>
> The actual boot order support is simple. Common libvirt domain xml parsing
> code makes the exact ordering of disks devices as described in docs
> for boot ordering (disks are sorted by bus order first, device target
> second. Bus order is the order of disk buses appearence in original
> xml. Device targets order is alphabetical). We add devices in the
> same order and SDK designates device indexes sequentially for each
> device type. Thus device index is equal to its boot index. For
> example N-th cdrom in boot specification refers to sdk cdrom with
> it's device index N.
>
> If there is no boot spec in xml the parsing code will add <boot dev='hdd'>
> for HVMs automatically and we backward compatibly set fist hdd as
> bootable.
>
> Signed-off-by: Nikolay Shirokovskiy <nshirokovskiy at virtuozzo.com>
> ---
>   src/vz/vz_sdk.c | 148 ++++++++++++++++++++++++++++++++++++++------------------
>   1 file changed, 101 insertions(+), 47 deletions(-)
>
> diff --git a/src/vz/vz_sdk.c b/src/vz/vz_sdk.c
> index c0fb4fb..528a253 100644
> --- a/src/vz/vz_sdk.c
> +++ b/src/vz/vz_sdk.c
> @@ -87,6 +87,14 @@ logPrlErrorHelper(PRL_RESULT err, const char *filename,
>           }                                          \
>       } while (0)
>   
> +#define prlsdkCheckRetExit(ret, code)              \
> +    do {                                           \
> +        if (PRL_FAILED(ret)) {                     \
> +            logPrlError(ret);                      \
> +            return code;                           \
> +        }                                          \
> +    } while (0)
> +
>   static PRL_RESULT
>   logPrlEventErrorHelper(PRL_HANDLE event, const char *filename,
>                          const char *funcname, size_t linenr)
> @@ -1988,13 +1996,9 @@ prlsdkCheckUnsupportedParams(PRL_HANDLE sdkdom, virDomainDefPtr def)
>       }
>   
>       if (!IS_CT(def)) {
> -        if (def->os.nBootDevs != 1 ||
> -            def->os.bootDevs[0] != VIR_DOMAIN_BOOT_DISK ||
> -            def->os.init != NULL || def->os.initargv != NULL) {
> -
> +        if (def->os.init != NULL || def->os.initargv != NULL) {
>               virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
> -                           _("changing OS parameters is not supported "
> -                             "by vz driver"));
> +                           _("unsupported OS parameters"));
>               return -1;
>           }
>       } else {
> @@ -2003,8 +2007,7 @@ prlsdkCheckUnsupportedParams(PRL_HANDLE sdkdom, virDomainDefPtr def)
>               (def->os.initargv != NULL && def->os.initargv[0] != NULL)) {
>   
>               virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
> -                           _("changing OS parameters is not supported "
> -                             "by vz driver"));
> +                           _("unsupported OS parameters"));
>               return -1;
>           }
>       }
> @@ -2991,9 +2994,7 @@ static int prlsdkDelDisk(PRL_HANDLE sdkdom, int idx)
>   
>   static int prlsdkAddDisk(vzConnPtr privconn,
>                            PRL_HANDLE sdkdom,
> -                         virDomainDiskDefPtr disk,
> -                         bool bootDisk,
> -                         bool isCt)
> +                         virDomainDiskDefPtr disk)
>   {
>       PRL_RESULT pret;
>       PRL_HANDLE sdkdisk = PRL_INVALID_HANDLE;
> @@ -3002,7 +3003,6 @@ static int prlsdkAddDisk(vzConnPtr privconn,
>       PRL_MASS_STORAGE_INTERFACE_TYPE sdkbus;
>       int idx;
>       virDomainDeviceDriveAddressPtr drive;
> -    PRL_UINT32 devIndex;
>       PRL_DEVICE_TYPE devType;
>       PRL_CLUSTERED_DEVICE_SUBTYPE scsiModel;
>       char *dst = NULL;
> @@ -3133,21 +3133,6 @@ static int prlsdkAddDisk(vzConnPtr privconn,
>           goto cleanup;
>       }
>   
> -    if (bootDisk) {
> -        pret = PrlVmDev_GetIndex(sdkdisk, &devIndex);
> -        prlsdkCheckRetGoto(pret, cleanup);
> -
> -        if (prlsdkAddDeviceToBootList(sdkdom, devIndex, devType, 0) < 0)
> -            goto cleanup;
> -
> -        /* If we add physical device as a boot disk to container
> -         * we have to specify mount point for it */
> -        if (isCt) {
> -            pret = PrlVmDevHd_SetMountPoint(sdkdisk, "/");
> -            prlsdkCheckRetGoto(pret, cleanup);
> -        }
> -    }
> -
>       return 0;
>    cleanup:
>       PrlHandle_Free(sdkdisk);
> @@ -3168,11 +3153,7 @@ prlsdkAttachVolume(vzConnPtr privconn,
>       if (PRL_FAILED(waitJob(job)))
>           goto cleanup;
>   
> -    ret = prlsdkAddDisk(privconn,
> -                        privdom->sdkdom,
> -                        disk,
> -                        false,
> -                        IS_CT(dom->def));
> +    ret = prlsdkAddDisk(privconn, privdom->sdkdom, disk);
>       if (ret == 0) {
>           job = PrlVm_CommitEx(privdom->sdkdom, PVCF_DETACH_HDD_BUNDLE);
>           if (PRL_FAILED(waitJob(job))) {
> @@ -3300,6 +3281,86 @@ prlsdkAddFS(PRL_HANDLE sdkdom, virDomainFSDefPtr fs)
>       PrlHandle_Free(sdkdisk);
>       return ret;
>   }
> +
> +static int
> +prlsdkSetBootOrderCt(PRL_HANDLE sdkdom, virDomainDefPtr def)
> +{
> +    size_t i;
> +    PRL_HANDLE hdd = PRL_INVALID_HANDLE;
> +    PRL_RESULT pret;
> +    int ret = -1;
> +
> +    /* if we have root mounted we don't need to explicitly set boot order */
> +    for (i = 0; i < def->nfss; i++) {
> +        if (STREQ(def->fss[i]->dst, "/"))
> +            return 0;
> +    }
> +
> +    /* else set first hard disk as boot device */
> +    pret = prlsdkAddDeviceToBootList(sdkdom, 0, PDE_HARD_DISK, 0);
> +    prlsdkCheckRetExit(pret, -1);
> +
> +    pret = PrlVmCfg_GetHardDisk(sdkdom, 0, &hdd);
> +    prlsdkCheckRetExit(pret, -1);
> +
> +    PrlVmDevHd_SetMountPoint(hdd, "/");
> +    prlsdkCheckRetGoto(pret, cleanup);
> +
> +    ret = 0;
> +
> + cleanup:
> +    PrlHandle_Free(hdd);
> +    return ret;
> +}
> +
> +static int
> +prlsdkSetBootOrderVm(PRL_HANDLE sdkdom, virDomainDefPtr def)
> +{
> +    size_t i;
> +    int idx[VIR_DOMAIN_BOOT_LAST] = { 0 };
> +    int bootIndex = 0;
> +    PRL_RESULT pret;
> +    PRL_UINT32 num;
> +    int sdkType;
> +    virDomainBootOrder virType;
> +
> +    for (i = 0; i < def->os.nBootDevs; ++i) {
> +        virType = def->os.bootDevs[i];
> +
> +        switch (virType) {
> +        case VIR_DOMAIN_BOOT_CDROM:
> +            sdkType = PDE_OPTICAL_DISK;
> +            break;
> +        case VIR_DOMAIN_BOOT_DISK:
> +            sdkType = PDE_HARD_DISK;
> +            break;
> +        case VIR_DOMAIN_BOOT_NET:
> +            sdkType = PDE_GENERIC_NETWORK_ADAPTER;
> +            break;
> +        default:
> +            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
> +                           _("Unsupported boot device type: '%s'"),
> +                           virDomainBootTypeToString(virType));
> +            return -1;
> +        }
> +
> +        pret = PrlVmCfg_GetDevsCountByType(sdkdom, sdkType, &num);
> +        prlsdkCheckRetExit(pret, -1);
> +
> +        if (idx[virType] >= num) {
> +            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
> +                           _("Too many devices of type '%s' in boot spec"),
> +                           virDomainBootTypeToString(virType));
> +            return -1;
> +        }

I would ease this strictness and remove the check as we didn't have it 
before and it actually doesn't solve any potential problem and only 
prohibits what was allowed before.

> +
> +        pret = prlsdkAddDeviceToBootList(sdkdom, idx[virType]++, sdkType, bootIndex++);
> +        prlsdkCheckRetExit(pret, -1);
> +    }
> +
> +    return 0;
> +}
> +
>   static int
>   prlsdkDoApplyConfig(virConnectPtr conn,
>                       PRL_HANDLE sdkdom,
> @@ -3309,7 +3370,6 @@ prlsdkDoApplyConfig(virConnectPtr conn,
>       PRL_RESULT pret;
>       size_t i;
>       char uuidstr[VIR_UUID_STRING_BUFLEN + 2];
> -    bool needBoot = true;
>       char *mask = NULL;
>   
>       if (prlsdkCheckUnsupportedParams(sdkdom, def) < 0)
> @@ -3388,26 +3448,20 @@ prlsdkDoApplyConfig(virConnectPtr conn,
>       }
>   
>       for (i = 0; i < def->nfss; i++) {
> -        if (STREQ(def->fss[i]->dst, "/"))
> -            needBoot = false;
>           if (prlsdkAddFS(sdkdom, def->fss[i]) < 0)
>               goto error;
>       }
>   
>       for (i = 0; i < def->ndisks; i++) {
> -        bool bootDisk = false;
> -
> -        if (needBoot &&
> -            def->disks[i]->device == VIR_DOMAIN_DISK_DEVICE_DISK) {
> +        if (prlsdkAddDisk(conn->privateData, sdkdom, def->disks[i]) < 0)
> +            goto error;
> +    }
>   
> -            needBoot = false;
> -            bootDisk = true;
> -        }
> -        if (prlsdkAddDisk(conn->privateData,
> -                          sdkdom,
> -                          def->disks[i],
> -                          bootDisk,
> -                          IS_CT(def)) < 0)
> +    if (IS_CT(def)) {
> +        if (prlsdkSetBootOrderCt(sdkdom, def) < 0)
> +            goto error;
> +    } else {
> +        if (prlsdkSetBootOrderVm(sdkdom, def) < 0)
>               goto error;
>       }
>   




More information about the libvir-list mailing list