Interestingly this looks like an upstream bug as well. If for some
reason we are unable to get a zvols statistics, because perhaps the
zpool is hopelessly corrupt, we would trigger the VERIFY. This
commit adds the proper error handling just to propagate the error
back to user space. Now the user space tools still must handle this
properly but in the worst case the tool will crash or perhaps have
some missing output. That's far far better than crashing the host.
Closes#45
Several folks have now remarked that when the regression tests
fail they leave a mess behind. This was done intentionally at
the time to facilitate debugging the wreckage.
However, this also means that you may need to do some manual
cleanup such as removing the loopback devices before re-running
the tests. To simplify this proceedure I've added the '-c'
option to zconfig.sh which will attempt to cleanup the mess
from a previous test before starting.
This is somewhat dangerous because it must guess as to which
loopback devices you were using. But this risk is fairly minimal
because devices which are currently still is use can not be
cleaned up. And because only devices with 'zpool' in the name
are considered for removal. That said if your running parallel
copies of say zconfig.sh this may cause you some trouble.
Update the zconfig.sh test script to verify not only that volumes,
snapshots, and clones are created and removed properly. But also
verify that the partition information for each of these types of
devices is properly enumerated by the kernel.
Tests 4 and 5 now also create two partitions on the original volume
and these partitions are expected to also exist on the snapshot and
the clone. Correctness is verified after import/export, module
load/unload, dataset creation, and pool destruction.
Additionally, the code to create a partition table was refactored
in to a small helper function to simplify the test cases. And
finally all of the function variables were flagged 'local' to ensure
their scope is limited. This should have been done a while ago.
Partitions for a zvol device were not appearing in /dev/zvol/<pool>/
at module load time for a couple of reasons.
1) The Linux block layer expects a block device to have a non-zero
capacity during add_disk(). If the capacity is zero it does not
attempt to open the device which means we never trigger a partition
scan. The device capacity was just being set during the first open.
2) Because we expect to be adding a block device to the zvol_state_list
during zvol_create_minor() the zvol_state_lock() is held. This
can result in a deadlock in add_disk() when it attempts to open
the block device via zvol_open() which also takes this same lock.
To avoid this issue special handling has been added to zvol_open()
and zvol_release() to allow the mutex owner to enter these functions
without retaking the lock.
3) In __zvol_create_minor() the call to dmu_objset_disown() must occur
before the call to add_disk(). As mentioned above add_disk() results
in a call to zvol_open() which will attempt to call dmu_objset_own()
again on the objset. If the objset is already open it will fail
resulting in a failed open. This in turn means the kernel will be
unable to read the partition information from the device.