@@ -110,7 +110,10 @@ specifications do not need to bother implementing [=/file system entry=]'s
110
110
111
111
Issue(101): Make access check algorithms associated with a FileSystemHandle.
112
112
113
- Each [=/file system entry=] has an associated <dfn for="file system entry" id=entry-name>name</dfn> (a [=string=] ).
113
+ Each [=/file system entry=] has an associated <dfn for="file system entry" id=entry-name>name</dfn> (a [=string=] ),
114
+ a <dfn for="file system entry">lock</dfn> (a string that may exclusively be "`open`", "`taken-exclusive`" or "`taken-shared`")
115
+ and a <dfn for="file system entry" id=file-system-entry-shared-lock-count>lock count</dfn>
116
+ (a number representing the number of locks that are taken at a given point in time).
114
117
115
118
A <dfn>valid file name</dfn> is a [=string=] that is not an empty string, is not equal to "." or "..",
116
119
and does not contain '/' or any other character used as path separator on the underlying platform.
@@ -124,50 +127,83 @@ Issue: We should consider having further normative restrictions on file names th
124
127
never be allowed using this API, rather than leaving it entirely up to underlying file
125
128
systems.
126
129
127
- A <dfn export id=file>file entry</dfn> additionally consists of
128
- <dfn for="file entry" export>binary data</dfn> (a [=byte sequence=] ), a
129
- <dfn for="file entry">modification timestamp</dfn> (a number representing the number of milliseconds since the <a spec=FileAPI>Unix Epoch</a> ),
130
- a <dfn for="file entry">lock</dfn> (a string that may exclusively be "`open`", "`taken-exclusive`" or "`taken-shared`")
131
- and a <dfn for="file entry">shared lock count</dfn> (a number representing the number shared locks that are taken at a given point in time).
132
-
133
130
A user agent has an associated <dfn>file system queue</dfn> which is the
134
131
result of [=starting a new parallel queue=] . This queue is to be used for all
135
132
file system operations.
136
133
137
134
<div algorithm>
138
- To <dfn for="file entry/lock">take</dfn> a [=file entry/lock=] with a |value| of
139
- "`exclusive`" or "`shared`" on a given [=file entry=] |file|:
140
-
141
- 1. Let |lock| be the |file|'s [=file entry/lock=] .
142
- 1. Let |count| be the |file|'s [=file entry/shared lock count=] .
135
+ To <dfn for="file system entry" id=file-entry-lock-take>take a lock</dfn> with a |value| of
136
+ "`exclusive`" or "`shared`" on a given [=/file system entry=] |entry|:
137
+
138
+ 1. Let |lock| be the |entry|'s [=file system entry/lock=] .
139
+ 1. Let |count| be the |entry|'s [=file system entry/lock count=] .
140
+ 1. Let |ancestorLockStatus| be the result of [=file system entry/checking for an ancestor lock=] on |entry|.
141
+ 1. If |ancestorLockStatus| is "`taken`":
142
+ 1. Return "`failure`".
143
+ 1. If |entry| is a [=directory entry=] :
144
+ 1. Let |descendantLockStatus| be the result of [=file system entry/checking for a descendant lock=] on |entry|.
145
+ 1. If |descendantLockStatus| is "`taken`":
146
+ 1. Return "`failure`".
147
+ 1. If |value| is "`exclusive`" or |lock| is "`taken-exclusive`":
148
+ 1. Return "`failure`".
143
149
1. If |value| is "`exclusive`":
144
- 1. If |lock| is "`open`":
145
- 1. Set lock to "`taken-exclusive`".
146
- 1. Return "`success`".
147
- 1. If |value| is "`shared`":
148
- 1. If |lock| is "`open`":
149
- 1. Set |lock| to "`taken-shared`".
150
- 1. Set |count| to 1.
151
- 1. Return "`success`".
152
- 1. Otherwise, if |lock| is "`taken-shared`":
153
- 1. Increase |count| by 1.
154
- 1. Return "`success`".
155
- 1. Return "`failure`".
150
+ 1. [=Assert=] : |lock| is "`open`".
151
+ 1. [=Assert=] : |count| is 0.
152
+ 1. Set lock to "`taken-exclusive`".
153
+ 1. Otherwise:
154
+ 1. [=Assert=] : |lock| is not "`taken-exclusive`".
155
+ 1. Set lock to "`taken-shared`".
156
+ 1. Increase |count| by 1.
157
+ 1. Return "`success`".
156
158
157
159
Note: These steps have to be run on the [=file system queue=] .
158
160
159
161
</div>
160
162
161
163
<div algorithm>
162
- To <dfn for="file entry/lock">release</dfn> a [=file entry/lock=] on a given
163
- [=file entry=] |file|:
164
+ To <dfn for="file system entry">check for an ancestor lock</dfn> on a given
165
+ [=/file system entry=] |entry|:
166
+
167
+ 1. Let |parent| be the |entry|'s [=file system entry/parent=] .
168
+ 1. If |parent| is null:
169
+ 1. Return "`open`".
170
+ 1. Let |lock| be the |parent|'s [=file system entry/lock=] .
171
+ 1. If |lock| is not "`open`":
172
+ 1. Return "`taken`".
173
+ 1. Let |ancestorLockStatus| be the result of [=file system entry/checking for an ancestor lock=] on |parent|.
174
+ 1. Return |ancestorLockStatus|.
164
175
165
- 1. Let |lock| be the |file|'s associated [=file entry/lock=] .
166
- 1. Let |count| be the |file|'s [=file entry/shared lock count=] .
167
- 1. If |lock| is "`taken-shared`":
168
- 1. Decrease |count| by 1.
169
- 1. If |count| is 0, set |lock| to "`open`".
170
- 1. Otherwise, set |lock| to "`open`".
176
+ Note: These steps have to be run on the [=file system queue=] .
177
+
178
+ </div>
179
+
180
+ <div algorithm>
181
+ To <dfn for="file system entry">check for a descendant lock</dfn> on a given
182
+ [=directory entry=] |directory|:
183
+
184
+ 1. [=set/For each=] |child| of |directory|'s [=directory entry/children=] :
185
+ 1. Let |lock| be the |child|'s [=file system entry/lock=] .
186
+ 1. If |lock| is not "`open`":
187
+ 1. Return "`taken`".
188
+ 1. If |child| is a [=directory entry=] :
189
+ 1. Let |descendantLockStatus| be the result of [=file system entry/checking for a descendant lock=] on |child|.
190
+ 1. If |descendantLockStatus| is "`taken`":
191
+ 1. Return "`taken`".
192
+ 1. Return "`open`".
193
+
194
+ Note: These steps have to be run on the [=file system queue=] .
195
+
196
+ </div>
197
+
198
+ <div algorithm>
199
+ To <dfn for="file system entry/lock">release</dfn> a [=file system entry/lock=] on a given
200
+ [=/file system entry=] |entry|:
201
+
202
+ 1. Let |lock| be the |entry|'s associated [=file system entry/lock=] .
203
+ 1. [=Assert=] : |lock| is not "`open`".
204
+ 1. Let |count| be the |entry|'s [=file system entry/lock count=] .
205
+ 1. Decrease |count| by 1.
206
+ 1. If |count| is 0, set |lock| to "`open`".
171
207
172
208
Note: These steps have to be run on the [=file system queue=] .
173
209
@@ -176,6 +212,10 @@ Note: These steps have to be run on the [=file system queue=].
176
212
Note: Locks help prevent concurrent modifications to a file. A {{FileSystemWritableFileStream}}
177
213
requires a shared lock, while a {{FileSystemSyncAccessHandle}} requires an exclusive one.
178
214
215
+ A <dfn export id=file>file entry</dfn> additionally consists of
216
+ <dfn for="file entry" export>binary data</dfn> (a [=byte sequence=] ) and a
217
+ <dfn for="file entry">modification timestamp</dfn> (a number representing the number of milliseconds since the <a spec=FileAPI>Unix Epoch</a> ).
218
+
179
219
A <dfn export id=directory>directory entry</dfn> additionally consists of a [=/set=] of
180
220
<dfn for="directory entry">children</dfn> , which are themselves [=/file system entries=] .
181
221
Each member is either a [=/file entry=] or a [=/directory entry=] .
@@ -538,7 +578,7 @@ The <dfn method for=FileSystemFileHandle>getFile()</dfn> method steps are:
538
578
the temporary file starts out empty,
539
579
otherwise the existing file is first copied to this temporary file.
540
580
541
- Creating a {{FileSystemWritableFileStream}} [=file entry/lock/ take|takes a shared lock=] on the
581
+ Creating a {{FileSystemWritableFileStream}} [=file system entry/take a lock |takes a shared lock=] on the
542
582
[=file entry=] [=locate an entry|locatable=] with |fileHandle|'s [=FileSystemHandle/locator=] .
543
583
This prevents the creation of {{FileSystemSyncAccessHandle|FileSystemSyncAccessHandles}}
544
584
for the entry, until the stream is closed.
@@ -575,7 +615,7 @@ The <dfn method for=FileSystemFileHandle>createWritable(|options|)</dfn> method
575
615
|result| with a "{{NotFoundError}} " {{DOMException}} and abort these steps.
576
616
1. [=Assert=] : |entry| is a [=file entry=] .
577
617
578
- 1. Let |lockResult| be the result of [=file entry/lock/ take|taking a lock=]
618
+ 1. Let |lockResult| be the result of [=file system entry/take a lock |taking a lock=]
579
619
with "`shared`" on |entry|.
580
620
581
621
1. [=Queue a storage task=] with |global| to run these steps:
@@ -603,7 +643,7 @@ The <dfn method for=FileSystemFileHandle>createWritable(|options|)</dfn> method
603
643
[=file entry=] [=locate an entry|locatable=] by |fileHandle|'s [=FileSystemHandle/locator=] .
604
644
To ensure the changes are reflected in this file, the handle can be flushed.
605
645
606
- Creating a {{FileSystemSyncAccessHandle}} [=file entry/lock/ take|takes an exclusive lock=] on the
646
+ Creating a {{FileSystemSyncAccessHandle}} [=file system entry/take a lock |takes an exclusive lock=] on the
607
647
[=file entry=] [=locate an entry|locatable=] with |fileHandle|'s [=FileSystemHandle/locator=] .
608
648
This prevents the creation of further {{FileSystemSyncAccessHandle|FileSystemSyncAccessHandles}}
609
649
or {{FileSystemWritableFileStream|FileSystemWritableFileStreams}}
@@ -645,7 +685,7 @@ The <dfn method for=FileSystemFileHandle>createSyncAccessHandle()</dfn> method s
645
685
|result| with a "{{NotFoundError}} " {{DOMException}} and abort these steps.
646
686
1. [=Assert=] : |entry| is a [=file entry=] .
647
687
648
- 1. Let |lockResult| be the result of [=file entry/lock/ take|taking a lock=]
688
+ 1. Let |lockResult| be the result of [=file system entry/take a lock |taking a lock=]
649
689
with "`exclusive`" on |entry|.
650
690
651
691
1. [=Queue a storage task=] with |global| to run these steps:
@@ -1181,15 +1221,15 @@ given a [=file entry=] |file| in a [=/Realm=] |realm|:
1181
1221
file on disk being written to.
1182
1222
1183
1223
1. [=Enqueue the following steps=] to the [=file system queue=] :
1184
- 1. [=file entry/lock/release|Release the lock=] on
1224
+ 1. [=file system entry/lock/release|Release the lock=] on
1185
1225
|stream|'s [=FileSystemWritableFileStream/[[file]]=] .
1186
1226
1. [=Queue a storage task=] with |file|'s [=relevant global object=]
1187
1227
to [=/resolve=] |closeResult| with `undefined`.
1188
1228
1189
1229
1. Return |closeResult|.
1190
1230
1. Let |abortAlgorithm| be these steps:
1191
1231
1. [=enqueue steps|Enqueue this step=] to the [=file system queue=] :
1192
- 1. [=file entry/lock/release|Release the lock=] on
1232
+ 1. [=file system entry/lock/release|Release the lock=] on
1193
1233
|stream|'s [=FileSystemWritableFileStream/[[file]]=] .
1194
1234
1. Let |highWaterMark| be 1.
1195
1235
1. Let |sizeAlgorithm| be an algorithm that returns `1`.
@@ -1649,7 +1689,7 @@ The <dfn method for=FileSystemSyncAccessHandle>flush()</dfn> method steps are:
1649
1689
: |handle| . {{FileSystemSyncAccessHandle/close()}}
1650
1690
:: Closes the access handle or no-ops if the access handle is already closed.
1651
1691
This disables any further operations on it and
1652
- [=file entry/lock/release|releases the lock=] on the
1692
+ [=file system entry/lock/release|releases the lock=] on the
1653
1693
[=FileSystemSyncAccessHandle/[[file]]=] associated with |handle|.
1654
1694
</div>
1655
1695
@@ -1661,7 +1701,7 @@ The <dfn method for=FileSystemSyncAccessHandle>close()</dfn> method steps are:
1661
1701
1. Set |lockReleased| to false.
1662
1702
1. Let |file| be [=this=] 's [=FileSystemSyncAccessHandle/[[file]]=] .
1663
1703
1. [=Enqueue the following steps=] to the [=file system queue=] :
1664
- 1. [=file entry/lock/release|Release the lock=] on |file|.
1704
+ 1. [=file system entry/lock/release|Release the lock=] on |file|.
1665
1705
1. Set |lockReleased| to true.
1666
1706
1. [=Pause=] until |lockReleased| is true.
1667
1707
0 commit comments