summaryrefslogtreecommitdiff
path: root/viengoos
diff options
context:
space:
mode:
authorNeal H. Walfield <neal@gnu.org>2008-12-18 22:54:15 +0100
committerNeal H. Walfield <neal@gnu.org>2008-12-18 22:54:15 +0100
commit207770cea7fece43bf5517fec7abd88a3a7d6146 (patch)
tree6f41abd1dc4782f34b339b00da956d0c778ef1b7 /viengoos
parentf5cfa7cbb8a2fff68cf87a3a685428507ce977b4 (diff)
Support batching requests for object_discarded_clear.
libviengoos/ 2008-12-18 Neal H. Walfield <neal@gnu.org> * viengoos/cap.h (object_discarded_clear): Take additional parameter count. Take multiple object addresses. viengoos/ 2008-12-18 Neal H. Walfield <neal@gnu.org> * server.c (server_loop): Handle multiple objects in object_discarded_clear. libhurd-mm/ 2008-12-18 Neal H. Walfield <neal@gnu.org> * anonymous.c (fault): Batch object discard requests.
Diffstat (limited to 'viengoos')
-rw-r--r--viengoos/ChangeLog5
-rw-r--r--viengoos/server.c114
2 files changed, 68 insertions, 51 deletions
diff --git a/viengoos/ChangeLog b/viengoos/ChangeLog
index d30da99..bc19cff 100644
--- a/viengoos/ChangeLog
+++ b/viengoos/ChangeLog
@@ -1,5 +1,10 @@
2008-12-18 Neal H. Walfield <neal@gnu.org>
+ * server.c (server_loop): Handle multiple objects in
+ object_discarded_clear.
+
+2008-12-18 Neal H. Walfield <neal@gnu.org>
+
* server.c (server_loop): Set SLOT to 0, not TARGET.
2008-12-18 Neal H. Walfield <neal@gnu.org>
diff --git a/viengoos/server.c b/viengoos/server.c
index c1cdb90..e423c14 100644
--- a/viengoos/server.c
+++ b/viengoos/server.c
@@ -1449,71 +1449,83 @@ server_loop (void)
DEBUG (4, VG_ADDR_FMT, VG_ADDR_PRINTF (object_addr));
- /* We can't look up the object use OBJECT as object_lookup
- returns NULL if the object's discardable bit is set!
- Instead, we lookup the capability, find the object's
- folio and then clear its discarded bit. */
- struct vg_cap cap = CAP (&thread->aspace, object_addr, -1, true);
- if (cap.type == vg_cap_void)
- REPLY (ENOENT);
- if (vg_cap_type_weak_p (cap.type))
- REPLY (EPERM);
-
- int idx = (cap.oid % (1 + VG_FOLIO_OBJECTS)) - 1;
- vg_oid_t foid = cap.oid - idx - 1;
+ vg_addr_t *addr = (void *) vg_message_data (message)
+ + sizeof (uintptr_t);
+ int count = ((vg_message_data_count (message) - sizeof (uintptr_t))
+ / sizeof (vg_addr_t));
+ int i;
+ for (i = 0; i < count; i ++)
+ {
+ /* We can't look up the object use OBJECT as object_lookup
+ returns NULL if the object's discardable bit is set!
+ Instead, we lookup the capability, find the object's
+ folio and then clear its discarded bit. */
+ struct vg_cap cap = CAP (target_root, addr[i], -1, true);
+ if (cap.type == vg_cap_void)
+ REPLY (ENOENT);
+ if (vg_cap_type_weak_p (cap.type))
+ REPLY (EPERM);
- struct vg_folio *folio = (struct vg_folio *)
- object_find (activity, foid, VG_OBJECT_POLICY_VOID);
+ int idx = (cap.oid % (1 + VG_FOLIO_OBJECTS)) - 1;
+ vg_oid_t foid = cap.oid - idx - 1;
- if (folio_object_version (folio, idx) != cap.version)
- REPLY (ENOENT);
+ struct vg_folio *folio = (struct vg_folio *)
+ object_find (activity, foid, VG_OBJECT_POLICY_VOID);
- bool was_discarded = folio_object_discarded (folio, idx);
- folio_object_discarded_set (folio, idx, false);
+ if (folio_object_version (folio, idx) != cap.version)
+ REPLY (ENOENT);
- vg_object_discarded_clear_reply (activity, reply);
+ bool was_discarded = folio_object_discarded (folio, idx);
+ folio_object_discarded_set (folio, idx, false);
#if 0
- /* XXX: Surprisingly, it appears that this may be more
- expensive than just faulting the pages normally. This
- needs more investivation. */
- if (was_discarded
- && cap.type == vg_cap_page
- && VG_CAP_GUARD_BITS (&cap) == 0
- && (vg_addr_depth (object_addr) == VG_ADDR_BITS - PAGESIZE_LOG2))
- /* The target object was discarded, appears to be a page
- and seems to be installed at a point where it would
- appear in the hardware address space. If this is
- really the case, then we can map it now and save a
- fault later. */
- {
- profile_region ("object_discard-prefault");
-
- struct vg_object *page = vg_cap_to_object (principal, &cap);
- if (page)
+ /* XXX: Surprisingly, it appears that this may be more
+ expensive than just faulting the pages normally. This
+ needs more investigation. */
+ if (target == thread
+ && was_discarded
+ && cap.type == vg_cap_page
+ && VG_CAP_GUARD_BITS (&cap) == 0
+ && (vg_addr_depth (object_addr)
+ == VG_ADDR_BITS - PAGESIZE_LOG2))
+ /* The target object was discarded, appears to be a page
+ and seems to be installed at a point where it would
+ appear in the hardware address space. If this is
+ really the case, then we can map it now and save a
+ fault later. */
{
- object_to_object_desc (page)->mapped = true;
+ profile_region ("object_discard-prefault");
- l4_fpage_t fpage = l4_fpage ((uintptr_t) page, PAGESIZE);
- fpage = l4_fpage_add_rights (fpage,
- L4_FPAGE_READABLE
- | L4_FPAGE_WRITABLE);
+ struct vg_object *page = vg_cap_to_object (principal, &cap);
+ if (page)
+ {
+ object_to_object_desc (page)->mapped = true;
- uintptr_t page_addr = vg_addr_prefix (object_addr);
+ l4_fpage_t fpage = l4_fpage ((uintptr_t) page,
+ PAGESIZE);
+ fpage = l4_fpage_add_rights (fpage,
+ L4_FPAGE_READABLE
+ | L4_FPAGE_WRITABLE);
- l4_map_item_t map_item = l4_map_item (fpage, page_addr);
+ uintptr_t page_addr = vg_addr_prefix (object_addr);
- l4_msg_append_map_item (msg, map_item);
+ l4_map_item_t map_item = l4_map_item (fpage, page_addr);
- DEBUG (4, "Prefaulting "VG_ADDR_FMT"(%x) <- %p (%x/%x/%x)",
- VG_ADDR_PRINTF (object_addr), page_addr,
- page, l4_address (fpage), l4_size (fpage),
- l4_rights (fpage));
- }
+ l4_msg_append_map_item (msg, map_item);
- profile_region_end ();
- }
+ DEBUG (4, "Prefaulting "VG_ADDR_FMT
+ "(%x) <- %p (%x/%x/%x)",
+ VG_ADDR_PRINTF (object_addr), page_addr,
+ page, l4_address (fpage), l4_size (fpage),
+ l4_rights (fpage));
+ }
+
+ profile_region_end ();
+ }
#endif
+ }
+
+ vg_object_discarded_clear_reply (activity, reply, i);
break;
}