New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
question about retiring Random / PCLOCK / MCLOCK / Time interfaces and functors #1513
Comments
Maybe there's a wider question, and we should address this in the next major release. There are certain things a unikernel is functorized over that I'm rather sad about:
These all don't have an internal state that you act on (something like TCP.t for creating connections) - but usually you use Now, what are alternatives? Do we actually care which modules use these functionality? Could the dune virtual library help us, and we simply use I also remember years ago someone said "we'll just use first-class modules for these functors" (so far I haven't seen anything like that). Resource-usage-wise they aren't too interesting either. Using objects and some "environment" (eio-style) does not (from my perspective) improve the situation at all. Certainly, there's need for initialization (esp. for the rng to start the entropy collection). There's as well potential use for pclock-synced-with-ntp (or whatever network time protocol you prefer - we've been discussing this since a decade without any NTP implementation...). But using the linking trick should allow an application (unikernel) to select the implementation. So, below the line: what is your take on these interfaces and implementations? Is there any real reason to retain this complexity? Or is there desire from your point to move on (and make life easier for 99%)? |
+1 to not relying on the functorized capabilities interface. This gets in the way of using Riot in a unikernel. I'd rather see a configuration (or even runtime) flag for enabling capabilities and replacing/injecting capability modules. |
Back on this topic, I'd be happy to hear your opinion:
Now, with this change, and a modified mirage-skeleton/device-usage/clock unikernel: config.ml: open Mirage
let main = main "Unikernel.Main" (time @-> job)
let () =
register "speaking_clock"
[ main $ default_time ] unikernel.ml: open Lwt.Infix
let log = Logs.Src.create "speaking clock" ~doc:"At the third stroke..."
module Log = (val Logs.src_log log : Logs.LOG)
module Main
(Time : Mirage_time.S) =
struct
let str_of_time (posix_time, timezone) =
Format.asprintf "%a" (Ptime.pp_human ?tz_offset_s:timezone ()) posix_time
let start _time =
let rec speak () =
let current_time = Mirage_clock.Pclock.now_d_ps () |> Ptime.v in
let tz = Mirage_clock.Pclock.current_tz_offset_s () in
let str =
Printf.sprintf
"%Lu nanoseconds have elapsed. \n\
\ At the stroke, the time will be %s \x07 *BEEP*"
(Mirage_clock.Mclock.elapsed_ns ())
@@ str_of_time (current_time, tz)
in
Log.info (fun f -> f "%s" str);
Time.sleep_ns 1_000_000_000L >>= fun () -> speak ()
in
speak ()
end After manual modification of mirage-generated files (dune.build refer to It is not clear to me whether it is possible in mirage-clock to define the default_implementation depending on the "context". But we can just emit the mirage-clock.solo5 / mirage-clock.unix inside of mirage!? Is this a valuable path forward? Since quite some packages depend on mclock/pclock, it would be great to first hear input before revising all these libraries and cutting releases. |
After discussing with @leostera, maybe for clock we can use conditional compilation instead. I'll give it a try. |
in a parallel universe, we are able to use "conditional compilation" (using some dune magic) instead of "virtual libraries"... pick your poison -- mine is the conditional compilation since I think it is the most straightforward. so, have a look at mirage/mirage-clock#59 and mirage/mirage-logs#28 - unikernel code same as in above comment. I really like that solution since it doesn't use the variant magic, but is a mostly normal dune file. I tested it again with the mirage-skeleton device-usage/clock unikernel. let me know (cc @mirage/core) about your opinion (and/or I'll push through and adapt these changes)... likely good to bundle with the time and random changes as discussed at the top. |
so, the mirage related changes for the clock unikernel are #1521 -- which only modifies the mirage-logs (removing functor, and clock requirement). |
A quick reply: I think I'm generally in favour of simplifying this part of the stack. Ideally, it would be great if we could find a solution where:
I think using |
I like the idea but I think the most problematic point, from Mirage's point of view, is the addition of a new target where a change has to be made to several projects. Wouldn't it be possible to use |
User code is at mirage/mirage-skeleton#390 -- still not really happy with it (that we need to define the The remaining PRs include:
I guess the mirage "extra_deps" (and some "connect" adjustments - why is in the default_connect even any code generated?) would be useful to specify "I depend on this thingy, but don't bother about values". I also think it is useful to go ahead and take a look at mirage-net (and mirage-block), figuring further things out.. WDYT? |
Thank you a lot for these PRs @hannesm. To me, although I really like the code of the skeleton/clock example, I think the 3 unit args for |
Dear Madam or Sir,
I encountered the "mirage-random" opam package, and its usage. I am curious what you think about it?
My feeling is that the interface can just be removed from the dependency cone, and unikernels can use
Mirage_crypto_rng
directly. I don't see much value in the abstraction (the mirage_impl_random only provide mirage-crypto-rng anyways).I even think that "functorizing over the RNG" is maybe not what we desire to do -- unless there's actual use of a different RNG (or plans to do so)? I guess that "RNG initialization" is still something the mirage utility should do (and here I've no clue whether there's another path than functorizing stuff over the RNG).
From my perspective, this originates from when we introduced nocrypto and entropy harvesting, but with the current state of mirage-crypto-rng (being independent of gmp/zarith), there's no need to abstract/functorize over it (when I repeat for myself that functors are great if and only if you have the requirement to have the same thing using two different modules in the same application). But from where I stand, there's really only ever a single RNG being used, and to reach the CSPRNG properties, our fortuna is the current choice (obviously, happy to get something different if there's new research in that area).
WDYT @mirage/core?
The text was updated successfully, but these errors were encountered: