diff --git a/definitions/objects/mailbox.def b/definitions/objects/mailbox.def index 87f0046..f9ac74a 100644 --- a/definitions/objects/mailbox.def +++ b/definitions/objects/mailbox.def @@ -19,7 +19,7 @@ object mailbox : object { method call [cap:send] { param tag uint64 [inout] param subtag uint64 [inout] - param give_handle ref object [inout handle] + param give_handle ref object [optional inout handle] } # Respond to a message sent using call, and wait for another @@ -29,7 +29,7 @@ object mailbox : object { method respond [cap:receive] { param tag uint64 [inout] param subtag uint64 [inout] - param give_handle ref object [inout handle] + param give_handle ref object [optional inout handle] param reply_tag uint64 [inout] param flags uint64 } diff --git a/src/kernel/syscall_verify.cpp.cog b/src/kernel/syscall_verify.cpp.cog index bbd7170..035f2ed 100644 --- a/src/kernel/syscall_verify.cpp.cog +++ b/src/kernel/syscall_verify.cpp.cog @@ -90,7 +90,7 @@ for id, scope, method in syscalls.methods: args = [] # The function call args to call the impl argdefs = [] # The user-facing syscall args signature cxxargdefs = [] # The kernel syscall impl args signature - refparams = [] # The list of params which are kobjects + refparams = [] # The list of params which are pointers handles = [] objparams = [] @@ -111,7 +111,11 @@ for id, scope, method in syscalls.methods: cxxargdefs.append(f"obj::{scope.cname} *self") objparams.append((f"obj::{scope.cname} *", "self")) - handles.append((scope.cname, "self", get_caps(method.options, scope))) + handles.append(( + scope.cname, + "self", + get_caps(method.options, scope), + False)) for param in method.params: needs_obj = param.type.needs_object(param.options) @@ -125,7 +129,12 @@ for id, scope, method in syscalls.methods: arg = f"{param.name}{suffix}" if needs_handle: - handles.append((param.type.object.cname, arg, get_caps(param.options, param.type.object))) + handles.append(( + param.type.object.cname, + arg, + get_caps(param.options, param.type.object), + param.optional)) + if needs_obj: objparams.append((type, arg)) args.append(f"{arg}_obj") @@ -138,7 +147,9 @@ for id, scope, method in syscalls.methods: if not needs_handle and param.caps: handles.append(( f"obj::{param.type.object.cname}", - arg, get_caps(param.options, param.type.object))) + arg, + get_caps(param.options, param.type.object, + param.optional))) if param.refparam: subs = param.type.c_names(param.options) @@ -173,13 +184,15 @@ for id, scope, method in syscalls.methods: if handles: cog.outl(f" j6_status_t res;") - for type, arg, caps in handles: + for type, arg, caps, optional in handles: capsval = "0" if caps: capsval = " | ".join(caps) + optstr = (optional and "true") or "false" + cog.outl(f" obj::{type} *{arg}_obj = nullptr;") - cog.outl(f" res = get_handle({arg}, {capsval}, {arg}_obj);") + cog.outl(f" res = get_handle({arg}, {capsval}, {arg}_obj, {optstr});") cog.outl(f" if (res != j6_status_ok) return res;") cog.outl() @@ -195,7 +208,7 @@ for id, scope, method in syscalls.methods: cog.outl(f""" _retval = {name}({", ".join(args)});""") cog.outl(" }\n") - for type, arg, caps in handles: + for type, arg, caps, optional in handles: cog.outl(f" release_handle({arg});") cog.outl(f""" return _retval;""") diff --git a/src/kernel/syscalls/helpers.h b/src/kernel/syscalls/helpers.h index 9dfb125..2649d65 100644 --- a/src/kernel/syscalls/helpers.h +++ b/src/kernel/syscalls/helpers.h @@ -23,11 +23,11 @@ T * construct_handle(j6_handle_t *id, Args... args) } template -j6_status_t get_handle(j6_handle_t id, j6_cap_t caps, T *&object) +j6_status_t get_handle(j6_handle_t id, j6_cap_t caps, T *&object, bool optional = false) { if (id == j6_handle_invalid) { object = nullptr; - return j6_status_ok; + return optional ? j6_status_ok : j6_err_invalid_arg; } capability *capdata = g_cap_table.retain(id); @@ -43,17 +43,17 @@ j6_status_t get_handle(j6_handle_t id, j6_cap_t caps, T *&object) } template -inline j6_status_t get_handle(j6_handle_t *id, j6_cap_t caps, T *&object) +inline j6_status_t get_handle(j6_handle_t *id, j6_cap_t caps, T *&object, bool optional = false) { - return get_handle(*id, caps, object); + return get_handle(*id, caps, object, optional); } template <> -inline j6_status_t get_handle(j6_handle_t id, j6_cap_t caps, obj::kobject *&object) +inline j6_status_t get_handle(j6_handle_t id, j6_cap_t caps, obj::kobject *&object, bool optional) { if (id == j6_handle_invalid) { object = nullptr; - return j6_status_ok; + return optional ? j6_status_ok : j6_err_invalid_arg; } capability *capdata = g_cap_table.retain(id); diff --git a/src/user/drv.uart/main.cpp b/src/user/drv.uart/main.cpp index ae2c846..bb20b26 100644 --- a/src/user/drv.uart/main.cpp +++ b/src/user/drv.uart/main.cpp @@ -41,7 +41,7 @@ int channel_pump_loop() { j6_status_t result; - constexpr size_t buffer_size = 512; + static constexpr size_t buffer_size = 512; char buffer[buffer_size]; j6_handle_t slp = j6_find_first_handle(j6_object_type_mailbox);