summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRobert Morris <[email protected]>2020-10-05 06:59:33 -0400
committerRobert Morris <[email protected]>2020-10-05 06:59:33 -0400
commita9b3dd457c647d2836080af4f1cd7c7cb4d1a40d (patch)
tree9d8edd8bab973691b93b3e391fe3995e25c3ec7b
parent271d89ae3065d397e26faa8e05aeec5cc3cd8934 (diff)
downloadxv6-labs-a9b3dd457c647d2836080af4f1cd7c7cb4d1a40d.tar.gz
xv6-labs-a9b3dd457c647d2836080af4f1cd7c7cb4d1a40d.tar.bz2
xv6-labs-a9b3dd457c647d2836080af4f1cd7c7cb4d1a40d.zip
eliminate virtio DMA into kernel stacks.
-rw-r--r--kernel/defs.h1
-rw-r--r--kernel/virtio_disk.c22
-rw-r--r--kernel/vm.c20
3 files changed, 12 insertions, 31 deletions
diff --git a/kernel/defs.h b/kernel/defs.h
index 4b9bbc0..49aafdd 100644
--- a/kernel/defs.h
+++ b/kernel/defs.h
@@ -156,7 +156,6 @@ int uartgetc(void);
// vm.c
void kvminit(void);
void kvminithart(void);
-uint64 kvmpa(uint64);
void kvmmap(uint64, uint64, uint64, int);
int mappages(pagetable_t, uint64, uint64, uint64, int);
pagetable_t uvmcreate(void);
diff --git a/kernel/virtio_disk.c b/kernel/virtio_disk.c
index 070490a..cca44cb 100644
--- a/kernel/virtio_disk.c
+++ b/kernel/virtio_disk.c
@@ -64,6 +64,10 @@ static struct disk {
struct buf *b;
char status;
} info[NUM];
+
+ // disk command headers.
+ // one-for-one with descriptors, for convenience.
+ struct virtio_blk_req ops[NUM];
struct spinlock vdisk_lock;
@@ -219,19 +223,17 @@ virtio_disk_rw(struct buf *b, int write)
// format the three descriptors.
// qemu's virtio-blk.c reads them.
- struct virtio_blk_req buf0;
+ struct virtio_blk_req *buf0 = &disk.ops[idx[0]];
if(write)
- buf0.type = VIRTIO_BLK_T_OUT; // write the disk
+ buf0->type = VIRTIO_BLK_T_OUT; // write the disk
else
- buf0.type = VIRTIO_BLK_T_IN; // read the disk
- buf0.reserved = 0;
- buf0.sector = sector;
-
- // buf0 is on a kernel stack, which is not direct mapped,
- // thus the call to kvmpa().
- disk.desc[idx[0]].addr = (uint64) kvmpa((uint64) &buf0);
- disk.desc[idx[0]].len = sizeof(buf0);
+ buf0->type = VIRTIO_BLK_T_IN; // read the disk
+ buf0->reserved = 0;
+ buf0->sector = sector;
+
+ disk.desc[idx[0]].addr = (uint64) buf0;
+ disk.desc[idx[0]].len = sizeof(struct virtio_blk_req);
disk.desc[idx[0]].flags = VRING_DESC_F_NEXT;
disk.desc[idx[0]].next = idx[1];
diff --git a/kernel/vm.c b/kernel/vm.c
index 0809aea..c99d2a5 100644
--- a/kernel/vm.c
+++ b/kernel/vm.c
@@ -121,26 +121,6 @@ kvmmap(uint64 va, uint64 pa, uint64 sz, int perm)
panic("kvmmap");
}
-// translate a kernel virtual address to
-// a physical address. only needed for
-// addresses on the stack.
-// assumes va is page aligned.
-uint64
-kvmpa(uint64 va)
-{
- uint64 off = va % PGSIZE;
- pte_t *pte;
- uint64 pa;
-
- pte = walk(kernel_pagetable, va, 0);
- if(pte == 0)
- panic("kvmpa");
- if((*pte & PTE_V) == 0)
- panic("kvmpa");
- pa = PTE2PA(*pte);
- return pa+off;
-}
-
// Create PTEs for virtual addresses starting at va that refer to
// physical addresses starting at pa. va and size might not
// be page-aligned. Returns 0 on success, -1 if walk() couldn't