summaryrefslogtreecommitdiff
path: root/libstore/file.c
diff options
context:
space:
mode:
Diffstat (limited to 'libstore/file.c')
-rw-r--r--libstore/file.c68
1 files changed, 46 insertions, 22 deletions
diff --git a/libstore/file.c b/libstore/file.c
index def0c4c0..49f1c3fb 100644
--- a/libstore/file.c
+++ b/libstore/file.c
@@ -27,6 +27,29 @@
#include "store.h"
+/* Return 0 if STORE's range is enforced by the filesystem, otherwise an
+ error. */
+static error_t
+enforced (struct store *store)
+{
+ if (store->num_runs != 1 || store->runs[0].start != 0)
+ /* Can't enforce non-contiguous ranges, or one not starting at 0. */
+ return EINVAL;
+ else
+ {
+ /* See if the the current (one) range is that the kernel is enforcing. */
+ struct stat st;
+ error_t err = io_stat (store->port, &st);
+
+ if (!err
+ && store->runs[0].length != (st.st_size >> store->log2_block_size))
+ /* The single run is not the whole file. */
+ err = EINVAL;
+
+ return err;
+ }
+}
+
static error_t
file_read (struct store *store,
store_offset_t addr, size_t index, size_t amount, void **buf,
@@ -46,6 +69,27 @@ file_write (struct store *store,
}
static error_t
+file_store_set_size (struct store *store, size_t newsize)
+{
+ error_t err;
+
+ if (enforced (store) != 0)
+ /* Bail out if there is more than a single run. */
+ return EOPNOTSUPP;
+
+ err = file_set_size (store->port, newsize);
+
+ if (!err)
+ {
+ /* Update STORE's size and run. */
+ store->size = newsize;
+ store->runs[0].length = newsize >> store->log2_block_size;
+ }
+
+ return err;
+}
+
+static error_t
file_decode (struct store_enc *enc, const struct store_class *const *classes,
struct store **store)
{
@@ -88,28 +132,7 @@ ficlose (struct store *store)
store->port = MACH_PORT_NULL;
}
-/* Return 0 if STORE's range is enforced by the filesystem, otherwise an
- error. */
-static error_t
-enforced (struct store *store)
-{
- if (store->num_runs != 1 || store->runs[0].start != 0)
- /* Can't enforce non-contiguous ranges, or one not starting at 0. */
- return EINVAL;
- else
- /* See if the the current (one) range is that the kernel is enforcing. */
- {
- struct stat st;
- error_t err = io_stat (store->port, &st);
-
- if (!err
- && store->runs[0].length != (st.st_size >> store->log2_block_size))
- /* The single run is not the whole file. */
- err = EINVAL;
- return err;
- }
-}
static error_t
file_set_flags (struct store *store, int flags)
@@ -192,7 +215,7 @@ file_map (const struct store *store, vm_prot_t prot, mach_port_t *memobj)
const struct store_class
store_file_class =
{
- STORAGE_HURD_FILE, "file", file_read, file_write,
+ STORAGE_HURD_FILE, "file", file_read, file_write, file_store_set_size,
store_std_leaf_allocate_encoding, store_std_leaf_encode, file_decode,
file_set_flags, file_clear_flags, 0, 0, 0, file_open, 0, file_map
};
@@ -219,6 +242,7 @@ struct store_class
store_file_byte_class =
{
STORAGE_HURD_FILE, "file", file_byte_read, file_byte_write,
+ file_store_set_size,
store_std_leaf_allocate_encoding, store_std_leaf_encode, file_decode,
file_set_flags, file_clear_flags, 0, 0, 0, file_open, 0, file_map
};