2 #include <inc/string.h>
7 union Fsipc fsipcbuf
__attribute__((aligned(PGSIZE
)));
9 // Send an inter-environment request to the file server, and wait for
10 // a reply. The request body should be in fsipcbuf, and parts of the
11 // response may be written back to fsipcbuf.
12 // type: request code, passed as the simple integer IPC value.
13 // dstva: virtual address at which to receive reply page, 0 if none.
14 // Returns result from the file server.
16 fsipc(unsigned type
, void *dstva
)
20 fsenv
= ipc_find_env(ENV_TYPE_FS
);
22 static_assert(sizeof(fsipcbuf
) == PGSIZE
);
25 cprintf("[%08x] fsipc %d %08x\n", thisenv
->env_id
, type
, *(uint32_t *)&fsipcbuf
);
27 ipc_send(fsenv
, type
, &fsipcbuf
, PTE_P
| PTE_W
| PTE_U
);
28 return ipc_recv(NULL
, dstva
, NULL
);
31 static int devfile_flush(struct Fd
*fd
);
32 static ssize_t
devfile_read(struct Fd
*fd
, void *buf
, size_t n
);
33 static ssize_t
devfile_write(struct Fd
*fd
, const void *buf
, size_t n
);
34 static int devfile_stat(struct Fd
*fd
, struct Stat
*stat
);
35 static int devfile_trunc(struct Fd
*fd
, off_t newsize
);
41 .dev_read
= devfile_read
,
42 .dev_write
= devfile_write
,
43 .dev_close
= devfile_flush
,
44 .dev_stat
= devfile_stat
,
45 .dev_trunc
= devfile_trunc
48 // Open a file (or directory).
51 // The file descriptor index on success
52 // -E_BAD_PATH if the path is too long (>= MAXPATHLEN)
53 // < 0 for other errors.
55 open(const char *path
, int mode
)
57 // Find an unused file descriptor page using fd_alloc.
58 // Then send a file-open request to the file server.
59 // Include 'path' and 'omode' in request,
60 // and map the returned file descriptor page
61 // at the appropriate fd address.
62 // FSREQ_OPEN returns 0 on success, < 0 on failure.
64 // (fd_alloc does not allocate a page, it just returns an
65 // unused fd address. Do you need to allocate a page?)
67 // Return the file descriptor index.
68 // If any step after fd_alloc fails, use fd_close to free the
71 // LAB 5: Your code here.
72 panic("open not implemented");
75 // Flush the file descriptor. After this the fileid is invalid.
77 // This function is called by fd_close. fd_close will take care of
78 // unmapping the FD page from this environment. Since the server uses
79 // the reference counts on the FD pages to detect which files are
80 // open, unmapping it is enough to free up server-side resources.
81 // Other than that, we just have to make sure our changes are flushed
84 devfile_flush(struct Fd
*fd
)
86 fsipcbuf
.flush
.req_fileid
= fd
->fd_file
.id
;
87 return fsipc(FSREQ_FLUSH
, NULL
);
90 // Read at most 'n' bytes from 'fd' at the current position into 'buf'.
93 // The number of bytes successfully read.
96 devfile_read(struct Fd
*fd
, void *buf
, size_t n
)
98 // Make an FSREQ_READ request to the file system server after
99 // filling fsipcbuf.read with the request arguments. The
100 // bytes read will be written back to fsipcbuf by the file
102 // LAB 5: Your code here
103 panic("devfile_read not implemented");
106 // Write at most 'n' bytes from 'buf' to 'fd' at the current seek position.
109 // The number of bytes successfully written.
112 devfile_write(struct Fd
*fd
, const void *buf
, size_t n
)
114 // Make an FSREQ_WRITE request to the file system server. Be
115 // careful: fsipcbuf.write.req_buf is only so large, but
116 // remember that write is always allowed to write *fewer*
117 // bytes than requested.
118 // LAB 5: Your code here
119 panic("devfile_write not implemented");
123 devfile_stat(struct Fd
*fd
, struct Stat
*st
)
127 fsipcbuf
.stat
.req_fileid
= fd
->fd_file
.id
;
128 if ((r
= fsipc(FSREQ_STAT
, NULL
)) < 0)
130 strcpy(st
->st_name
, fsipcbuf
.statRet
.ret_name
);
131 st
->st_size
= fsipcbuf
.statRet
.ret_size
;
132 st
->st_isdir
= fsipcbuf
.statRet
.ret_isdir
;
136 // Truncate or extend an open file to 'size' bytes
138 devfile_trunc(struct Fd
*fd
, off_t newsize
)
140 fsipcbuf
.set_size
.req_fileid
= fd
->fd_file
.id
;
141 fsipcbuf
.set_size
.req_size
= newsize
;
142 return fsipc(FSREQ_SET_SIZE
, NULL
);
147 remove(const char *path
)
149 if (strlen(path
) >= MAXPATHLEN
)
151 strcpy(fsipcbuf
.remove
.req_path
, path
);
152 return fsipc(FSREQ_REMOVE
, NULL
);
155 // Synchronize disk with buffer cache
159 // Ask the file server to update the disk
160 // by writing any dirty blocks in the buffer cache.
162 return fsipc(FSREQ_SYNC
, NULL
);