{"id":5236,"date":"2017-04-24T09:17:40","date_gmt":"2017-04-24T07:17:40","guid":{"rendered":"https:\/\/new.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/"},"modified":"2023-03-08T16:04:32","modified_gmt":"2023-03-08T15:04:32","slug":"block-level-data-tracking-using-davice-mappers-dm-era","status":"publish","type":"post","link":"https:\/\/www.cloudandheat.com\/en\/block-level-data-tracking-using-davice-mappers-dm-era\/","title":{"rendered":"Block-level data tracking using device mapper's dm-era"},"content":{"rendered":"<p>&nbsp;<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">This blog post will be a full tutorial about the usage of the \u201cera\u201d target of device mapper, also known as \u201cdm-era\u201d. It provides a step by step walkthrough for setting up the device mapper mappings and parsing the resulting metadata.<\/span><\/p>\n<p>&nbsp;<\/p>\n<h2>Content<\/h2>\n<p><a href=\"#devicemappermappings\">Device Mapper Mappings<\/a><\/p>\n<p><a href=\"#CreatingaplaygroundWMusingVagrant\">Creating a playground VM using Vagrant<\/a><\/p>\n<p><a href=\"#DeviceMApperSetup\">Device Mapper Setup<\/a><\/p>\n<p><a href=\"#DeterminingMetadatasize\">Determining Metadata size<\/a><\/p>\n<p><a href=\"#Usingtheeradevice\">Using the dm-era<\/a><\/p>\n<p><a href=\"#Conclusiones\">Conclusion<\/a><\/p>\n<p><a href=\"#Acknowledgments\">Acknowledgments<\/a><\/p>\n<p>&nbsp;<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The \u201cera\u201d target of device mapper can be quite powerful when looking for live tracking of changed blocks on an arbitrary block device, no matter if physical or logical. Since it is a low-level device mapper target it supports raw\/physical block devices, device mapper targets as well as LVM volumes to keep track of.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The dm-era target has been integral part of the Linux kernel since version 3.15. So it has been around for quite a while already, however, documentation is still astonishingly sparse. Essentially, I could only come up with three results while searching the web: the <\/span><a href=\"https:\/\/www.kernel.org\/doc\/Documentation\/device-mapper\/era.txt\" target=\"_blank\" rel=\"noopener\"><span style=\"font-size: 11.0pt; font-family: Montserrat;\">official kernel docs<\/span><\/a><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> <sup>[1]<\/sup>, a <\/span><a href=\"http:\/\/blog.rackcorp.com\/2016\/03\/dm-era-device-for-backups\/\" target=\"_blank\" rel=\"noopener\"><span style=\"font-size: 11.0pt; font-family: Montserrat;\">blog post by Rackcorp<\/span><\/a><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> <sup>[2]<\/sup>, and a <\/span><a href=\"https:\/\/wiki.gentoo.org\/wiki\/Device-mapper#Era\" target=\"_blank\" rel=\"noopener\"><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Gentoo wiki entry<\/span><\/a><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> <sup>[3]<\/sup>.<br \/>\nSince the kernel docs and the Gentoo wiki entry only provide the most basic information without full usage examples, the Rackspace blog entry is a more elaborated guide \u2013 but not without its flaws.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The essential part about working with device mapper is to understand that the basic size unit used is sectors. Whenever specifying a size for mappings, keep in mind it\u2019s at sector level. Usually a sector is defined as 512 bytes.<\/span><\/p>\n<p>&nbsp;<\/p>\n<h2 id=\"devicemappermappings\">Device Mapper Mappings<\/h2>\n<p>&nbsp;<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The basic modus operandi of device mapper is to apply mappings to block devices. That means you will be building layers above block devices, creating new block devices in the process. This is achieved by \u201ctargets\u201d, which are modules for device mapper that provide a particular mapping functionality.<br \/>\nThe most basic target is \u201clinear\u201d, which means the resulting block device will be a mapping to one or more linear sections of one or more other block devices. This way it\u2019s possible to logically merge two block devices into one or to split one up into several (like logical partitions). Please refer to one of the plenty documentations or tutorials about the \u201clinear\u201d device mapper target to learn more.<br \/>\nIn this guide we will be focussing on the cooperation of \u201clinear\u201d and \u201cera\u201d device mapper targets to track changed blocks on a block device in realtime.<\/span><\/p>\n<h3><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The Era Target<\/span><\/h3>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The \u201cera\u201d target behaves similar to the \u201clinear\u201d target but additionally it writes metadata to a separate block device which is used to keep track of changed blocks on the origin block device. To be precise, the \u201cera\u201d target keeps track of changed blocks within a specific period of time, called an era. This era is a monotonically increasing counter and each block has an era associated to it, where it was last updated in. The era can be increased by command and is also automatically increased when grabbing a metadata snapshot to inspect changed blocks. This allows tracking changed blocks between those snapshots and can be used for a variety of use cases, e.g. incremental backup or replication strategies.<br \/>\nOther than that, the \u201cera\u201d target does an identity mapping to the underlying origin block device, normally chosen the same size as its origin.<\/span><\/p>\n<p>&nbsp;<\/p>\n<h2 id=\"CreatingaplaygroundWMusingVagrant\">Creating a playground VM using Vagrant<\/h2>\n<p>For this tutorial, we will be setting up a virtual machine (VM) with 2 additional drives using VirtualBox. We will be using the VM and the drives to create a sample dm-era setup, so you can easily recreate an identical setup and follow the instructions step-by-step. To make things quick and easy regarding the VM setup, we will be using Vagrant to automatically set this up. Place the following file named \u201cVagrantfile\u201d into a (preferably empty) folder of your choice:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>extdisk1 = '.\/extdisk1.vdi'\nextdisk2 = '.\/extdisk2.vdi'\nVagrant.configure(\"2\") do |config|\nconfig.vm.define \"alice\" do |alice|\nalice.vm.provider \"virtualbox\" do |vbox|\nvbox.name = \"dm-era-testvm\"\nunless File.exist?(extdisk1)\nvbox.customize ['createhd', '--filename', extdisk1, '--size', 256]\nvbox.customize ['storageattach', :id, '--storagectl', 'SATA Controller', '--port', 1, '--device', 0, '--type', 'hdd', '--medium', extdisk1]\nend\nunless File.exist?(extdisk2)\nvbox.customize ['createhd', '--filename', extdisk2, '--size', 256]\nvbox.customize ['storageattach', :id, '--storagectl', 'SATA Controller', '--port', 2, '--device', 0, '--type', 'hdd', '--medium', extdisk2]\nend\nend\nalice.vm.box = \"bento\/ubuntu-16.04\"\nalice.vm.hostname = \"alice\"\nend\nend\n<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">This Vagrantfile will download the \u201cbento\/ubuntu-16.04\u201d image from the Vagrant repositories, which is a pre-configured Ubuntu 16.04 minimal VM. Additionally, it will create two 256 MB virtual disk files and attach them to the VM.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">After saving the file, start up the VM from command line in the same folder:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant up<\/code><\/pre>\n<p>&nbsp;<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">This will completely setup and start the VM. After its completion, you can SSH into the new VM:<\/span><\/p>\n<pre><span style=\"font-size: 11.0pt; font-family: Montserrat;\"><code>vagrant ssh alice<\/code><\/span><\/pre>\n<p>&nbsp;<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">(You may omit stating the machine name, if your Vagrantfile contains only one VM)<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Now verify, that the additional drives exist:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ lsblk\nNAME&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; MAJ:MIN RM&nbsp; SIZE RO TYPE MOUNTPOINT\n...\nsdb&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 8:16&nbsp;&nbsp; 0&nbsp; 256M&nbsp; 0 disk\nsdc&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;8:32&nbsp;&nbsp; 0&nbsp; 256M&nbsp; 0 disk<\/code><\/pre>\n<p>&nbsp;<\/p>\n<p>It should list two additional drives sized 256M each. Now we\u2019ve got our playground ready, let\u2019s start setting up dm-era!<\/p>\n<h2 id=\"DeviceMApperSetup\">Device Mapper setup<\/h2>\n<p>In contrast to Rackcorp\u2019s tutorial [2], we will be using only device mapper in this guide, no LVM. Keep in mind, that you <em>can<\/em> use the dm-era mapping on LVM volumes or simply any block device just fine as well. LVM is simply using device mapper in the background anyway. All following instructions and examples are based on the sample VM setup as described above.<\/p>\n<p>The resulting setup we will try to achieve will look as follows:<\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p><img fetchpriority=\"high\" decoding=\"async\" class=\" wp-image-2231\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-01.png\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"920\" height=\"364\"><\/p>\n<p>The two physical drives (sdb and sdc) each fulfill different purposes: sdb will only be used for holding the era metadata (information about changed blocks), whereas sdc will be the data device (origin), which we want to track the changed blocks of. <a href=\"https:\/\/www.redhat.com\/archives\/dm-devel\/2014-September\/msg00168.html\">Holding both the metadata and the origin on the same physical drive<\/a><sup>[4]<\/sup> is not supported [4].<\/p>\n<p>The era device \u2013 simply called \u201cera\u201d \u2013 will be layered ontop of the origin drive (sdc), similar to a linear mapping. Further, we will logically partition sdb by applying a linear mapping called \u201cera-meta\u201d of a fixed size to it, required for the metadata. Since device mapper can\u2019t read the metadata directly from it, a second linear mapping to the metadata is required for metadata snapshots and read operations. We will create this as \u201cera-access\u201d in same size as the metadata mapping ontop of the \u201cera-meta\u201d device.<\/p>\n<p>Before beginning to set this up, we have to determine the size required by the metadata. And this is a tricky topic.<\/p>\n<h2 id=\"DeterminingMetadatasize\">Determining Metadata size<\/h2>\n<p>(You can <a href=\"https:\/\/www.cloudandheat.com\/blog\/block-level-data-tracking-using-device-mappers-dm-era-e-g-for-replication-2\/#settingupdmera\">skip this chapter<\/a><sup>[5]<\/sup> if you are not interested in how I determined the estimated formula for metadata size requirement)<\/p>\n<p>Unfortunately, neither the official docs nor the dm tools themselves tell you anything about the size that will be required by the metadata device for correct function of the era device.<br \/>\nThe blog entry by Rackcorp [2] simply states that dividing the origin device\u2019s size by 1000 is sufficient.<br \/>\nHowever, that is a very rough estimate. Let\u2019s say you have a 1TB large drive you want to track blocks of using dm-era. With this formula you\u2019d estimate to reserve 1GB on another drive solely for the metadata. But actually my internal tests showed a far less space requirement than this. By several orders of magnitudes.<\/p>\n<p>So, I wasn\u2019t satisfied with this estimate pulled out of thin air, without any indication of what this assumption is actually based on. To get a little closer to reality you are basically left with two choices: For one you could dig into the kernel\u2019s source code related to dm-era and try to put up a formula based on the actual code \u2013 on the other hand you could simply try to estimate a formula based on a series of measurements done on differently sized era devices.<br \/>\nSince the first option requires a kernel specialist or at least someone familiar with the workings of device mapper and a sufficient amount of time on their hands, I was only left with the second option.<\/p>\n<h3>Estimating metadata size using empirical trials<\/h3>\n<p>I did the tests within an Ubuntu 16.04 VM and two virtual hard drives, which will be referred to as sdb and sdc. The sdb drive is a small 256M sized drive that acted as a containment for the metadata and another up to 16TB sized sdc drive that acted as a origin for the era device.<br \/>\nNow I set up a dm-era setup which uses a fixed amount of sdc as the origin and tried to find the minimum required metadata size on sdb. For each sdc size I slowly increased the size of the linear mapping ontop of sdb by 4k steps, trying to execute the following steps each time:<\/p>\n<ul>\n<li>set up a linear mapping on sdb using the current proposed metadata size<\/li>\n<li>set up a dm-era mapping\n<ul>\n<li>use fixed size linear mapping on sdc as origin<\/li>\n<li>use the linear mapping on sdb as metadata device target<\/li>\n<\/ul>\n<\/li>\n<li>try taking and dropping a metadata snapshot subsequently 10 times<\/li>\n<\/ul>\n<p>If the above mentioned procedure fails at any step, the metadata size is insufficient, leading to errors. However, if all of the steps succeed without issues, we deem the chosen metadata size as being sufficient for the current sdc mapping size. This is based on the assumption that taking more than 10 metadata snapshots (eras) or actually writing data to the origin device does not influence the required size any further, i.e. the size requirement does not grow over time.<br \/>\nTesting this with varying sizes of sdc mappings (up to 16TB) led to the following values getting recorded:<\/p>\n<p>&nbsp;<\/p>\n<table>\n<tbody>\n<tr>\n<td rowspan=\"2\"><strong>data size<br \/>\nin MB<\/strong><\/td>\n<td colspan=\"2\"><strong>required metadata size<\/strong><\/td>\n<\/tr>\n<tr>\n<td>for 4k (sectors) granularity<\/td>\n<td>for 8k (sectors) granularity<\/td>\n<\/tr>\n<tr>\n<td>4M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>8M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>16M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>32M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>64M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>128M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>256M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>512M<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>1G<\/td>\n<td>64<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>2G<\/td>\n<td>68<\/td>\n<td>64<\/td>\n<\/tr>\n<tr>\n<td>4G<\/td>\n<td>72<\/td>\n<td>68<\/td>\n<\/tr>\n<tr>\n<td>8G<\/td>\n<td>80<\/td>\n<td>72<\/td>\n<\/tr>\n<tr>\n<td>16G<\/td>\n<td>96<\/td>\n<td>80<\/td>\n<\/tr>\n<tr>\n<td>32G<\/td>\n<td>128<\/td>\n<td>96<\/td>\n<\/tr>\n<tr>\n<td>64G<\/td>\n<td>204<\/td>\n<td>128<\/td>\n<\/tr>\n<tr>\n<td>128G<\/td>\n<td>344<\/td>\n<td>204<\/td>\n<\/tr>\n<tr>\n<td>256G<\/td>\n<td>628<\/td>\n<td>348<\/td>\n<\/tr>\n<tr>\n<td>512G<\/td>\n<td>1336<\/td>\n<td>628<\/td>\n<\/tr>\n<tr>\n<td>1T<\/td>\n<td>2768<\/td>\n<td>1320<\/td>\n<\/tr>\n<tr>\n<td>2T<\/td>\n<td>5568<\/td>\n<td>2764<\/td>\n<\/tr>\n<tr>\n<td>4T<\/td>\n<td>11248<\/td>\n<td>5560<\/td>\n<\/tr>\n<tr>\n<td>8T<\/td>\n<td>22308<\/td>\n<td>11248<\/td>\n<\/tr>\n<tr>\n<td>16T<\/td>\n<td>42388<\/td>\n<td>21168<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>&nbsp;<\/p>\n<p><img decoding=\"async\" class=\"size-full wp-image-2230\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-02.png\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"803\" height=\"450\"><\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p>Although this looks like an exponential correlation at first glance, take notice that the x axis is not on linear scale but a power of 2 due to the sizes tested. When putting this into a chart with linear scaling on both axes, an almost perfect linear correlation becomes visible:<\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p><img decoding=\"async\" class=\"size-full wp-image-2232\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-03.png\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"532\" height=\"471\"><\/p>\n<p>&nbsp;<\/p>\n<p>Here I observed required metadata size for varying origin device size while keeping the granularity (dm-era setup command block size) constant.<\/p>\n<p>Besides the origin device size, the granularity is the second influence to the metadata size requirement. That\u2019s why I also had a closer look to varying granularity in a second measurement series. Here I varied the granularity while keeping the origin device size constant:<\/p>\n<figure id=\"attachment_2233\" aria-describedby=\"caption-attachment-2233\" style=\"width: 554px\" class=\"wp-caption alignnone\"><img loading=\"lazy\" decoding=\"async\" class=\"size-full wp-image-2233\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-04.png\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"554\" height=\"340\"><figcaption id=\"caption-attachment-2233\" class=\"wp-caption-text\">Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud<\/figcaption><\/figure>\n<p>&nbsp;<\/p>\n<p>The graph shows that the relation is not exactly linear which makes it harder to generate a one-size-fits-all formula for the calculation for the metadata size as any approximation towards the origin device size is additionally influenced by the chosen granularity in a non-linear fashion.<\/p>\n<p>This is the reason why I decided to stick to 4k (sectors) granularity while approximating the formula. Using the linear regression framework of the math framework R and our measured values in KB, the following formula was generated:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>metadata_size = 2.49E-6 * origin_size + 115.4<\/code><\/pre>\n<p>(all values in KB)<\/p>\n<p>To leave enough space for deviation and to streamline the values to multiples of 4k, I adjusted this to:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>metadata_size = round( (2.5E-6 * origin_size + 128) \/ 4 ) * 4<\/code><\/pre>\n<p>(all values in KB)<\/p>\n<h2 id=\"Settingupdm-era\"><a href=\"#Settingupdm-era\">Setting up dm-era<\/a><\/h2>\n<p>The following explanations will always refer to the setup overview illustration from above.<\/p>\n<h3>\u201cera-meta\u201d \u2013 the metadata target<\/h3>\n<p>First we will setup a part of sdb to function as a storage for the metadata created by dm-era where it stores information about the eras and blocks. We only need a fraction of the 256 MB that sdb offers. According to our formula explained above, we only require 128 KB for the metadata. To logically partition sdb so that the remaining space may be used otherwise, we create a linear mapping for the first 128 KB. As mentioned before, device mapper works on sector level, thus we need to calculate the amount of 512 byte sectors needed for 128 KB:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>sectors = 128 * 1024 \/ 512 = 256\n<\/code> Now we can create a linear mapping (run as root):<\/pre>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup create era-meta --table \"0 256 linear \/dev\/sdb 0\" <\/code><\/pre>\n<p>&nbsp;<\/p>\n<p>This creates a new logical block device called \u201cera-meta\u201d whose sectors\/blocks ranging from 0 to 256 are mapped to sdb in a linear fashion. The last digit (zero in this case) is the offset of the mapping on sdb. If you would create several metadata targets on sdb, you will have to adjust the offset to the sum of any preceeding mappings so that they don\u2019t overlap on sdb.<\/p>\n<p>We can now verify our 128 KB sized linear mapping called \u201cera-meta\u201d:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ lsblk\nNAME                   MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT\n...\nsdb                      8:16   0  256M  0 disk \n`-era-meta             252:2    0  128K  0 dm   \nsdc                      8:32   0  256M  0 disk<\/code><\/pre>\n<p>It will show up and be accessible on \/dev\/mapper\/era-meta.<\/p>\n<h3>\u201cera\u201d \u2013 the data holding target<\/h3>\n<p>Since our metadata target is now prepared, we can proceed by creating our actual dm-era target mapping. The era target has to be the same size as the underlying data block device. We need its size in 512 byte sectors again, which we can determine via the following command:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>blockdev --getsz \/dev\/sd<\/code><\/pre>\n<p>For our 256 MB sized sdc device this yields 524288 sectors (physical blocks). We are now able to set up our era device (run as root):<\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup create era --table \"0 524288 era \/dev\/mapper\/era-meta \/dev\/sdc 4096\"<\/code><\/pre>\n<p>Here we create new logical block device called \u201cera\u201d that contains a direct linear mapping to sdc for the first 524288 blocks. Additionally, our \u201cera-meta\u201d mapping is used as a target for metadata. The 4096 is the tracking granularity of the era device in sectors, also called \u201cblock size\u201d in the official docs. Essentially it is the resolution of the block change tracking mechanism. If anything changes within a block of 4096 sectors, that block is marked as changed.<br \/>\nWe can again verify the creation of this mapping:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ lsblk\nNAME                   MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT\n...\nsdb                      8:16   0  256M  0 disk \n`-era-meta             252:2    0  128K  0 dm   \n`-era                252:3    0  256M  0 dm   \nsdc                      8:32   0  256M  0 disk \n`-era                  252:3    0  256M  0 dm<\/code><\/pre>\n<p>What may look irritating at first is that the 256 MB \u201cera\u201d device is now listed both ontop of sdc and \u201cera-meta\u201d. This is no error, it is perfectly normal and just how dm-era works. The \u201cera\u201d device shown ontop of \u201cera-meta\u201d is simply an indicator that the metadata is stored there. The size of this metadata area is not adjusted by the dm-era module, which is why we needed to determine it manually beforehand and provide a sufficiently sized partition; dm-era simply writes there and errors out when the device is full.<\/p>\n<h3>\u201cera-access\u201d \u2013 metadata access layer<\/h3>\n<p>Due to the nature of the dm-era target, we can\u2019t directly access the live metadata on \u201cera-meta\u201d but need to put another identically sized mapping ontop of it, which we will simply call \u201cera-access\u201d. We use the same linear mapping method and metadata size as before (run as root):<\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup create era-access --table \"0 256 linear \/dev\/mapper\/era-meta 0\" <\/code><\/pre>\n<p>We have now reached our final setup that represents the initial illustration:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ lsblk\nNAME                   MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT\n...\nsdb                      8:16   0  256M  0 disk \n`-era-meta             252:2    0  128K  0 dm   \n|-era                252:3    0  256M  0 dm   \n`-era-access         252:4    0  128K  0 dm   \nsdc                      8:32   0  256M  0 disk \n`-era                  252:3    0  256M  0 dm<\/code><\/pre>\n<h3>Comparison to Rackcorp\u2019s guide<\/h3>\n<p>This is also where Rackcorp\u2019s blog entry [2] contains unintended pitfalls\/mistakes. First, they presumably create the era device with the size of the metadata device not the origin device because they most likely copy\/pasted the wrong variable calculation above it.<br \/>\nSecond, they specify 1048576 as the block size parameter of dm-era and declare it as a 1 MB granularity, which seems wrong since those are still 512 byte sectors and would actually result in a 512 MB granularity. Remember that everything device mapper handles is specified in physical (512 byte) sectors!<\/p>\n<h2 id=\"Usingtheeradevice\">Using the era device<\/h2>\n<h3>Relationship between era device and origin device<\/h3>\n<p>What many documentations or guides fail to mention is the relation between the dm-era device and the origin device. In short terms, simply use the created era device instead of the origin device. Simple as that. The era device is a plain mapping ontop of the origin device. We can simply verify that by using the above mentioned setup.<br \/>\nHere we simply look at the start of sdc on byte level:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ head \/dev\/sdc | od -x\n0000000 0000 0000 0000 0000 0000 0000 0000 0000<\/code><\/pre>\n<p>Everything is zero\/empty as our virtual hard drive has just been created and is not formatted yet.<br \/>\nNow we try to format sdc with ext4:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ mkfs.ext4 \/dev\/sdc\nmke2fs 1.42.13 (17-May-2015)\n\/dev\/sdc is apparently in use by the system; will not make a filesystem here!<\/code><\/pre>\n<p>This doesn\u2019t work since the usage of dm-era makes the underlying block device read-only. This is perfectly normal and required for dm-era to work correctly.<br \/>\nInstead we now format the era device:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ mkfs.ext4 \/dev\/mapper\/era\n[...]\nWriting superblocks and filesystem accounting information: done<\/code><\/pre>\n<p>This time around it works.<br \/>\nTo prove this actually ended up on sdc physically, we compare both on byte level:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant@alice:~$ head \/dev\/sdc | od -x | head\n0000000 0000 0000 0000 0000 0000 0000 0000 0000\n*\n1440002000 0000 0001 0000 0004 3333 0000 b7a1 0003\n1440002020 fff5 0000 0001 0000 0000 0000 0000 0000\n1440002040 2000 0000 2000 0000 0800 0000 0000 0000\n1440002060 8167 5807 0000 ffff ef53 0000 0001 0000\n1440002100 8167 5807 0000 0000 0000 0000 0001 0000\n1440002120 0000 0000 000b 0000 0080 0019 003c 0000\n1440002140 0242 0000 007b 0000 3677 e0fa 0ec4 8948\n1440002160 d49a 947e 501a 3dab 0000 0000 0000 0000\nvagrant@alice:~$ head \/dev\/mapper\/era | od -x | head\n0000000 0000 0000 0000 0000 0000 0000 0000 0000\n*\n0002000 0000 0001 0000 0004 3333 0000 b7a1 0003\n0002020 fff5 0000 0001 0000 0000 0000 0000 0000\n0002040 2000 0000 2000 0000 0800 0000 0000 0000\n0002060 8167 5807 0000 ffff ef53 0001 0001 0000\n0002100 8167 5807 0000 0000 0000 0000 0001 0000\n0002120 0000 0000 000b 0000 0080 0000 003c 0000\n0002140 0242 0000 007b 0000 3677 e0fa 0ec4 8948\n0002160 d49a 947e 501a 3dab 0000 0000 0000 0000<\/code><\/pre>\n<p>Both show the same content. The era device is basically nothing but a linear mapping to the underlying block device but additionally keeps track of changed blocks as a bonus feature.<br \/>\nIn conclusion, we can handle the era device as just another block device, e.g. mount it:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>sudo mkdir \/media\/sdc-data\nsudo mount \/dev\/mapper\/era \/media\/sdc-data<\/code><\/pre>\n<p>Now that we clarified the relation between the era device and its origin device, it is time to look at the actual interesting feature: the metadata and retrieval of changed blocks.<\/p>\n<h3>Using the dm-era metadata<\/h3>\n<p>Fortunately, device mapper already provides you with tools for handling the metadata device, so you don\u2019t have to poke around on byte level there. On Debian-based systems (e.g. Ubuntu) they are most likely part of a package called thin-provisioning-tools, which you need to install manually first.<br \/>\nIn particular we\u2019re interested in two tools: era_dump and era_invalidate. Both allow you to examine the current metadata in one way or another:<\/p>\n<p>\u2022 era_dump will provide you with a XML-formatted list of blocks of the origin device and the corresponding era which they were last updated at; additionally it informs you about the current era and chosen granularity<br \/>\n\u2022 era_invalidate takes an era number as parameter and provides you with a XML-formatted list of all blocks that have been updated since the given era<br \/>\nTo make use of aformentioned commands, you have to take a snapshot of the metadata. Luckily, this is already part of the dm-era module and device mapper provides predefined dmsetup messages for this:<br \/>\nTaking and dropping a snapshot (needs to be run as root!):<\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup message era 0 take_metadata_snap<\/code><\/pre>\n<pre><code>dmsetup message era 0 drop_metadata_snap<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The second argument to <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">dmsetup<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> (<\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">era<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> in this case) is the name of the era block device as created before. The third argument is always zero for those actions. Whenever you are about to use one of the aformentioned commands to examine the metadata, take a snapshot and drop it as soon as you have parsed the output of the command.<\/span><\/p>\n<h3><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Era metadata handling example<\/span><\/h3>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">As basis for our following usage example we take the setup which we created before up to the point where we have already formatted our era device with ext4. For reference, with our exemplary Vagrantfile shown at the beginning, this includes the following sequence of commands:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>vagrant up\nvagrant ssh\n# become root\nsudo -i\napt-get install -y thin-provisioning-tools\ndmsetup create era-meta --table \"0 256 linear \/dev\/sdb 0\" \ndmsetup create era --table \"0 524288 era \/dev\/mapper\/era-meta \/dev\/sdc 4096\" \ndmsetup create era-access --table \"0 256 linear \/dev\/mapper\/era-meta 0\"\nmkfs.ext4 \/dev\/mapper\/era<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">First let\u2019s take a snapshot of the metadata:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup message era 0 take_metadata_snap<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Now let\u2019s dump our metadata:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>root@alice:~# era_dump \/dev\/mapper\/era-access\n&lt;superblock uuid=\"\" block_size=\"4096\" nr_blocks=\"128\" current_era=\"2\"&gt;\n&lt;writeset era=\"1\" nr_bits=\"128\"&gt;\n&lt;bit block=\"0\" value=\"true\"\/&gt;\n&lt;bit block=\"1\" value=\"false\"\/&gt;\n&lt;bit block=\"2\" value=\"true\"\/&gt;\n...\n&lt;bit block=\"125\" value=\"false\"\/&gt;\n&lt;bit block=\"126\" value=\"false\"\/&gt;\n&lt;bit block=\"127\" value=\"true\"\/&gt;\n&lt;\/writeset&gt;\n&lt;era_array&gt;\n&lt;era block=\"0\" era=\"0\"\/&gt;\n&lt;era block=\"1\" era=\"0\"\/&gt;\n&lt;era block=\"2\" era=\"0\"\/&gt;\n...\n&lt;era block=\"125\" era=\"0\"\/&gt;\n&lt;era block=\"126\" era=\"0\"\/&gt;\n&lt;era block=\"127\" era=\"0\"\/&gt;\n&lt;\/era_array&gt;\n&lt;\/superblock&gt;<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Here we get a list of 128 blocks where each block is 4096 sectors in size (granularity), thus 128 * 4096 * 512 bytes = 256 MB in total, which is exactly the size of our origin device. The important part of the output is the <code>era_array<\/code> that maps the blocks to the era in which they were last updated in. Unfortunately no information on the <\/span><code>writeset<\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> was available and Rackcorp [2] didn\u2019t have a clue what it stands for either. I will discuss that in a bit.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Also we see that we are currently at era 2 (era 1 seems to be the initial one). Each time you take a snapshot, you most likely end up increasing the era counter in the process. However, the official docs [1] state that this isn\u2019t guaranteed, so you should always check out the <\/span><code>current_era<\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> value yourself.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\"><br \/>\nAnother method to examine the current era count is to parse the status output of the device mapper target:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>root@alice:~# dmsetup status era\n<code>0 524288 era 8 12\/32 2 9<\/code><\/code><\/pre>\n<p>The second to last digit of this output is the current era. The main difference of the status command is, that you can use it without taking a snapshot.<\/p>\n<p>In the example above we get all zeroes for the blocks which means they haven\u2019t been changed yet. But is this really the case? Didn\u2019t we format the era device with ext4? Surely that should have changed some blocks. Well, actually it did. And this is where the mysterious writeset array comes into play.<\/p>\n<p>For now, let\u2019s drop our current snapshot and take a new one:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup message era 0 drop_metadata_snap\ndmsetup message era 0 take_metadata_snap<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Let\u2019s look at the dump again:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>&lt;pre&gt;&lt;code&gt;root@alice:~# era_dump \/dev\/mapper\/era-access\n&lt;superblock uuid=\"\" block_size=\"4096\" nr_blocks=\"128\" current_era=\"3\"&gt;\n&lt;writeset era=\"2\" nr_bits=\"128\"&gt;\n&lt;bit block=\"0\" value=\"false\"\/&gt;\n&lt;bit block=\"1\" value=\"false\"\/&gt;\n&lt;bit block=\"2\" value=\"false\"\/&gt;\n...\n&lt;bit block=\"125\" value=\"false\"\/&gt;\n&lt;bit block=\"126\" value=\"false\"\/&gt;\n&lt;bit block=\"127\" value=\"false\"\/&gt;\n&lt;\/writeset&gt;\n&lt;era_array&gt;\n&lt;era block=\"0\" era=\"1\"\/&gt;\n&lt;era block=\"1\" era=\"0\"\/&gt;\n&lt;era block=\"2\" era=\"1\"\/&gt;\n...\n&lt;era block=\"125\" era=\"0\"\/&gt;\n&lt;era block=\"126\" era=\"0\"\/&gt;\n&lt;era block=\"127\" era=\"1\"\/&gt;\n&lt;\/era_array&gt;\n&lt;\/superblock&gt;&lt;\/code&gt;&lt;\/pre&gt;<\/code><\/pre>\n<p>We have now advanced to the next era, which is 3. Also we now indeed see blocks that changed in the first era listed. When we compare the current era_array with the writeset of the previous dump, it becomes obvious that wherever the writeset listed a true before, we now have an era identifier of 1 in the era_array.<\/p>\n<p>Taking a close look at the writeset of the previous dump, it actually specifies writeset era=&#8220;2&#8243;. This means supposedly that this set of era values are still to be written in the specified era but contain changed blocks from some previous era. The purpose of writeset is not documented anywhere, but from the observations it\u2019s safe to assume that it kind of represents some caching or buffer swapping mechanism within dm-era. After all, this is essentially just a dump of the metadata, except for the XML-format it may still represent unedited raw data which in turn may or may not require special care in order to interpret correctly.<br \/>\nIn conclusion, when we reach the next era and examine the era_dump output, we can\u2019t just trust the era_array if the writeset contains true entries, at least if we want the changed blocks of the directly preceding era. This reduces the usefulness of era_dump for live block tracking, especially in terms of performance when parsing and computing its output.<\/p>\n<p>Luckily, era_dump is not the only tool, the thin-provisioning-tools package provides us with. There\u2019s also era_invalidate which is a much better choice if you\u2019re just after the changed blocks. Basically era_invalidate requires you to specify an era using the &#8211;written-since flag and will return a collection of blocks that have been changed since that era up to the current<\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Just imagine a timeline with steadily increasing eras:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>|0|--#--|1|--#--|2|--#--|3|--#--|4|--#--&gt;\n|&nbsp;&nbsp; ^&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ^&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ^\n'-(written since era 2)<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Inbetween the eras, block changes may happen (marked with the hash <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">#<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">). When you specify the <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">--written-since<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> era value, it will list a summary of all blocks that have got changed since that era, i.e. when following the timeline to the right.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Back to our example; we can get the list of the blocks changed during the ext4 formatting operation simply via:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>&lt;pre&gt;&lt;code&gt;root@alice:~# era_invalidate --written-since 1 \/dev\/mapper\/era-access\n&lt;blocks&gt;\n&lt;block block=\"0\"\/&gt;\n&lt;block block=\"2\"\/&gt;\n&lt;block block=\"4\"\/&gt;\n&lt;block block=\"12\"\/&gt;\n&lt;block block=\"20\"\/&gt;\n&lt;block block=\"28\"\/&gt;\n&lt;block block=\"36\"\/&gt;\n&lt;range begin=\"56\" end = \"61\"\/&gt;\n&lt;block block=\"64\"\/&gt;\n&lt;block block=\"100\"\/&gt;\n&lt;block block=\"108\"\/&gt;\n&lt;block block=\"127\"\/&gt;\n&lt;\/blocks&gt;&lt;\/code&gt;&lt;\/pre&gt;<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Now let\u2019s drop our snapshot:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup message era 0 drop_metadata_snap<\/code><\/pre>\n<p>We can use dd to write some random data at a specific part of the block device:<\/p>\n<pre>dd if=\/dev\/urandom of=\/dev\/mapper\/era bs=1M seek=60 count=40<\/pre>\n<p>This writes exactly 40 MB of random data starting at the 60th 1 MB block on our era device.<br \/>\nLet\u2019s have a look at the era_invalidate output again:<\/p>\n<p>&nbsp;<\/p>\n<pre><code>root@alice:~# dmsetup message era 0 drop_metadata_snap\nroot@alice:~# dmsetup message era 0 take_metadata_snap\nroot@alice:~# era_invalidate --written-since 1 \/dev\/mapper\/era-access\n&lt;blocks&gt;\n&lt;block block=\"0\"\/&gt;\n&lt;block block=\"2\"\/&gt;\n&lt;block block=\"4\"\/&gt;\n&lt;block block=\"12\"\/&gt;\n&lt;block block=\"20\"\/&gt;\n&lt;block block=\"28\"\/&gt;\n&lt;range begin=\"30\" end = \"50\"\/&gt;\n&lt;range begin=\"56\" end = \"61\"\/&gt;\n&lt;block block=\"64\"\/&gt;\n&lt;block block=\"100\"\/&gt;\n&lt;block block=\"108\"\/&gt;\n&lt;block block=\"127\"\/&gt;\n&lt;\/blocks&gt;<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">In comparison to the previous output, this now lists blocks ranging from 30 to 50 instead of only block 36. This is exactly where our data from the <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">dd<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> command ended up. Remember that we chose a dm-era granularity of 4096 sectors and each sector being 512 bytes, this yields 2 MB per block \u2013 which is why 40 MB of random data starting at 60 (as in the <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">dd<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> command) now end up as 20 blocks starting at 30.<br \/>\nSince we didn\u2019t change the<\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">--written-since<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> parameter, it also additionally lists the changes done in era 1.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Now let\u2019s only list the changes done since the previous era. First we need to determine the era we are in now:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>root@alice:~# dmsetup status era\n0 524288 era 8 12\/32 4 7<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Since we\u2019re in era 4 now (second to last digit), let\u2019s list all changes since era 3:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>root@alice:~# era_invalidate --written-since 3 \/dev\/mapper\/era-access\n&lt;blocks&gt;&lt;range begin=\"30\" end = \"50\"\/&gt;\n&lt;\/blocks&gt;<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">And this is exactly what has been changed during the <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">dd<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> command on block level.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Another nice feature of <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">era_invalidate<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> is that it automatically merges sequentially connected blocks into ranges in its output which can be used for sequential read operations instead of reading all blocks individually, vastly improving read performance.<\/span><\/p>\n<h2 id=\"Conclusiones\">Conclusiones<\/h2>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Using a sample setup based on a VM and two virtual hard drives, I demonstrated the setup and usage of the dm-era device mapper module to track changes of a block device on block level.<br \/>\nAfter we\u2019ve now examined every part of the proposed dm-era setup in an extensive fashion, the following paragraphs serve as a summary of the essential steps to be taken.<\/span><\/p>\n<h3><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Minimal setup<\/span><\/h3>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The following is a summary of the minimal steps for the proposed dm-era setup, parameterized with bash variables:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>dmsetup create $META_DEV_NAME --table \"0 $META_BLOCKSIZE linear \/dev\/sdb $META_OFFSET\"\ndmsetup create $ERA_DEV_NAME --table \"0 $ORIGIN_BLOCKSIZE era \/dev\/mapper\/$META_DEV_NAME $ORIGIN_DEV $GRANULARITY\" \ndmsetup create $ERA_ACCESS_NAME --table \"0 $META_BLOCKSIZE linear \/dev\/mapper\/$META_DEV_NAME 0\" <\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">These three commands have to be used for the initial setup as well as after any subsequent reboot of the machine, since the device mapper structure created is not persistent.<\/span><\/p>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">For calculating the value of <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">META_BLOCKSIZE<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">, first calculate the byte size required. For a granularity of 4096, you may use the formula which I determined earlier:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code>metadata_size = round( (2.5E-6 * origin_size + 128) \/ 4 ) * 4<\/code><\/pre>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">This results in KB, so you simply need to multiply it with 1024 and then divide by 512 to get the amount of sectors as input for device mapper (as <\/span><code><span style=\"font-size: 11.0pt; font-family: Montserrat;\">META_BLOCKSIZE<\/span><\/code><span style=\"font-size: 11.0pt; font-family: Montserrat;\"> above).<\/span><\/p>\n<h3><span style=\"font-size: 11.0pt; font-family: Montserrat;\">Replication routine<\/span><\/h3>\n<p><span style=\"font-size: 11.0pt; font-family: Montserrat;\">The following command sequence may serve as a template for creating a block tracking loop for replication mechanism purposes:<\/span><\/p>\n<p>&nbsp;<\/p>\n<pre><code># take a metadata snapshot\ndmsetup message $ERA_DEV_NAME 0 take_metadata_snap\n# parse $ERA_NUM by parsing the second to last digit of:\ndmsetup status $ERA_DEV_NAME\nERA_PREV=$(( ${ERA_NUM}-1 ))\n# parse the list of changes blocks from:\nera_invalidate --written-since $ERA_PREV \/dev\/mapper\/$ERA_ACCESS_NAME\n# drop metadata snapshot\ndmsetup message $ERA_DEV_NAME 0 drop_metadata_snap\n# (replicate the changed blocks according to the 'era_invalidate' output)\n# (repeat)<\/code><\/pre>\n<h3>Important things to remember<\/h3>\n<p>The following list is a short summary about the most important findings and possible pitfalls to look out for:<\/p>\n<ul>\n<li>using one physical block device for both era origin and metadata device might be possible using LVM but <strong>is not<\/strong> possible with pure device mapper, as device mapper doesn\u2019t allow it [4]!<\/li>\n<li>always choose the era device the same size as your origin device, don\u2019t get it irritated by it being listed ontop of your metadata device in full size<\/li>\n<li>do not try to use your origin device directly, always use the created era device within \/dev\/mapper\/ instead for read &amp; write access (this includes reading blocks for replication purposes!)<\/li>\n<li>do not try to access the metadata device directly, create an identically sized linear mapping ontop of it for access (e.g. for tools like era_dump or era_invalidate)<\/li>\n<li>when using the metadata tools, always take a metadata snapshot before and correctly drop it afterwards<\/li>\n<li>prefer era_invalidate over era_dump when tracking changed blocks, because the latter may be difficult to parse because of the additional writeset that has to be taken into account<\/li>\n<li>always keep in mind that device mapper is working on sector level, any block sizes specified have to be multiplied by 512 bytes if you want to know the actual physical byte size!<\/li>\n<li>keep in mind that the device mapper structure applied to the physical block devices is temporary until reboot, it is necessary use the exact same dmsetup commands as initally to recreate the mapping after power-up<\/li>\n<\/ul>\n<h3>Limitations and issue regarding reboots<\/h3>\n<p>Keep in mind that the dm-era implementation is still considered an experimental feature of the Linux kernel. Judging from the very sparse documentation and the small number of mentions on the net, it isn\u2019t widely used either. So I suspect it\u2019s neither extensively tested nor is it suitable for productive use.<\/p>\n<p>During my testing I also ran into a rather aggravating issue: the metadata doesn\u2019t survive reboots, although the \u201cResilience\u201d section in the official docs [1] implies otherwise. Even when reapplying the same mappings after powering up the machine and thus restoring the same block device setup as before the shutdown, the era tools report the metadata being broken on subsequent usage attempts.<\/p>\n<p>A quick fix is to zero out the sectors of the metadata device where the metadata target was located before applying the metadata and era device mappings again, which essentially leads to a full reset of the era history. For replication attempts this means there is no way to trace back any unsynced blocks from before the shutdown. A full resync in conjunction with era snapshotting could circumvent this until the replication has caught up again, albeit very costly.<\/p>\n<p>However, I got confirmation on the dm-devel mailing list that this is indeed unintended behavior and a patch [5] is already underway to fix this. Judging from the short tests I did with this kernel patch it does seem to fix this issue.<\/p>\n<p>[1] <a href=\"https:\/\/www.kernel.org\/doc\/Documentation\/device-mapper\/era.txt\">https:\/\/www.kernel.org\/doc\/Documentation\/device-mapper\/era.txt<\/a><br \/>\n[2] <a href=\"http:\/\/blog.rackcorp.com\/2016\/03\/dm-era-device-for-backups\/\">http:\/\/blog.rackcorp.com\/2016\/03\/dm-era-device-for-backups\/<\/a><br \/>\n[3] <a href=\"https:\/\/wiki.gentoo.org\/wiki\/Device-mapper#Era\">https:\/\/wiki.gentoo.org\/wiki\/Device-mapper#Era<\/a><br \/>\n[4] <a href=\"https:\/\/www.redhat.com\/archives\/dm-devel\/2014-September\/msg00168.html\">https:\/\/www.redhat.com\/archives\/dm-devel\/2014-September\/msg00168.html<\/a><br \/>\n[5] <a href=\"https:\/\/www.redhat.com\/archives\/dm-devel\/2017-April\/msg00138.html\">https:\/\/www.redhat.com\/archives\/dm-devel\/2017-April\/msg00138.html<\/a><\/p>\n<h2 id=\"Acknowledgments\">Acknowledgments<\/h2>\n<p>This work has been funded by the fast realtime project.<\/p>\n<p><strong><em>fast<\/em><\/strong><em> realtime<\/em> is basis project in the <a href=\"http:\/\/de.fast-zwanzig20.de\/fast-komplett\/\">project <em><strong>fast<\/strong><\/em><\/a><em><sup>[6]<\/sup><\/em> (fast actuators, sensors and transceivers). <em><strong>fast<\/strong><\/em> started in 2013 and is being funded within the BMBF programme \u201eZwanzig20 \u2013 Partnership for Innovation\u201c, which is dedicated to the future related topic of innovative realtime systems. In total, the consortium counts 80 partners.<\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" class=\" wp-image-2234\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-05.png\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"337\" height=\"174\"><\/p>\n<figure id=\"attachment_2235\" aria-describedby=\"caption-attachment-2235\" style=\"width: 300px\" class=\"wp-caption alignnone\"><img loading=\"lazy\" decoding=\"async\" class=\"size-full wp-image-2235\" src=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2023\/01\/2017-04-24-Blog-Block-level-data-tracking-06.jpg\" alt=\"Cloud and Heat | Blog | Block Level Data Tracking | Green Computing | Edge Cloud\" width=\"300\" height=\"221\"><figcaption id=\"caption-attachment-2235\" class=\"wp-caption-text\"><strong>Links<\/strong><\/figcaption><\/figure>\n<p><sup>[1]<\/sup> <a href=\"https:\/\/www.kernel.org\/doc\/Documentation\/device-mapper\/era.txt\">https:\/\/www.kernel.org\/doc\/Documentation\/device-mapper\/era.txt<\/a><br \/>\n<sup>[2]<\/sup> <a href=\"http:\/\/blog.rackcorp.com\/2016\/03\/dm-era-device-for-backups\/\">http:\/\/blog.rackcorp.com\/2016\/03\/dm-era-device-for-backups\/<\/a><br \/>\n<sup>[3]<\/sup> <a href=\"https:\/\/wiki.gentoo.org\/wiki\/Device-mapper#Era\">https:\/\/wiki.gentoo.org\/wiki\/Device-mapper#Era<\/a><br \/>\n<sup>[4]<\/sup> <a href=\"https:\/\/www.redhat.com\/archives\/dm-devel\/2014-September\/msg00168.html\">https:\/\/www.redhat.com\/archives\/dm-devel\/2014-September\/msg00168.html<\/a><br \/>\n<sup>[5]<\/sup> <a href=\"https:\/\/www.redhat.com\/archives\/dm-devel\/2017-April\/msg00138.html\">https:\/\/www.redhat.com\/archives\/dm-devel\/2017-April\/msg00138.html<\/a><br \/>\n<sup>[6]<\/sup> <a href=\"http:\/\/de.fast-zwanzig20.de\/fast-komplett\/\">http:\/\/de.fast-zwanzig20.de\/fast-komplett\/<\/a><\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Step by step tutorial for setting up the device mapper mappings.<\/p>","protected":false},"author":2,"featured_media":6046,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"_relevanssi_hide_post":"","_relevanssi_hide_content":"","_relevanssi_pin_for_all":"","_relevanssi_pin_keywords":"","_relevanssi_unpin_keywords":"","_relevanssi_related_keywords":"","_relevanssi_related_include_ids":"","_relevanssi_related_exclude_ids":"","_relevanssi_related_no_append":"","_relevanssi_related_not_related":"","_relevanssi_related_posts":"","_relevanssi_noindex_reason":"","inline_featured_image":false,"footnotes":""},"categories":[83,1],"tags":[],"class_list":["post-5236","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-cloud-services","category-iaas"],"acf":[],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.0 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>Cloud&amp;Heat | Block-Level data tracking using device mapper\u2019s dm-era<\/title>\n<meta name=\"description\" content=\"Cloud&amp;Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.cloudandheat.com\/en\/block-level-data-tracking-using-davice-mappers-dm-era\/\" \/>\n<meta property=\"og:locale\" content=\"en_GB\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Cloud&amp;Heat | Block-Level data tracking using device mapper\u2019s dm-era\" \/>\n<meta property=\"og:description\" content=\"Cloud&amp;Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.cloudandheat.com\/en\/block-level-data-tracking-using-davice-mappers-dm-era\/\" \/>\n<meta property=\"og:site_name\" content=\"Cloud &amp; Heat\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/CloudandHeat\" \/>\n<meta property=\"article:published_time\" content=\"2017-04-24T07:17:40+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2023-03-08T15:04:32+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png\" \/>\n\t<meta property=\"og:image:width\" content=\"2292\" \/>\n\t<meta property=\"og:image:height\" content=\"1201\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"Clemens M\u00fcller\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@cloudandheat\" \/>\n<meta name=\"twitter:site\" content=\"@cloudandheat\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"Clemens M\u00fcller\" \/>\n\t<meta name=\"twitter:label2\" content=\"Estimated reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"29 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#article\",\"isPartOf\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/\"},\"author\":{\"name\":\"Clemens M\u00fcller\",\"@id\":\"https:\/\/www.cloudandheat.com\/#\/schema\/person\/ba09b0c184d05469ca875d2cb5ba730a\"},\"headline\":\"Block-level data tracking using device mapper\u2019s dm-era\",\"datePublished\":\"2017-04-24T07:17:40+00:00\",\"dateModified\":\"2023-03-08T15:04:32+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/\"},\"wordCount\":4695,\"publisher\":{\"@id\":\"https:\/\/www.cloudandheat.com\/#organization\"},\"image\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png\",\"articleSection\":[\"Cloud Services\",\"IaaS\"],\"inLanguage\":\"en-GB\"},{\"@type\":\"WebPage\",\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/\",\"url\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/\",\"name\":\"Cloud&Heat | Block-Level data tracking using device mapper\u2019s dm-era\",\"isPartOf\":{\"@id\":\"https:\/\/www.cloudandheat.com\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage\"},\"image\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png\",\"datePublished\":\"2017-04-24T07:17:40+00:00\",\"dateModified\":\"2023-03-08T15:04:32+00:00\",\"description\":\"Cloud&Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking\",\"breadcrumb\":{\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#breadcrumb\"},\"inLanguage\":\"en-GB\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-GB\",\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage\",\"url\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png\",\"contentUrl\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png\",\"width\":2292,\"height\":1201},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Startseite\",\"item\":\"https:\/\/www.cloudandheat.com\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Block-level data tracking using device mapper\u2019s dm-era\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/www.cloudandheat.com\/#website\",\"url\":\"https:\/\/www.cloudandheat.com\/\",\"name\":\"Cloud & Heat Technolgies GmbH\",\"description\":\"Cloud-Service- und Cloud-Technologie-Provider\",\"publisher\":{\"@id\":\"https:\/\/www.cloudandheat.com\/#organization\"},\"alternateName\":\"Cloud and Heat Technologies GmbH\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/www.cloudandheat.com\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-GB\"},{\"@type\":\"Organization\",\"@id\":\"https:\/\/www.cloudandheat.com\/#organization\",\"name\":\"Cloud&Heat Technologies GmbH\",\"url\":\"https:\/\/www.cloudandheat.com\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-GB\",\"@id\":\"https:\/\/www.cloudandheat.com\/#\/schema\/logo\/image\/\",\"url\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2022\/08\/logo.svg\",\"contentUrl\":\"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2022\/08\/logo.svg\",\"width\":907,\"height\":1782,\"caption\":\"Cloud&Heat Technologies GmbH\"},\"image\":{\"@id\":\"https:\/\/www.cloudandheat.com\/#\/schema\/logo\/image\/\"},\"sameAs\":[\"https:\/\/www.facebook.com\/CloudandHeat\",\"https:\/\/x.com\/cloudandheat\"]},{\"@type\":\"Person\",\"@id\":\"https:\/\/www.cloudandheat.com\/#\/schema\/person\/ba09b0c184d05469ca875d2cb5ba730a\",\"name\":\"Clemens M\u00fcller\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-GB\",\"@id\":\"https:\/\/www.cloudandheat.com\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/secure.gravatar.com\/avatar\/350f97f507a0c231669ebf507b516e705ead54569fde6f8537dee0acc251ee2d?s=96&d=mm&r=g\",\"contentUrl\":\"https:\/\/secure.gravatar.com\/avatar\/350f97f507a0c231669ebf507b516e705ead54569fde6f8537dee0acc251ee2d?s=96&d=mm&r=g\",\"caption\":\"Clemens M\u00fcller\"}}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Cloud&amp;Heat | Block-Level data tracking using device mapper's dm-era","description":"Cloud&amp;Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.cloudandheat.com\/en\/block-level-data-tracking-using-davice-mappers-dm-era\/","og_locale":"en_GB","og_type":"article","og_title":"Cloud&Heat | Block-Level data tracking using device mapper\u2019s dm-era","og_description":"Cloud&Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking","og_url":"https:\/\/www.cloudandheat.com\/en\/block-level-data-tracking-using-davice-mappers-dm-era\/","og_site_name":"Cloud &amp; Heat","article_publisher":"https:\/\/www.facebook.com\/CloudandHeat","article_published_time":"2017-04-24T07:17:40+00:00","article_modified_time":"2023-03-08T15:04:32+00:00","og_image":[{"width":2292,"height":1201,"url":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png","type":"image\/png"}],"author":"Clemens M\u00fcller","twitter_card":"summary_large_image","twitter_creator":"@cloudandheat","twitter_site":"@cloudandheat","twitter_misc":{"Written by":"Clemens M\u00fcller","Estimated reading time":"29 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#article","isPartOf":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/"},"author":{"name":"Clemens M\u00fcller","@id":"https:\/\/www.cloudandheat.com\/#\/schema\/person\/ba09b0c184d05469ca875d2cb5ba730a"},"headline":"Block-level data tracking using device mapper\u2019s dm-era","datePublished":"2017-04-24T07:17:40+00:00","dateModified":"2023-03-08T15:04:32+00:00","mainEntityOfPage":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/"},"wordCount":4695,"publisher":{"@id":"https:\/\/www.cloudandheat.com\/#organization"},"image":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage"},"thumbnailUrl":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png","articleSection":["Cloud Services","IaaS"],"inLanguage":"en-GB"},{"@type":"WebPage","@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/","url":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/","name":"Cloud&amp;Heat | Block-Level data tracking using device mapper's dm-era","isPartOf":{"@id":"https:\/\/www.cloudandheat.com\/#website"},"primaryImageOfPage":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage"},"image":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage"},"thumbnailUrl":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png","datePublished":"2017-04-24T07:17:40+00:00","dateModified":"2023-03-08T15:04:32+00:00","description":"Cloud&amp;Heat Technologies makes sustainability and security the drivers of digital innovation. | Future of compute | Cloud Security | data tracking","breadcrumb":{"@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#breadcrumb"},"inLanguage":"en-GB","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/"]}]},{"@type":"ImageObject","inLanguage":"en-GB","@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#primaryimage","url":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png","contentUrl":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2016\/02\/2023-Cloud-and-Heat-Website-Blog-Vorlage-Headerbild.png","width":2292,"height":1201},{"@type":"BreadcrumbList","@id":"https:\/\/www.cloudandheat.com\/block-level-data-tracking-using-davice-mappers-dm-era\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Startseite","item":"https:\/\/www.cloudandheat.com\/"},{"@type":"ListItem","position":2,"name":"Block-level data tracking using device mapper\u2019s dm-era"}]},{"@type":"WebSite","@id":"https:\/\/www.cloudandheat.com\/#website","url":"https:\/\/www.cloudandheat.com\/","name":"Cloud &amp; Heat Technolgies GmbH","description":"Cloud service and cloud technology providers","publisher":{"@id":"https:\/\/www.cloudandheat.com\/#organization"},"alternateName":"Cloud and Heat Technologies GmbH","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.cloudandheat.com\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-GB"},{"@type":"Organization","@id":"https:\/\/www.cloudandheat.com\/#organization","name":"Cloud&amp;Heat Technologies GmbH","url":"https:\/\/www.cloudandheat.com\/","logo":{"@type":"ImageObject","inLanguage":"en-GB","@id":"https:\/\/www.cloudandheat.com\/#\/schema\/logo\/image\/","url":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2022\/08\/logo.svg","contentUrl":"https:\/\/www.cloudandheat.com\/wp-content\/uploads\/2022\/08\/logo.svg","width":907,"height":1782,"caption":"Cloud&Heat Technologies GmbH"},"image":{"@id":"https:\/\/www.cloudandheat.com\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/CloudandHeat","https:\/\/x.com\/cloudandheat"]},{"@type":"Person","@id":"https:\/\/www.cloudandheat.com\/#\/schema\/person\/ba09b0c184d05469ca875d2cb5ba730a","name":"Clemens M\u00fcller","image":{"@type":"ImageObject","inLanguage":"en-GB","@id":"https:\/\/www.cloudandheat.com\/#\/schema\/person\/image\/","url":"https:\/\/secure.gravatar.com\/avatar\/350f97f507a0c231669ebf507b516e705ead54569fde6f8537dee0acc251ee2d?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/350f97f507a0c231669ebf507b516e705ead54569fde6f8537dee0acc251ee2d?s=96&d=mm&r=g","caption":"Clemens M\u00fcller"}}]}},"_links":{"self":[{"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/posts\/5236","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/comments?post=5236"}],"version-history":[{"count":0,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/posts\/5236\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/media\/6046"}],"wp:attachment":[{"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/media?parent=5236"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/categories?post=5236"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.cloudandheat.com\/en\/wp-json\/wp\/v2\/tags?post=5236"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}