Add rights for mapping buffer. Update (shared) buffer APIs. R=azani@chromium.org Review URL: https://codereview.chromium.org/1964953002 .
diff --git a/mojo/edk/system/core.cc b/mojo/edk/system/core.cc index a8c2007..65eb073 100644 --- a/mojo/edk/system/core.cc +++ b/mojo/edk/system/core.cc
@@ -638,7 +638,7 @@ uint32_t info_num_bytes) { RefPtr<Dispatcher> dispatcher; MojoResult result = - GetDispatcherAndCheckRights(buffer_handle, MOJO_HANDLE_RIGHT_READ, + GetDispatcherAndCheckRights(buffer_handle, MOJO_HANDLE_RIGHT_GET_OPTIONS, EntrypointClass::BUFFER, &dispatcher); if (result != MOJO_RESULT_OK) return result; @@ -652,11 +652,13 @@ UserPointer<void*> buffer, MojoMapBufferFlags flags) { RefPtr<Dispatcher> dispatcher; - // TODO(vtl): Is this right? Or should there be a "map" right? Probably I need - // to rethink rights for buffers. - MojoResult result = - GetDispatcherAndCheckRights(buffer_handle, MOJO_HANDLE_RIGHT_WRITE, - EntrypointClass::BUFFER, &dispatcher); + // TODO(vtl): Currently we can only map read/write. So both + // |MOJO_HANDLE_RIGHT_MAP_READABLE| and |MOJO_HANDLE_RIGHT_MAP_WRITABLE| are + // required. + MojoResult result = GetDispatcherAndCheckRights( + buffer_handle, + MOJO_HANDLE_RIGHT_MAP_READABLE | MOJO_HANDLE_RIGHT_MAP_WRITABLE, + EntrypointClass::BUFFER, &dispatcher); if (result != MOJO_RESULT_OK) return result;
diff --git a/mojo/edk/system/core_test_base.cc b/mojo/edk/system/core_test_base.cc index ed98702..1f982ec 100644 --- a/mojo/edk/system/core_test_base.cc +++ b/mojo/edk/system/core_test_base.cc
@@ -230,7 +230,9 @@ std::move(dispatcher), MOJO_HANDLE_RIGHT_DUPLICATE | MOJO_HANDLE_RIGHT_TRANSFER | MOJO_HANDLE_RIGHT_READ | MOJO_HANDLE_RIGHT_WRITE | - MOJO_HANDLE_RIGHT_GET_OPTIONS | MOJO_HANDLE_RIGHT_SET_OPTIONS)); + MOJO_HANDLE_RIGHT_GET_OPTIONS | MOJO_HANDLE_RIGHT_SET_OPTIONS | + MOJO_HANDLE_RIGHT_MAP_READABLE | MOJO_HANDLE_RIGHT_MAP_WRITABLE | + MOJO_HANDLE_RIGHT_MAP_EXECUTABLE)); CHECK_NE(rv, MOJO_HANDLE_INVALID); return rv; }
diff --git a/mojo/edk/system/handle_unittest.cc b/mojo/edk/system/handle_unittest.cc index 8c630ed..5dc27cd 100644 --- a/mojo/edk/system/handle_unittest.cc +++ b/mojo/edk/system/handle_unittest.cc
@@ -125,6 +125,9 @@ EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_WRITE)); EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_GET_OPTIONS)); EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_SET_OPTIONS)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_READABLE)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_WRITABLE)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_EXECUTABLE)); } { @@ -138,6 +141,9 @@ EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_WRITE)); EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_GET_OPTIONS)); EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_SET_OPTIONS)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_READABLE)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_WRITABLE)); + EXPECT_FALSE(h.has_all_rights(MOJO_HANDLE_RIGHT_MAP_EXECUTABLE)); EXPECT_TRUE( h.has_all_rights(MOJO_HANDLE_RIGHT_DUPLICATE | MOJO_HANDLE_RIGHT_READ));
diff --git a/mojo/edk/system/shared_buffer_dispatcher.h b/mojo/edk/system/shared_buffer_dispatcher.h index 70e2158..68c3209 100644 --- a/mojo/edk/system/shared_buffer_dispatcher.h +++ b/mojo/edk/system/shared_buffer_dispatcher.h
@@ -36,7 +36,9 @@ // duplicable by default. static constexpr MojoHandleRights kDefaultHandleRights = MOJO_HANDLE_RIGHT_DUPLICATE | MOJO_HANDLE_RIGHT_TRANSFER | - MOJO_HANDLE_RIGHT_READ | MOJO_HANDLE_RIGHT_WRITE; + MOJO_HANDLE_RIGHT_GET_OPTIONS | MOJO_HANDLE_RIGHT_SET_OPTIONS | + MOJO_HANDLE_RIGHT_MAP_READABLE | MOJO_HANDLE_RIGHT_MAP_WRITABLE | + MOJO_HANDLE_RIGHT_MAP_EXECUTABLE; // The default options to use for |MojoCreateSharedBuffer()|. (Real uses // should obtain this via |ValidateCreateOptions()| with a null |in_options|;
diff --git a/mojo/public/c/system/buffer.h b/mojo/public/c/system/buffer.h index 0c253c0..2dd7477 100644 --- a/mojo/public/c/system/buffer.h +++ b/mojo/public/c/system/buffer.h
@@ -102,7 +102,11 @@ // |options| may be set to null for a shared buffer with the default options. // // On success, |*shared_buffer_handle| will be set to the handle for the shared -// buffer. (On failure, it is not modified.) +// buffer. (On failure, it is not modified.) The handle has (at least) the +// following rights: |MOJO_HANDLE_RIGHT_DUPLICATE|, +// |MOJO_HANDLE_RIGHT_TRANSFER|, |MOJO_HANDLE_RIGHT_GET_OPTIONS|, +// |MOJO_HANDLE_RIGHT_SET_OPTIONS|, |MOJO_HANDLE_RIGHT_MAP_READABLE|, +// |MOJO_HANDLE_RIGHT_MAP_WRITABLE|, and |MOJO_HANDLE_RIGHT_MAP_EXECUTABLE|. // // Note: While more than |num_bytes| bytes may apparently be // available/visible/readable/writable, trying to use those extra bytes is @@ -122,11 +126,11 @@ uint64_t num_bytes, // In. MojoHandle* MOJO_RESTRICT shared_buffer_handle); // Out. -// |MojoDuplicateBufferHandle()|: Duplicates the handle |buffer_handle| to a -// buffer. This creates another handle (returned in |*new_buffer_handle| on -// success), which can then be sent to another application over a message pipe, -// while retaining access to the |buffer_handle| (and any mappings that it may -// have). +// |MojoDuplicateBufferHandle()|: Duplicates the handle |buffer_handle| (which +// must have the |MOJO_HANDLE_RIGHT_DUPLICATE| right) to a buffer. This creates +// another handle (returned in |*new_buffer_handle| on success), which can then +// be sent to another application over a message pipe, while retaining access to +// the |buffer_handle| (and any mappings that it may have). // // |options| may be set to null to duplicate the buffer handle with the default // options. @@ -138,6 +142,8 @@ // |MOJO_RESULT_OK| on success. // |MOJO_RESULT_INVALID_ARGUMENT| if some argument was invalid (e.g., // |buffer_handle| is not a valid buffer handle or |*options| is invalid). +// |MOJO_RESULT_PERMISSION_DENIED| if |buffer_handle| does not have the +// |MOJO_HANDLE_RIGHT_DUPLICATE| right. // |MOJO_RESULT_UNIMPLEMENTED| if an unsupported flag was set in |*options|. // |MOJO_RESULT_BUSY| if |buffer_handle| is currently in use in some // transaction (that, e.g., may result in it being invalidated, such as @@ -149,9 +155,10 @@ MojoHandle* MOJO_RESTRICT new_buffer_handle); // Out. // |MojoGetBufferInformation()|: Gets information about the buffer with handle -// |buffer_handle|. |info| should be non-null and point to a buffer of size -// |info_num_bytes|; |info_num_bytes| should be at least 16 (the size of the -// first, and currently only, version of |struct MojoBufferInformation|). +// |buffer_handle| (which must have the |MOJO_HANDLE_RIGHT_GET_OPTIONS| right). +// |info| should be non-null and point to a buffer of size |info_num_bytes|; +// |info_num_bytes| should be at least 16 (the size of the first, and currently +// only, version of |struct MojoBufferInformation|). // // On success, |*info| will be filled with information about the given buffer. // Note that if additional (larger) versions of |struct MojoBufferInformation| @@ -164,6 +171,8 @@ // |MOJO_RESULT_INVALID_ARGUMENT| if some argument was invalid (e.g., // |buffer_handle| is not a valid buffer handle, |*info| is null, or // |info_num_bytes| is too small). +// |MOJO_RESULT_PERMISSION_DENIED| if |buffer_handle| does not have the +// |MOJO_HANDLE_RIGHT_GET_OPTIONS| right. // |MOJO_RESULT_BUSY| if |buffer_handle| is currently in use in some // transaction (that, e.g., may result in it being invalidated, such as // being sent in a message). @@ -172,10 +181,12 @@ uint32_t info_num_bytes); // In. // |MojoMapBuffer()|: Maps the part (at offset |offset| of length |num_bytes|) -// of the buffer given by |buffer_handle| into memory, with options specified by -// |flags|. |offset + num_bytes| must be less than or equal to the size of the -// buffer. On success, |*buffer| points to memory with the requested part of the -// buffer. (On failure, it is not modified.) +// of the buffer given by |buffer_handle| (which must have both the +// |MOJO_HANDLE_RIGHT_MAP_READABLE| and |MOJO_HANDLE_RIGHT_MAP_WRITABLE| rights) +// into memory, with options specified by |flags|. |offset + num_bytes| must be +// less than or equal to the size of the buffer. On success, |*buffer| points to +// memory with the requested part of the buffer. (On failure, it is not +// modified.) // // A single buffer handle may have multiple active mappings (possibly depending // on the buffer type). The permissions (e.g., writable or executable) of the @@ -191,6 +202,9 @@ // |MOJO_RESULT_INVALID_ARGUMENT| if some argument was invalid (e.g., // |buffer_handle| is not a valid buffer handle or the range specified by // |offset| and |num_bytes| is not valid). +// |MOJO_RESULT_PERMISSION_DENIED| if |buffer_handle| does not have both the +// |MOJO_HANDLE_RIGHT_MAP_READABLE| and |MOJO_HANDLE_RIGHT_MAP_WRITABLE| +// rights. // |MOJO_RESULT_RESOURCE_EXHAUSTED| if the mapping operation itself failed // (e.g., due to not having appropriate address space available). // |MOJO_RESULT_BUSY| if |buffer_handle| is currently in use in some
diff --git a/mojo/public/c/system/handle.h b/mojo/public/c/system/handle.h index 096a248..445558c 100644 --- a/mojo/public/c/system/handle.h +++ b/mojo/public/c/system/handle.h
@@ -35,6 +35,12 @@ // message). // |MOJO_HANDLE_RIGHT_GET_OPTIONS| - Right to get a handle's options. // |MOJO_HANDLE_RIGHT_SET_OPTIONS| - Right to set a handle's options. +// |MOJO_HANDLE_RIGHT_MAP_READABLE| - Right to "map" a (e.g., buffer) handle +// as readable memory. +// |MOJO_HANDLE_RIGHT_MAP_WRITABLE| - Right to "map" a (e.g., buffer) handle +// as writable memory. +// |MOJO_HANDLE_RIGHT_MAP_EXECUTABLE| - Right to "map" a (e.g., buffer) handle +// as executable memory. // // TODO(vtl): Add rights support/checking to existing handle types. @@ -47,6 +53,9 @@ #define MOJO_HANDLE_RIGHT_WRITE ((MojoHandleRights)1 << 3) #define MOJO_HANDLE_RIGHT_GET_OPTIONS ((MojoHandleRights)1 << 4) #define MOJO_HANDLE_RIGHT_SET_OPTIONS ((MojoHandleRights)1 << 5) +#define MOJO_HANDLE_RIGHT_MAP_READABLE ((MojoHandleRights)1 << 6) +#define MOJO_HANDLE_RIGHT_MAP_WRITABLE ((MojoHandleRights)1 << 7) +#define MOJO_HANDLE_RIGHT_MAP_EXECUTABLE ((MojoHandleRights)1 << 8) // |MojoHandleSignals|: Used to specify signals that can be waited on for a // handle (and which can be triggered), e.g., the ability to read or write to @@ -79,6 +88,7 @@ // determine which, if any, of the signals can still be satisfied. // Note: This struct is not extensible (and only has 32-bit quantities), so it's // 32-bit-aligned. + MOJO_STATIC_ASSERT(MOJO_ALIGNOF(uint32_t) == 4, "uint32_t has weird alignment"); struct MOJO_ALIGNAS(4) MojoHandleSignalsState { MojoHandleSignals satisfied_signals;