1 /* 2 * File access convenience functions. 3 * 4 * Copyright (C) 2021 Paul Boddie <paul@boddie.org.uk> 5 * 6 * This program is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License as 8 * published by the Free Software Foundation; either version 2 of 9 * the License, or (at your option) any later version. 10 * 11 * This program is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with this program; if not, write to the Free Software 18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, 19 * Boston, MA 02110-1301, USA 20 */ 21 22 #include <ipc/cap_alloc.h> 23 #include <ipc/mem_ipc.h> 24 25 #include "dataspace_client.h" 26 #include "opener_client.h" 27 #include "opener_context_client.h" 28 #include "mapped_file_client.h" 29 30 #include "file.h" 31 32 33 34 offset_t file_span(file_t *file) 35 { 36 offset_t size = file->end_pos - file->start_pos; 37 38 return (file->data_end < size) ? file->data_end : size; 39 } 40 41 void file_init(file_t *file) 42 { 43 file->memory = NULL; 44 file->ref = L4_INVALID_CAP; 45 } 46 47 long file_open(file_t *file, l4_cap_idx_t context_ref) 48 { 49 client_OpenerContext context(context_ref); 50 file_init(file); 51 return context.open(L4_FPAGE_RW, &file->size, &file->ref); 52 } 53 54 void file_close(file_t *file) 55 { 56 if (l4_is_valid_cap(file->ref)) 57 ipc_cap_free_um(file->ref); 58 59 if (file->memory != NULL) 60 ipc_detach_dataspace(file->memory); 61 62 file_init(file); 63 } 64 65 long file_mmap(file_t *file, offset_t position, offset_t length) 66 { 67 client_MappedFile mapped_file(file->ref); 68 long err = mapped_file.mmap(position, length, &file->start_pos, &file->end_pos, &file->data_end); 69 70 if (err) 71 return err; 72 73 return ipc_attach_dataspace(file->ref, file->end_pos - file->start_pos, (void **) &file->memory); 74 } 75 76 long context_open(file_t *file, l4_cap_idx_t server) 77 { 78 client_Opener opener(server); 79 unsigned long size, flags; 80 long err; 81 82 file_init(file); 83 err = opener.context(&file->ref); 84 85 if (err) 86 return err; 87 88 client_Dataspace context_ds(file->ref); 89 90 err = context_ds.info(&size, &flags); 91 92 if (err) 93 return err; 94 95 return ipc_attach_dataspace(file->ref, size, (void **) &file->memory); 96 } 97 98 // vim: tabstop=2 expandtab shiftwidth=2