Filesystem: Don't store lock length of Infinity
Infinity is not JSON.stringifiable and will turn into null during state save and restore.
This commit is contained in:
parent
400ed64d54
commit
2bac2198e8
1 changed files with 33 additions and 19 deletions
|
|
@ -1745,6 +1745,24 @@ FSLockRegion.prototype.clone = function()
|
|||
return new_region;
|
||||
};
|
||||
|
||||
/**
|
||||
* Handle special interpretation of length of 0.
|
||||
* @return {number}
|
||||
*/
|
||||
FSLockRegion.prototype.get_length = function()
|
||||
{
|
||||
return this.length === 0 ? Infinity : this.length;
|
||||
};
|
||||
|
||||
/**
|
||||
* Handle special interpretation of length of 0.
|
||||
* @param {number} length
|
||||
*/
|
||||
FSLockRegion.prototype.set_length = function(length)
|
||||
{
|
||||
this.length = length === Infinity ? 0 : length;
|
||||
};
|
||||
|
||||
/**
|
||||
* @param {FSLockRegion} region
|
||||
* @return {boolean}
|
||||
|
|
@ -1754,8 +1772,8 @@ FSLockRegion.prototype.conflicts_with = function(region)
|
|||
if(this.proc_id === region.proc_id && this.client_id === region.client_id) return false;
|
||||
if(this.type === P9_LOCK_TYPE_UNLCK || region.type === P9_LOCK_TYPE_UNLCK) return false;
|
||||
if(this.type !== P9_LOCK_TYPE_WRLCK && region.type !== P9_LOCK_TYPE_WRLCK) return false;
|
||||
if(this.start + this.length <= region.start) return false;
|
||||
if(region.start + region.length <= this.start) return false;
|
||||
if(this.start + this.get_length() <= region.start) return false;
|
||||
if(region.start + region.get_length() <= this.start) return false;
|
||||
return true;
|
||||
};
|
||||
|
||||
|
|
@ -1776,7 +1794,7 @@ FSLockRegion.prototype.is_alike = function(region)
|
|||
*/
|
||||
FSLockRegion.prototype.may_merge_after = function(region)
|
||||
{
|
||||
return this.is_alike(region) && region.start + region.length === this.start;
|
||||
return this.is_alike(region) && region.start + region.get_length() === this.start;
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
@ -1799,8 +1817,7 @@ FS.prototype.DescribeLock = function(type, start, length, proc_id, client_id)
|
|||
const lock = new FSLockRegion();
|
||||
lock.type = type;
|
||||
lock.start = start;
|
||||
// Internally represent length of '0' as infinity.
|
||||
lock.length = length === 0 ? Infinity : length;
|
||||
lock.set_length(length);
|
||||
lock.proc_id = proc_id;
|
||||
lock.client_id = client_id;
|
||||
|
||||
|
|
@ -1826,10 +1843,7 @@ FS.prototype.GetLock = function(id, request)
|
|||
{
|
||||
if(request.conflicts_with(region))
|
||||
{
|
||||
const ret = region.clone();
|
||||
// Convert internal representation of '0' back.
|
||||
ret.length = ret.length === Infinity ? 0 : ret.length;
|
||||
return ret;
|
||||
return region.clone();
|
||||
}
|
||||
}
|
||||
return null;
|
||||
|
|
@ -1864,18 +1878,18 @@ FS.prototype.Lock = function(id, request, flags)
|
|||
{
|
||||
const region = inode.locks[i];
|
||||
|
||||
dbg_assert(region.length > 0,
|
||||
"Filesystem: Found non-positive lock region length: " + region.length);
|
||||
dbg_assert(region.get_length() > 0,
|
||||
"Filesystem: Found non-positive lock region length: " + region.get_length());
|
||||
dbg_assert(region.type === P9_LOCK_TYPE_RDLCK || region.type === P9_LOCK_TYPE_WRLCK,
|
||||
"Filesystem: Found invalid lock type: " + region.type);
|
||||
dbg_assert(!inode.locks[i-1] || inode.locks[i-1].start <= region.start,
|
||||
"Filesystem: Locks should be sorted by starting offset");
|
||||
|
||||
// Skip to requested region.
|
||||
if(region.start + region.length <= request.start) continue;
|
||||
if(region.start + region.get_length() <= request.start) continue;
|
||||
|
||||
// Check whether we've skipped past the requested region.
|
||||
if(request.start + request.length <= region.start) break;
|
||||
if(request.start + request.get_length() <= region.start) break;
|
||||
|
||||
// Skip over locks of different owners.
|
||||
if(region.proc_id !== request.proc_id || region.client_id !== request.client_id)
|
||||
|
|
@ -1887,9 +1901,9 @@ FS.prototype.Lock = function(id, request, flags)
|
|||
|
||||
// Pretend region would be split into parts 1 and 2.
|
||||
const start1 = region.start;
|
||||
const start2 = request.start + request.length;
|
||||
const start2 = request.start + request.get_length();
|
||||
const length1 = request.start - start1;
|
||||
const length2 = region.start + region.length - start2;
|
||||
const length2 = region.start + region.get_length() - start2;
|
||||
|
||||
if(length1 > 0 && length2 > 0 && region.type === request.type)
|
||||
{
|
||||
|
|
@ -1901,14 +1915,14 @@ FS.prototype.Lock = function(id, request, flags)
|
|||
if(length1 > 0)
|
||||
{
|
||||
// Shrink from right / first half of the split.
|
||||
region.length = length1;
|
||||
region.set_length(length1);
|
||||
}
|
||||
|
||||
if(length1 <= 0 && length2 > 0)
|
||||
{
|
||||
// Shrink from left.
|
||||
region.start = start2;
|
||||
region.length = length2;
|
||||
region.set_length(length2);
|
||||
}
|
||||
else if(length2 > 0)
|
||||
{
|
||||
|
|
@ -1942,7 +1956,7 @@ FS.prototype.Lock = function(id, request, flags)
|
|||
{
|
||||
if(new_region.may_merge_after(inode.locks[i]))
|
||||
{
|
||||
inode.locks[i].length += request.length;
|
||||
inode.locks[i].set_length(inode.locks[i].get_length() + request.get_length());
|
||||
new_region = inode.locks[i];
|
||||
has_merged = true;
|
||||
}
|
||||
|
|
@ -1962,7 +1976,7 @@ FS.prototype.Lock = function(id, request, flags)
|
|||
|
||||
if(inode.locks[i].may_merge_after(new_region))
|
||||
{
|
||||
new_region.length += inode.locks[i].length;
|
||||
new_region.set_length(new_region.get_length() + inode.locks[i].get_length());
|
||||
inode.locks.splice(i, 1);
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue