summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMaksym Planeta <mcsim.planeta@gmail.com>2012-10-08 16:46:28 +0200
committerMaksym Planeta <mcsim.planeta@gmail.com>2012-10-28 12:23:37 +0100
commit5fb4561e864d834cf7c637f6c798f04aea26c23e (patch)
treeb0d15670d4eef7f456526e8d97f726f2c8764c52
parent2cf980488c7ffafae4036dddefa92d9a8cf2b0db (diff)
Add special treatment in memory_object_data_error RPC.
This commit add possibility for server to inform kernel that server has no some data requested by kernel. This possibility should be used when kernel asks for cluster of data, but server can't return all the data. * include/mach/kern_return.h (KERN_NO_DATA): New macro. Using this value server may notify kernel that not all data in requested by kernel cluster are available at the moment. * vm/memory_object.c (memory_object_data_error): Add special treatment for error code KERN_NO_DATA.
-rw-r--r--include/mach/kern_return.h6
-rw-r--r--vm/memory_object.c35
2 files changed, 27 insertions, 14 deletions
diff --git a/include/mach/kern_return.h b/include/mach/kern_return.h
index 2274328b..22161e3c 100644
--- a/include/mach/kern_return.h
+++ b/include/mach/kern_return.h
@@ -157,4 +157,10 @@
/* Object has been terminated and is no longer available.
*/
+#define KERN_NO_DATA 27
+ /* The address range specified does not contain data
+ * at the moment. This value should be provided after
+ * m_o_data_request call.
+ */
+
#endif /* _MACH_KERN_RETURN_H_ */
diff --git a/vm/memory_object.c b/vm/memory_object.c
index 090b58eb..8836c290 100644
--- a/vm/memory_object.c
+++ b/vm/memory_object.c
@@ -337,11 +337,6 @@ kern_return_t memory_object_data_error(object, offset, size, error_value)
if (size != round_page(size))
return(KERN_INVALID_ARGUMENT);
-#ifdef lint
- /* Error value is ignored at this time */
- error_value++;
-#endif
-
vm_object_lock(object);
offset -= object->paging_offset;
@@ -349,16 +344,28 @@ kern_return_t memory_object_data_error(object, offset, size, error_value)
register vm_page_t m;
m = vm_page_lookup(object, offset);
- if ((m != VM_PAGE_NULL) && m->busy && m->absent) {
- m->error = TRUE;
- m->absent = FALSE;
- vm_object_absent_release(object);
- PAGE_WAKEUP_DONE(m);
-
- vm_page_lock_queues();
- vm_page_activate(m);
- vm_page_unlock_queues();
+ switch (error_value) {
+ case KERN_NO_DATA:
+ if ((m != VM_PAGE_NULL) && m->busy && m->absent) {
+ vm_page_lock_queues();
+ vm_page_free(m);
+ vm_page_unlock_queues();
+ }
+ break;
+ default:
+ if ((m != VM_PAGE_NULL) && m->busy && m->absent) {
+ m->error = TRUE;
+ m->absent = FALSE;
+ vm_object_absent_release(object);
+
+ PAGE_WAKEUP_DONE(m);
+
+ vm_page_lock_queues();
+ vm_page_activate(m);
+ vm_page_unlock_queues();
+ }
+ break;
}
size -= PAGE_SIZE;