mirror of
				https://gitlab.com/libvirt/libvirt.git
				synced 2025-11-04 12:24:23 +03:00 
			
		
		
		
	storage: optional 'refresh' elemement on pool
The new 'refresh' element can override the default refresh operations
for a storage pool. The only currently supported override is to set
the volume allocation size to the volume capacity. This can be specified
by adding the following snippet:
<pool>
...
  <refresh>
    <volume allocation='capacity'/>
  </refresh>
...
</pool>
This is useful for certain backends where computing the actual allocation
of a volume might be an expensive operation.
Signed-off-by: Jason Dillaman <dillaman@redhat.com>
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
			
			
This commit is contained in:
		
				
					committed by
					
						
						Michal Privoznik
					
				
			
			
				
	
			
			
			
						parent
						
							21deeaf02f
						
					
				
				
					commit
					669018bc9c
				
			@@ -508,6 +508,32 @@
 | 
			
		||||
      device, measured in bytes.  <span class="since">Since 0.4.1</span>
 | 
			
		||||
    </p>
 | 
			
		||||
 | 
			
		||||
    <h3><a id="StoragePoolRefresh">Refresh overrides</a></h3>
 | 
			
		||||
 | 
			
		||||
    <p>
 | 
			
		||||
      The optional <code>refresh</code> element can control how the pool and
 | 
			
		||||
      associated volumes are refreshed (pool type <code>rbd</code>). The
 | 
			
		||||
      <code>allocation</code> attribute of the <code>volume</code> child element
 | 
			
		||||
      controls the method used for computing the allocation of a volume. The
 | 
			
		||||
      valid attribute values are <code>default</code> to compute the actual
 | 
			
		||||
      usage or <code>capacity</code> to use the logical capacity for cases where
 | 
			
		||||
      computing the allocation is too expensive. The following XML snippet
 | 
			
		||||
      shows the syntax:
 | 
			
		||||
      <pre>
 | 
			
		||||
<pool type="rbd">
 | 
			
		||||
  <name>myrbdpool</name>
 | 
			
		||||
...
 | 
			
		||||
  <source/>
 | 
			
		||||
...
 | 
			
		||||
  <refresh>
 | 
			
		||||
    <volume allocation='capacity'/>
 | 
			
		||||
  </refresh>
 | 
			
		||||
...
 | 
			
		||||
</pool>
 | 
			
		||||
</pre>
 | 
			
		||||
      <span class="since">Since 5.2.0</span>
 | 
			
		||||
    </p>
 | 
			
		||||
 | 
			
		||||
    <h3><a id="StoragePoolNamespaces">Storage Pool Namespaces</a></h3>
 | 
			
		||||
 | 
			
		||||
    <p>
 | 
			
		||||
 
 | 
			
		||||
@@ -236,4 +236,11 @@
 | 
			
		||||
    </optional>
 | 
			
		||||
  </define>
 | 
			
		||||
 | 
			
		||||
  <define name='refreshVolumeAllocation'>
 | 
			
		||||
    <choice>
 | 
			
		||||
      <value>default</value>
 | 
			
		||||
      <value>capacity</value>
 | 
			
		||||
    </choice>
 | 
			
		||||
  </define>
 | 
			
		||||
 | 
			
		||||
</grammar>
 | 
			
		||||
 
 | 
			
		||||
@@ -155,6 +155,7 @@
 | 
			
		||||
      <ref name='commonMetadataNameOptional'/>
 | 
			
		||||
      <ref name='sizing'/>
 | 
			
		||||
      <ref name='sourcerbd'/>
 | 
			
		||||
      <ref name='refresh'/>
 | 
			
		||||
    </interleave>
 | 
			
		||||
    <optional>
 | 
			
		||||
      <ref name='rbd_config_opts'/>
 | 
			
		||||
@@ -691,6 +692,28 @@
 | 
			
		||||
    </data>
 | 
			
		||||
  </define>
 | 
			
		||||
 | 
			
		||||
  <define name='refresh'>
 | 
			
		||||
    <optional>
 | 
			
		||||
      <element name='refresh'>
 | 
			
		||||
        <interleave>
 | 
			
		||||
          <ref name='refreshVolume'/>
 | 
			
		||||
        </interleave>
 | 
			
		||||
      </element>
 | 
			
		||||
    </optional>
 | 
			
		||||
  </define>
 | 
			
		||||
 | 
			
		||||
  <define name='refreshVolume'>
 | 
			
		||||
    <optional>
 | 
			
		||||
      <element name='volume'>
 | 
			
		||||
        <optional>
 | 
			
		||||
          <attribute name='allocation'>
 | 
			
		||||
            <ref name="refreshVolumeAllocation"/>
 | 
			
		||||
          </attribute>
 | 
			
		||||
        </optional>
 | 
			
		||||
      </element>
 | 
			
		||||
    </optional>
 | 
			
		||||
  </define>
 | 
			
		||||
 | 
			
		||||
  <!--
 | 
			
		||||
       Optional storage pool extensions in their own namespace:
 | 
			
		||||
         "fs" or "netfs"
 | 
			
		||||
 
 | 
			
		||||
@@ -94,6 +94,11 @@ VIR_ENUM_IMPL(virStorageVolFormatDisk,
 | 
			
		||||
              "extended",
 | 
			
		||||
);
 | 
			
		||||
 | 
			
		||||
VIR_ENUM_IMPL(virStorageVolDefRefreshAllocation,
 | 
			
		||||
              VIR_STORAGE_VOL_DEF_REFRESH_ALLOCATION_LAST,
 | 
			
		||||
              "default", "capacity",
 | 
			
		||||
);
 | 
			
		||||
 | 
			
		||||
VIR_ENUM_IMPL(virStoragePartedFs,
 | 
			
		||||
              VIR_STORAGE_PARTED_FS_TYPE_LAST,
 | 
			
		||||
              "ext2", "ext2", "fat16",
 | 
			
		||||
@@ -789,6 +794,51 @@ virStorageDefParsePerms(xmlXPathContextPtr ctxt,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
virStoragePoolDefRefreshParse(xmlXPathContextPtr ctxt,
 | 
			
		||||
                              virStoragePoolDefPtr def)
 | 
			
		||||
{
 | 
			
		||||
    VIR_AUTOFREE(virStoragePoolDefRefreshPtr) refresh = NULL;
 | 
			
		||||
    VIR_AUTOFREE(char *) allocation = NULL;
 | 
			
		||||
    int tmp;
 | 
			
		||||
 | 
			
		||||
    allocation = virXPathString("string(./refresh/volume/@allocation)", ctxt);
 | 
			
		||||
 | 
			
		||||
    if (!allocation)
 | 
			
		||||
        return 0;
 | 
			
		||||
 | 
			
		||||
    if ((tmp = virStorageVolDefRefreshAllocationTypeFromString(allocation)) < 0) {
 | 
			
		||||
        virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
 | 
			
		||||
                       _("unknown storage pool volume refresh allocation type %s"),
 | 
			
		||||
                       allocation);
 | 
			
		||||
        return -1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (VIR_ALLOC(refresh) < 0)
 | 
			
		||||
        return -1;
 | 
			
		||||
 | 
			
		||||
    refresh->volume.allocation = tmp;
 | 
			
		||||
    VIR_STEAL_PTR(def->refresh, refresh);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static void
 | 
			
		||||
virStoragePoolDefRefreshFormat(virBufferPtr buf,
 | 
			
		||||
                               virStoragePoolDefRefreshPtr refresh)
 | 
			
		||||
{
 | 
			
		||||
    if (!refresh)
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    virBufferAddLit(buf, "<refresh>\n");
 | 
			
		||||
    virBufferAdjustIndent(buf, 2);
 | 
			
		||||
    virBufferAsprintf(buf, "<volume allocation='%s'/>\n",
 | 
			
		||||
                      virStorageVolDefRefreshAllocationTypeToString(refresh->volume.allocation));
 | 
			
		||||
    virBufferAdjustIndent(buf, -2);
 | 
			
		||||
    virBufferAddLit(buf, "</refresh>\n");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
virStoragePoolDefPtr
 | 
			
		||||
virStoragePoolDefParseXML(xmlXPathContextPtr ctxt)
 | 
			
		||||
{
 | 
			
		||||
@@ -799,6 +849,7 @@ virStoragePoolDefParseXML(xmlXPathContextPtr ctxt)
 | 
			
		||||
    VIR_AUTOFREE(char *) type = NULL;
 | 
			
		||||
    VIR_AUTOFREE(char *) uuid = NULL;
 | 
			
		||||
    VIR_AUTOFREE(char *) target_path = NULL;
 | 
			
		||||
    VIR_AUTOFREE(char *) refresh_volume_allocation = NULL;
 | 
			
		||||
 | 
			
		||||
    if (VIR_ALLOC(def) < 0)
 | 
			
		||||
        return NULL;
 | 
			
		||||
@@ -931,6 +982,9 @@ virStoragePoolDefParseXML(xmlXPathContextPtr ctxt)
 | 
			
		||||
        return NULL;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (virStoragePoolDefRefreshParse(ctxt, def) < 0)
 | 
			
		||||
        return NULL;
 | 
			
		||||
 | 
			
		||||
    /* Make a copy of all the callback pointers here for easier use,
 | 
			
		||||
     * especially during the virStoragePoolSourceClear method */
 | 
			
		||||
    def->ns = options->ns;
 | 
			
		||||
@@ -1163,6 +1217,8 @@ virStoragePoolDefFormatBuf(virBufferPtr buf,
 | 
			
		||||
        virBufferAddLit(buf, "</target>\n");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    virStoragePoolDefRefreshFormat(buf, def->refresh);
 | 
			
		||||
 | 
			
		||||
    if (def->namespaceData && def->ns.format) {
 | 
			
		||||
        if ((def->ns.format)(buf, def->namespaceData) < 0)
 | 
			
		||||
            return -1;
 | 
			
		||||
 
 | 
			
		||||
@@ -83,6 +83,13 @@ struct _virStorageVolSource {
 | 
			
		||||
                   * backend for partition type creation */
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
typedef enum {
 | 
			
		||||
    VIR_STORAGE_VOL_DEF_REFRESH_ALLOCATION_DEFAULT,  /* compute actual allocation */
 | 
			
		||||
    VIR_STORAGE_VOL_DEF_REFRESH_ALLOCATION_CAPACITY, /* use logical capacity */
 | 
			
		||||
    VIR_STORAGE_VOL_DEF_REFRESH_ALLOCATION_LAST,
 | 
			
		||||
} virStorageVolDefRefreshAllocation;
 | 
			
		||||
 | 
			
		||||
VIR_ENUM_DECL(virStorageVolDefRefreshAllocation);
 | 
			
		||||
 | 
			
		||||
typedef struct _virStorageVolDef virStorageVolDef;
 | 
			
		||||
typedef virStorageVolDef *virStorageVolDefPtr;
 | 
			
		||||
@@ -236,6 +243,21 @@ struct _virStoragePoolTarget {
 | 
			
		||||
    virStoragePerms perms; /* Default permissions for volumes */
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
typedef struct _virStorageVolDefRefresh virStorageVolDefRefresh;
 | 
			
		||||
typedef virStorageVolDefRefresh *virStorageVolDefRefreshPtr;
 | 
			
		||||
struct _virStorageVolDefRefresh {
 | 
			
		||||
  int allocation; /* virStorageVolDefRefreshAllocation */
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
typedef struct _virStoragePoolDefRefresh virStoragePoolDefRefresh;
 | 
			
		||||
typedef virStoragePoolDefRefresh *virStoragePoolDefRefreshPtr;
 | 
			
		||||
struct _virStoragePoolDefRefresh {
 | 
			
		||||
  virStorageVolDefRefresh volume;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
typedef struct _virStoragePoolDef virStoragePoolDef;
 | 
			
		||||
typedef virStoragePoolDef *virStoragePoolDefPtr;
 | 
			
		||||
struct _virStoragePoolDef {
 | 
			
		||||
@@ -243,6 +265,8 @@ struct _virStoragePoolDef {
 | 
			
		||||
    unsigned char uuid[VIR_UUID_BUFLEN];
 | 
			
		||||
    int type; /* virStoragePoolType */
 | 
			
		||||
 | 
			
		||||
    virStoragePoolDefRefreshPtr refresh;
 | 
			
		||||
 | 
			
		||||
    unsigned long long allocation; /* bytes */
 | 
			
		||||
    unsigned long long capacity; /* bytes */
 | 
			
		||||
    unsigned long long available; /* bytes */
 | 
			
		||||
 
 | 
			
		||||
@@ -942,6 +942,8 @@ virStorageVolDefFree;
 | 
			
		||||
virStorageVolDefParseFile;
 | 
			
		||||
virStorageVolDefParseNode;
 | 
			
		||||
virStorageVolDefParseString;
 | 
			
		||||
virStorageVolDefRefreshAllocationTypeFromString;
 | 
			
		||||
virStorageVolDefRefreshAllocationTypeToString;
 | 
			
		||||
virStorageVolTypeFromString;
 | 
			
		||||
virStorageVolTypeToString;
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -0,0 +1,15 @@
 | 
			
		||||
<pool type='rbd'>
 | 
			
		||||
  <name>ceph</name>
 | 
			
		||||
  <uuid>47c1faee-0207-e741-f5ae-d9b019b98fe2</uuid>
 | 
			
		||||
  <source>
 | 
			
		||||
    <name>rbd</name>
 | 
			
		||||
    <host name='localhost' port='6789'/>
 | 
			
		||||
    <host name='localhost' port='6790'/>
 | 
			
		||||
    <auth username='admin' type='ceph'>
 | 
			
		||||
      <secret uuid='2ec115d7-3a88-3ceb-bc12-0ac909a6fd87'/>
 | 
			
		||||
    </auth>
 | 
			
		||||
  </source>
 | 
			
		||||
  <refresh>
 | 
			
		||||
    <volume allocation='capacity'/>
 | 
			
		||||
  </refresh>
 | 
			
		||||
</pool>
 | 
			
		||||
@@ -0,0 +1,18 @@
 | 
			
		||||
<pool type='rbd'>
 | 
			
		||||
  <name>ceph</name>
 | 
			
		||||
  <uuid>47c1faee-0207-e741-f5ae-d9b019b98fe2</uuid>
 | 
			
		||||
  <capacity unit='bytes'>0</capacity>
 | 
			
		||||
  <allocation unit='bytes'>0</allocation>
 | 
			
		||||
  <available unit='bytes'>0</available>
 | 
			
		||||
  <source>
 | 
			
		||||
    <host name='localhost' port='6789'/>
 | 
			
		||||
    <host name='localhost' port='6790'/>
 | 
			
		||||
    <name>rbd</name>
 | 
			
		||||
    <auth type='ceph' username='admin'>
 | 
			
		||||
      <secret uuid='2ec115d7-3a88-3ceb-bc12-0ac909a6fd87'/>
 | 
			
		||||
    </auth>
 | 
			
		||||
  </source>
 | 
			
		||||
  <refresh>
 | 
			
		||||
    <volume allocation='capacity'/>
 | 
			
		||||
  </refresh>
 | 
			
		||||
</pool>
 | 
			
		||||
@@ -95,6 +95,7 @@ mymain(void)
 | 
			
		||||
    DO_TEST("pool-zfs-sourcedev");
 | 
			
		||||
    DO_TEST("pool-rbd");
 | 
			
		||||
#ifdef WITH_STORAGE_RBD
 | 
			
		||||
    DO_TEST("pool-rbd-refresh-volume-allocation");
 | 
			
		||||
    DO_TEST("pool-rbd-ns-configopts");
 | 
			
		||||
#endif
 | 
			
		||||
    DO_TEST("pool-vstorage");
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user