4 ms·
I meant time-delayed. Eg, run this in 10ms type of thing. How else would you do things like exponential backoff?
by kllrnohj 9y ago
I meant time-delayed. Eg, run this in 10ms type of thing. How else would you do things like exponential backoff?
- naasking 9y agoRight, but your original statement was about clock_gettime, hence my confusion. Something like sleep() is an operation on your own schedule, not an operation on a global system clock. That's not nearly as problematic. Consider if you wanted to virtualize a process, say to deterministically replay it to trigger a fault or something. sleep(100 ticks) doesn't require additional kernel support for virtualization, but an ambient clock requires a lot of extra kernel support. If the clock were only accessible via a handle, then you could proxy invocations on the handle without any extra support in the kernel. See my other comment for more details: https://news.ycombinator.com/item?id=16817462 https://news.ycombinator.com/item?id=16817462
- kllrnohj 9y agoYou could use sleep, sure, but then you require a seperate thread for every delayed message, which is a whole different ball of not-fun. Otherwise what actually happens when you do a postDelayed(func, delay) is it immediately is translated into a postAt(func, clock_gettime() + delay). Then as messages are consumed the work queue consistently knows how long it should wait to wake back up, no matter how many delayed tasks are in flight.
- naasking 9y agoI feel like I'm missing some context. I thought you were talking about work stealing in threaded systems, in which case sleeping seems reasonable. Are you instead talking about some kind of event loop? If so, then clock_gettime seems like it's merely convenient, not essential. You could just as easily keep a ticket incremented on successful operations or successive loops (or some other metric), and exponential backoff is a wait operation on a ticket number. Unless you're suggesting the delay must be based on real time for some reason?
- kllrnohj 9y ago> You could just as easily keep a ticket incremented [..], and exponential backoff is a wait operation on a ticket number. Congrats, you've re-invented clock_gettime(CLOCK_MONOTONIC) :) You're right that it's not essential to have, but if you can re-implement it then you've also just re-introduced the timing attack that the removal of clock_gettime was trying to prevent. The trivial-ness with which a clock suitable for timing attacks is able to be created is literally why SharedArrayBuffer was panic-removed from all major browsers. Because that's all you need, shared memory & a worker. Congrats, you have a high-precision timer with zero OS support. So as soon as you allow any form of threading or shared memory to occur you've given apps a high precision timer, so you might as well just give them an actual timer, too.
- naasking 9y ago> You're right that it's not essential to have, but if you can re-implement it then you've also just re-introduced the timing attack that the removal of clock_gettime was trying to prevent. I'm not convinced. The clock is global, shared among all processes, the ticket I suggested is local to a process, and so can't be used to signal between processes. Unless I'm again missing some context for what you mean.
- kllrnohj 9y agoYou might want to go lookup the meltdown/spectre SharedArrayBuffer proof of concept attack. A timing attack just needs local timing to work, it doesn't care whatsoever about any time in any other process. That's just not how it works. All it needs is a stopwatch of any kind no matter how local.
- naasking 9y ago> You might want to go lookup the meltdown/spectre SharedArrayBuffer proof of concept attack. That still requires a piece shared state, like I said. That vulnerability results from running untrusted code in the same process as trusted code. The whole point of a process is to establish a protection boundary around potentially unsafe code, hence why I keep mentioning processes, and this is the whole point of microkernels and IPC. Within a process, all bets are off. My earlier point was that a shared clock between processes amplifies this problem so that timing attacks cross even the process protection boundary. So when you started talking about job scheduling, I assumed the following: 1. we're in a microkernel context, where we partition trusted and untrusted code using processes. 2. the job scheduling system you mentioned either a) is a process running its own code that it trusts and so in-process timing attacks don't matter, but timing attacks with another process might matter and so you don't want to grant a clock capability if it isn't needed, or b) is a process scheduling system ala cron, where the job scheduler is trusted but the jobs being run are untrusted, and so they run in separate processes. In case (a), the ticket system seems sufficient if you don't want/need to grant access to the clock consistent with least privilege, and for (b) the job scheduler may or may not have the clock installed or not, doesn't really matter, since job scheduling happens via IPC so there's no shared read, ie. delay(100 ticks, self) sends the relative delay which the cron-like scheduler adds to its own clock. Hopefully that clarifies my context, and you can then describe what assumptions your scenario violates.