00:36:13 -!- pool has quit (Read error: Connection reset by peer). 00:38:18 -!- pool has joined. 00:59:05 [[Chicken chicken chicken: chicken chicken]] M https://esolangs.org/w/index.php?diff=167636&oldid=167476 * None1 * (-107) /* XKCD Random Number */ Fix example 01:00:56 -!- amby has quit (Quit: so long suckers! i rev up my motorcylce and create a huge cloud of smoke. when the cloud dissipates im lying completely dead on the pavement). 02:31:51 [[Chicken chicken chicken: chicken chicken]] https://esolangs.org/w/index.php?diff=167637&oldid=167636 * None1 * (+95) Added Python interpreter and changed unimplemented to implemented 02:36:24 -!- pool has quit (Read error: Connection reset by peer). 02:38:13 -!- pool has joined. 02:38:54 [[Befreege]] https://esolangs.org/w/index.php?diff=167638&oldid=167436 * None1 * (+125) /* Addition by PSTF */ 02:39:12 [[Befreege]] M https://esolangs.org/w/index.php?diff=167639&oldid=167638 * None1 * (+2) /* Addition by PSTF */ 02:39:24 [[Befreege]] M https://esolangs.org/w/index.php?diff=167640&oldid=167639 * None1 * (+4) /* Addition by PSTF */ 02:42:35 [[Befreege]] M https://esolangs.org/w/index.php?diff=167641&oldid=167640 * None1 * (+12) /* Addition by PSTF */ 03:33:30 [[Suomalaiset ohjelmointikielet]] N https://esolangs.org/w/index.php?oldid=167642 * PrySigneToFry * (+1553) Created page with "Suomalaiset ohjelmointikielet, or simply Suomi, is designed by PSTF. Se kytt suomea pasiallisena ohjelmointikielen. Again a programming language based on LOLCODE. = Command Table = It's almost just simply replace LOLCODE with Finnish equiva 03:34:27 [[Language list]] https://esolangs.org/w/index.php?diff=167643&oldid=167607 * PrySigneToFry * (+36) 03:41:22 [[]] https://esolangs.org/w/index.php?diff=167644&oldid=165821 * PrySigneToFry * (+774) 04:29:06 -!- Zip57 has joined. 05:36:12 [[User:RaiseAfloppaFan3925/Sandbox]] M https://esolangs.org/w/index.php?diff=167645&oldid=167137 * RaiseAfloppaFan3925 * (+168) /* RaiseAfloppaFan's Stupid Idea 0 */ Add note that RSI0 has been moved to its own page 05:44:23 -!- Yayimhere has joined. 05:48:35 thinking of underload in terms of rewriting, is it still turing complete if the operators are applied in prefix? for example (:^):^ would be ^:(^:). I would guess it is still TC but I have no real idea 06:01:37 [[User:Jasper]] https://esolangs.org/w/index.php?diff=167646&oldid=160066 * Jasper * (-48) 06:30:33 -!- Zip57 has quit (Ping timeout: 250 seconds). 06:30:43 Can the General Lock Notation somehow be meaningful for computation (and have a computational class)? Would it do, if the ordering and priority would be included? 07:14:33 [[User:RaiseAfloppaFan3925/Sandbox]] https://esolangs.org/w/index.php?diff=167647&oldid=167645 * RaiseAfloppaFan3925 * (+4130) RaiseAfloppaFan's Stupid Idea 1: The Sequel 07:15:39 [[Photography]] N https://esolangs.org/w/index.php?oldid=167648 * Yayimhere2(school) * (+2185) Created page with "'''Photography''' is an esolang created by [[User:Yayimhere]], after being disappointed at [[Infinite Goto]]'s execution of its concept. Photography is quite similar to a [[Minsky machine]]. It is inspired by [[I/D machine]], [[Minsky Swap]], and [[Karvit 07:32:49 [[Infinite Goto]] https://esolangs.org/w/index.php?diff=167649&oldid=120693 * Yayimhere2(school) * (+64) /* Resources */ 07:34:24 [[Photography]] https://esolangs.org/w/index.php?diff=167650&oldid=167648 * Yayimhere2(school) * (+9) /* Computational class */ 07:49:51 -!- Yayimhere has quit (Ping timeout: 250 seconds). 07:55:01 -!- Yayimhere has joined. 08:07:28 [[Special:Log/move]] move * Yayimhere2(school) * moved [[Photography]] to [[TLQ]]: I dislike the name quite a bit. 08:07:38 [[Photography]] https://esolangs.org/w/index.php?diff=167653&oldid=167652 * Yayimhere2(school) * (-17) Blanked the page 08:11:30 [[TLQ]] https://esolangs.org/w/index.php?diff=167654&oldid=167651 * Yayimhere2(school) * (+209) 08:17:38 [[TLQ]] https://esolangs.org/w/index.php?diff=167655&oldid=167654 * Yayimhere2(school) * (+65) /* Etymology */ 08:21:58 -!- Sgeo has quit (Read error: Connection reset by peer). 08:38:21 [[User:RaiseAfloppaFan3925/Sandbox]] https://esolangs.org/w/index.php?diff=167656&oldid=167647 * RaiseAfloppaFan3925 * (+1643) /* RaiseAfloppaFan's Stupid Idea 1 */ Add RSI1 extension support + some time travel quirks hehe 08:44:47 [[TDQ]] https://esolangs.org/w/index.php?diff=167657&oldid=165538 * ChuckEsoteric08 * (+1) /* Additions */ 08:52:45 -!- ehmry has joined. 08:57:22 [[,(*+)]] https://esolangs.org/w/index.php?diff=167658&oldid=167598 * Yayimhere2(school) * (+106) 09:02:33 [[User:RaiseAfloppaFan3925]] M https://esolangs.org/w/index.php?diff=167659&oldid=167412 * RaiseAfloppaFan3925 * (+126) /* My languages */ Added RSI1 09:06:59 [[Esolang:Sandbox]] https://esolangs.org/w/index.php?diff=167660&oldid=167634 * PrySigneToFry * (+334) Multilingual testing 09:07:56 [[Esolang:Sandbox]] https://esolangs.org/w/index.php?diff=167661&oldid=167660 * PrySigneToFry * (-334) Wow, Tianheng's Unicode Serif is really amazing to use! 09:23:46 [[,(*+)]] https://esolangs.org/w/index.php?diff=167662&oldid=167658 * Yayimhere2(school) * (-33) 09:24:35 [[,(*+)]] https://esolangs.org/w/index.php?diff=167663&oldid=167662 * Yayimhere2(school) * (+54) Undo revision [[Special:Diff/167662|167662]] by [[Special:Contributions/Yayimhere2(school)|Yayimhere2(school)]] ([[User talk:Yayimhere2(school)|talk]]) 09:24:51 [[,(*+)]] https://esolangs.org/w/index.php?diff=167664&oldid=167663 * Yayimhere2(school) * (-233) /* Tips */ 09:25:40 [[,(*+)]] https://esolangs.org/w/index.php?diff=167665&oldid=167664 * Yayimhere2(school) * (-290) 09:29:11 [[,(*+)]] https://esolangs.org/w/index.php?diff=167666&oldid=167665 * Yayimhere2(school) * (+242) /* Programs */ 09:29:19 [[,(*+)]] https://esolangs.org/w/index.php?diff=167667&oldid=167666 * Yayimhere2(school) * (+2) /* Computational class */ 09:38:57 [[Talk:6]] N https://esolangs.org/w/index.php?oldid=167668 * PrySigneToFry * (+323) Created page with "== Author's comments == Actually, I didn't expect this page to become very popular, but I later noticed that an online interpreter had included this programming language. Anyway, this is actually one of my more 'early' works. Later on, I basically stopped making th 09:48:24 [[Formin]] https://esolangs.org/w/index.php?diff=167669&oldid=166978 * CapinolDev * (+1404) 09:52:04 -!- ais523 has joined. 10:49:48 [[Talk:RaiseAfloppaFan's Stupid Idea 0]] https://esolangs.org/w/index.php?diff=167670&oldid=167232 * RaiseAfloppaFan3925 * (+314) /* Joke thread */ Oh yeah, gotta tell you that RSI1 is now a thing. 10:52:17 -!- Yayimhere has quit (Ping timeout: 250 seconds). 11:08:59 -!- Yayimhere has joined. 11:12:04 Hi 11:12:50 APic: (assuming this was to me) hello! 11:20:42 I made an esolang because I didn't want to reconcile command-line arguments and config files https://codeberg.org/eris/eris-go/src/branch/trunk/erishell.1.md https://www.concatenative.org/wiki/view/ERIShell 11:22:18 ehmry: cool! ill check it out 11:26:48 [[User:RaiseAfloppaFan3925/Sandbox]] https://esolangs.org/w/index.php?diff=167671&oldid=167656 * Esolangist * (+451) /* Extensions */ 11:48:37 -!- pool has quit (Read error: Connection reset by peer). 11:50:38 -!- pool has joined. 11:53:26 [[Stopload]] N https://esolangs.org/w/index.php?oldid=167672 * Yayimhere2(school) * (+2074) Created page with "'''Stopload''' is an esolang created by [[User:Yayimhere]] based off of the [[I/D machine]] and [[Malbolge]], alike [[Muriel]] and [[Underload]], it needs to quine to loop, however it is propably much harder to do. All strings of ISO 8859-1 char's is a valid 11:53:35 yaaay! 11:56:48 [[User:Yayimhere]] https://esolangs.org/w/index.php?diff=167673&oldid=167625 * Yayimhere2(school) * (+15) /* esolangs */ 11:57:55 [[User:Yayimhere]] https://esolangs.org/w/index.php?diff=167674&oldid=167673 * Yayimhere2(school) * (+10) 12:00:14 [[User:Esolangist/Sandbox]] https://esolangs.org/w/index.php?diff=167675&oldid=167011 * Esolangist * (+76) 12:06:53 [[g]] https://esolangs.org/w/index.php?diff=167676&oldid=167561 * Yayimhere2(school) * (+2) /* semantics(g Normal) */ 12:08:05 [[g]] https://esolangs.org/w/index.php?diff=167677&oldid=167676 * Yayimhere2(school) * (+4) /* semantics(g Normal) */ 12:14:56 [[User:RaiseAfloppaFan3925/Sandbox]] https://esolangs.org/w/index.php?diff=167678&oldid=167671 * Esolangist * (+848) /* User:Esolangist */ 12:16:23 [[User:RaiseAfloppaFan3925/Sandbox]] M https://esolangs.org/w/index.php?diff=167679&oldid=167678 * RaiseAfloppaFan3925 * (+236) /* Core Modules */ Make the existence of the module a little clearer 12:20:47 [[g]] https://esolangs.org/w/index.php?diff=167680&oldid=167677 * Yayimhere2(school) * (+567) /* semantics(g Normal) */ 12:21:01 [[g]] https://esolangs.org/w/index.php?diff=167681&oldid=167680 * Yayimhere2(school) * (-54) /* odd rules */ 12:21:21 [[User:RaiseAfloppaFan3925/Sandbox]] M https://esolangs.org/w/index.php?diff=167682&oldid=167679 * RaiseAfloppaFan3925 * (+26) /* RaiseAfloppaFan's Stupid Idea 1 */ RSI1 is statically-typed. 12:22:25 [[g]] https://esolangs.org/w/index.php?diff=167683&oldid=167681 * Yayimhere2(school) * (+35) /* odd rules */ 12:25:07 -!- ais523 has quit (Quit: quit). 12:30:33 [[Stopload]] https://esolangs.org/w/index.php?diff=167684&oldid=167672 * Yayimhere2(school) * (+176) /* Semantics */ 12:35:42 [[g]] https://esolangs.org/w/index.php?diff=167685&oldid=167683 * Yayimhere2(school) * (-6) 12:44:32 [[,(*+)]] https://esolangs.org/w/index.php?diff=167686&oldid=167667 * Yayimhere2(school) * (+28) /* Computational class */ 12:54:21 -!- amby has joined. 12:55:24 [[Minimialized Programming Language]] N https://esolangs.org/w/index.php?oldid=167687 * PrySigneToFry * (+13484) Created page with "Minimialized Programming Language is designed by PSTF. It is really minimialized, and I will design the One-character version of it. = Definition = == Commands ==
 program     = { statement } statement   = if_stmt | while_stmt | l
13:12:03  [[Fuck'n]] N https://esolangs.org/w/index.php?oldid=167688 * Yayimhere2(school) * (+996) Created page with "'''Fuck'n''' is a [[brainfuck]] simplification based off of [[Unary]] and [[Underload]]. It is an [[OISC]] == Etymology == Fuck'n's name comes from Fuck and Unary combined. == Memory == Memory is stored within 5 unbounded cells on a circular ta
13:12:19  [[Fuck'n]]  https://esolangs.org/w/index.php?diff=167689&oldid=167688 * Yayimhere2(school) * (+1) 
13:13:02 -!- ehmry has left (too noisy).
13:18:19 -!- Yayimhere has quit (Ping timeout: 250 seconds).
13:20:22  [[RECT4n=GLE]]  https://esolangs.org/w/index.php?diff=167690&oldid=166413 * Yayimhere2(school) * (-19) add a note on how RECT4n=GLE measures how well formed a set of shapes are
13:25:28  [[,(*+)]]  https://esolangs.org/w/index.php?diff=167691&oldid=167686 * Yayimhere2(school) * (-155) /* Programs */ deleted the truth machine as its wrong
13:37:03  [[Ooh]] M https://esolangs.org/w/index.php?diff=167692&oldid=142524 * Ractangle * (-45) /* Python implementation */
13:48:07  [[Esolang:Introduce yourself]]  https://esolangs.org/w/index.php?diff=167693&oldid=167592 * Wuyugu * (+199) /* Introductions */
13:48:12  [[Stopload]]  https://esolangs.org/w/index.php?diff=167694&oldid=167684 * Yayimhere2(school) * (+0) Fix a weird comma
14:11:32 -!- DOS_User has joined.
14:13:04 -!- DOS_User has quit (Client Quit).
14:37:11  [[Stopload]]  https://esolangs.org/w/index.php?diff=167695&oldid=167694 * Yayimhere2(school) * (+87) /* Semantics */
15:15:43  [[T+Riangle]]  https://esolangs.org/w/index.php?diff=167696&oldid=165576 * C++DSUCKER * (+41) 
15:24:30  [[Karvity]]  https://esolangs.org/w/index.php?diff=167697&oldid=167626 * Yayimhere2(school) * (+905) Add a demonstration of the language!
15:28:07  [[Noddity]]  https://esolangs.org/w/index.php?diff=167698&oldid=167620 * Yayimhere2(school) * (+50) 
15:30:07  [[Karvity]]  https://esolangs.org/w/index.php?diff=167699&oldid=167697 * Yayimhere2(school) * (+102) 
15:30:38  [[Noddity]]  https://esolangs.org/w/index.php?diff=167700&oldid=167698 * Yayimhere2(school) * (+46) /* Memory */
15:31:14  [[Karvity]]  https://esolangs.org/w/index.php?diff=167701&oldid=167699 * Yayimhere2(school) * (+2) /* Commands */
16:17:54 -!- ais523 has joined.
16:27:37 -!- Lord_of_Life has quit (Ping timeout: 264 seconds).
16:28:25 -!- Lord_of_Life has joined.
16:32:47  [[Combine and continue]] N https://esolangs.org/w/index.php?oldid=167702 * Yayimhere2(school) * (+1438) Created page with "'''Combine and continue''' or '''CAC''' is an esolang created by [[User:Yayimhere]], created to make a church numeral based language, that is not actually [[Lambda calculus]] == Memory == Memory is stored on an unbounded stack, starting with an i
16:35:48  [[Combine and continue]]  https://esolangs.org/w/index.php?diff=167703&oldid=167702 * Yayimhere2(school) * (+118) /* Commands */
16:38:20  [[Combine and continue]]  https://esolangs.org/w/index.php?diff=167704&oldid=167703 * Yayimhere2(school) * (+0) /* Commands */
16:41:19  [[Combine and continue]]  https://esolangs.org/w/index.php?diff=167705&oldid=167704 * Yayimhere2(school) * (+98) /* Commands */
16:49:08 -!- pool has quit (Read error: Connection reset by peer).
16:49:26 -!- pool has joined.
17:23:39  [[Combine and continue]]  https://esolangs.org/w/index.php?diff=167706&oldid=167705 * Yayimhere2(school) * (+830) /* Commands */ Prove CAC turing complete
17:44:15  [[Viktor's amazing 4-bit processor]] M https://esolangs.org/w/index.php?diff=167707&oldid=167400 * TheBigH * (+967) added multiplication program
17:48:04  [[Special:Log/newusers]] create  * GolferHome *  New user account
17:49:28  [[Esolang:Introduce yourself]]  https://esolangs.org/w/index.php?diff=167708&oldid=167693 * GolferHome * (+225) 
18:04:08  [[QuantumGolf]] N https://esolangs.org/w/index.php?oldid=167709 * GolferHome * (+2762) Created page with "QuantumGolf is a [[QOO-OOKALAN]] extension for even shorter codes.  === Language Addictions ===  ==== Basic Syntax ====    // Assignment returns value (like JavaScript)   x = 5        // Assigns 5 to x, returns 5    // Implicit output: last expression is printed 
18:06:17  [[QuantumGolf]]  https://esolangs.org/w/index.php?diff=167710&oldid=167709 * GolferHome * (+135) 
18:06:41  [[Special:Log/newusers]] create  * QuoteDam!anquote *  New user account
18:07:37  [[QuantumGolf]]  https://esolangs.org/w/index.php?diff=167711&oldid=167710 * GolferHome * (+88) 
18:11:56  Hmm, do we have a platform that adheres to POSIX but has a NULL pointer representation that's not all-0 bits?
18:18:46  [[Esolang:Introduce yourself]]  https://esolangs.org/w/index.php?diff=167712&oldid=167708 * QuoteDam!anquote * (+270) 
18:20:18  [[TernaryDigitPointer]] N https://esolangs.org/w/index.php?oldid=167713 * QuoteDam!anquote * (+28271) i apologize this couldnt be more formal but present circumstances in my life make serious formulation rather difficult. love you esolangs ~~~~
18:20:32  int-e: you don't count C++ pointer-to-members, right? 
18:20:57  right
18:22:59  CHERI might come close but kind of for the wrong reasons (invisible tags in memory). Plus it's not fully conformant for more or less the same reasons.
18:23:34  I hope there isn't. all zero bits to represent null pointer is convenient. 
18:27:56 -!- Sgeo has joined.
18:28:12  and I think a different representation would break a lot of existing code that hardcodes that (unless perhaps there are multiple valid null pointers that the C comparison operators all compare equal and they all count as false in boolean context and the all zeros is one of them)
18:36:38  [[BytePusher]]  https://esolangs.org/w/index.php?diff=167714&oldid=165606 * Wlad * (+175) Add new BytePusher implementation
19:13:30  fwiw I think there are reasons to want pointers that have set bits in interesting places, like the top bit
19:13:47  so that they can be more easily distinguished from integers (especially in systems with "this is a pointer" bits like OCaml)
19:14:17  but that doesn't mean that NULL can't be all-bits-zero because normally you want NULL to be non-dereferenceable, so it's OK if it doesn't have a valid representation for a pointer
19:16:04  The entire belief that pointers are rows of bits is a quirk of Von Neumann machines. It's not a coincidence that this assumption fails precisely in Harvard arches like CHERI or WASM.
19:16:20  I have been thinking a lot about this today in particualr
19:16:39  I was thinking about the difference between shadow-capability models and tracing-capability models
19:16:51  Good Night!
19:17:24  It's akin to the belief that I've been quietly grapping with in Vixen, that a directory path is a bytestring, a UTF-8 string, or a list of path segments; but on a modern Unix, a directory path can be a file descriptor! Folks' difficulty in accepting this is why Capsicum was never merged to Linux.
19:17:28  APic: Peace.
19:17:37  (the former is systems like Fil-C and CHERI where the thing that makes the pointer a pointer is stored in a parallel set of memory somehow; the latter uses the equivalent of "GC roots" (although there needn't actually be a GC) and a state machine to know what a pointer is, sort of like a tracing GC but without the actual GC)
19:18:16  korvo: file descriptors are clearly the best way to represent directories – but it's fairly easy to go back and forth between the two representations in modern Linux
19:18:23  you can just write /proc/self/fd/10 or whatever
19:18:40  As opposed to e.g. Cello, I suppose? In Cello, a fat pointer is represented as a pair of pointers, and the GC interop is achieved by requiring all fat pointers to be *allocated* by libcello.
19:18:47  (I think there's even an abbreviation /dev/fd/10)
19:19:30  ais523: In many BSDs, there's a flag O_BENEATH or O_OPEN_BENEATH that allows open() on a directory to return a *restricted* descriptor. Doing an openat() or similar on this descriptor will fail if the path is not relative, or if it contains segments like "..".
19:19:40  korvo: Linux too
19:20:03  the RESOLVE_BENEATH option to openat2(2)
19:20:19  ais523: Kind of? The flag only works for a completely separate version of the syscall, called something like open2(), and it's not bound in glibc. So actually doing it on Linux requires a syscall().
19:20:19  oh, no, it's an option to a different syscall
19:20:30  the BSD approach does it when opening the directory, Linux does it when opening the file
19:20:50  you could still use seccomp or the like to force the flag to be given
19:20:54  Yeah. Gotta paper over that. There's a Rust crate, and it's part of the std::cap capability-friendly stdlib.
19:21:36  (I think it is correct to do this as defence in depth when using an object-capability model – having the kernel block things that don't use capabilities properly is nice even if your type system also does that)
19:21:59  This doesn't sound like a fun time though. I'd have to somehow show that Vixen objects can't allow user code to handle raw paths? Or perhaps I'd have to show that user code can't invoke certain syscalls? Either way it's daunting.
19:22:22  (Yes! See also pledge() and unveil() on some BSDs.)
19:22:30  both Linux and OpenBSD (and maybe some of the other BSDs too?) have a way for a process to prevent itself from ever using certain syscalls
19:22:39  seccomp on Linux, pledge on OpenBSD
19:22:58  but the BSD version is easier to use, Linux's is very general but a bit difficult to use because of that
19:23:34  Right. In capability theory, what we really seek is a system that has safe *loading* of untrusted user code; if the user can't ever instantiate a malicious object, then they can't possibly violate any security property.
19:23:48  also, if you use seccomp you can't subsequently exec setuid binaries (basically because if they could use the syscalls themself that would be a hole in the sandbox, and if they couldn't they might malfunction due to some of their syscalls not working)
19:24:12  And so Vixen's going to have to do the same thing that many cap systems do, where there's two kinds of pointers. There's low-level references that are unsafe, but the user can't touch; and high-level references that are safe and obey the cap rules.
19:25:02  I think the correct way to do loading of untrusted code is "it comes with a proof that it doesn't violate any of the capability rules and you verify it on load" (where the proof is ideally just types in an appropriate type system)
19:26:02  In E, low-level refs are Java refs and high-level refs are fat pointers of safe code and a closure to more refs. In Monte, low-level refs are RPython object refs and high-level refs are fat pointers again. But this pattern can't work for Vixen because a fat pointer containing a path still lets the user read the path; this is a problem in Nix too.
19:26:30  oh right, I also had a terminology problem
19:26:44  the thing that proves you have access to, e.g., a filesystem resource is called a "capability"
19:26:57  the thing that makes a piece of memory into a pointer and lets you dereference through it is also called a "capability"
19:27:19  Yeah, probably. In practice, we start by requiring the code itself to be highly restricted, usually equivalent to a simply-typed lambda calculus; cap safety is free there. Then we ensure that the loaded code only has access to *tamed* resources, which have been structured to preserve caps. And we have to take away stuff like timers that seem harmless.
19:27:27  this is OK as long as you're only dealing with one of those at a time, but trying to think about both at once is confusing and I've been looking for a clear way to distinguish
19:27:56  (they are clearly connected concepts, but a little different in nature and in most cases substantially different in implementation)
19:28:04  As Arlo Guthrie put it, "Officer Obie wanted to make sure that we wouldn't hurt ourselves in the jail cell. So Obie took away our belts so we couldn't hang ourselves, and our shirts so we couldn't strangle ourselves, and even the toilet seat so we couldn't hit ourselves over the head with it."
19:28:19  some real-life prisons actually do do that sort of thing
19:28:40  Right. The capability is the *reference* and the resource itself is an object/actor/machine/etc.
19:29:25  I guess it helps if your file descriptors are Windows/WASM-style opaque-numbers-that-look-a-lot-like-pointers rather than POSIX's consecutive integers
19:30:00  Yeah, we usually require a capability representation to be *unguessable*, which is a truly bad word but better than "very-hard-to-guess-able".
19:30:03  because then you can make them not collide with actual real pointers you can store through
19:30:22  korvo: oh, I'm surprised, I thought you would use the type system to make them unforgeable
19:30:43  This is actually kind of nice for Vixen though, because we can say that the calling convention includes a *row* of FDs, starting with the standard three and optionally adding more. Just like how we can pass additional argv by appending them to the end, we can pass additional FDs in a little stack.
19:31:36  (I believe that, given the number of speculative execution vulnerabilities that have been discovered and the rate at which they are still being discovered, there are almost certainly a large number of such vulnerabilities that aren't publicly known, some of which may be known to adversaries – and as such, with today's processors, unguessability is probably unwise to rely on)
19:31:38  ais523: Some languages do that. Pony's a good example. It's got like six different kinds of modifier for pointers, and the type system strongly restricts how pointers can be casted. They ended up incorporating a fair amount of Rust's thinking IIRC.
19:32:16  Wyvern's another decent example. They have dependency injection for global concepts; if you want to write an HTTP handler but not an HTTP server, you can write just the handler and the type system will wire it up for you.
19:32:20  Rust is a mix of things that are only incidentally there and could easily be different, and some fundamental insights about programming
19:32:40  "exclusive references are useful" is one of the fundamental insights, I think
19:33:02  I realised that today, because I was thinking about casts between pointer-to-pointer and pointer-to-integer
19:33:04  (I don't know why most cap languages are named after animals. The pattern has never stopped, though; E was originally Joe-E, both a coffee and "joey" pun. Monte is homophonic with Lojban {manti}, "ant".)
19:33:38  in almost all memory-safe language, these either can't be allowed (for semantic reasons) or are permitted but don't actually work correctly
19:34:20  whereas in Rust, the cast is safe as long as you have an exclusive reference, and write through it before reading through it
19:34:34  and I was trying to work out where the difference was – it's purely the exclusive reference that makes it work
19:34:39  Or they do something silly. In cap theory, a *c-table* or *cap table* holds pointers for users, since users can't be trusted to do bad things. Instead, the user gets a reference into the c-table. Examples range from the kernel's row of per-process FDs to ECMAScript's WeakMap.
19:35:19  that reminds me of WebAssembly's function table, which I think is similar but not quite the ame
19:35:21  *same
19:35:39  (WebAssembly doesn't really have function pointers, but you can use indexes into the function table as a substittue)
19:36:06  Further, a *powerbox* is a set of pre-delegated powers that are already packed into a c-table. We usually assume that the user has to *know* the keys for a powerbox before it will do anything for them; keys are unguessable in WASM or Nix, or unforgeable in ECMAScript's WeakMap.
19:37:02  And yeah, WASM starts each module with a powerbox of imports and other stuff. The runtimes like wasmtime include tamed POSIX syscalls in the powerbox. I think that the fullest example of all of this was CloudABI, an also-ran for Capsicum that I think is now defunct.
19:37:39  A variant would be to store a generation number with each reference into the table as well; Free Hero Mesh does this (although this is an internal representation and not exposed to user code, which only sees references to objects without knowing their internal representation). (Free Hero Mesh also uses 0 for null pointers, even though non-null pointers are distinguished from integers.)
19:38:14  one of the things I want to do is write my own interact-with-the-OS library, sort-of like the OS-interaction parts of libc, but with a very different interface
19:39:04  What kind of different interface?
19:39:14  it would be designed to be compatible with object-capabilities but I would want to make other changes too (e.g. supplying a solution to the heterogenous select problem, and being compatible with asynchronous interfaces)
19:39:44  like, you could start a write and two reads and then select on any of those completing, or signals arriving, or timers expiring, or a directory being changed, or anything else of that nature
19:40:38  I had thought of that, although in the context of redesigning the entire operating system and computer rather than working with existing systems.
19:40:56  this interface is compatible with old-fashioned POSIX (not async, you use pselect and maybe threads if you have to), with nonblocking IO, with async IO, and with io_uring
19:41:39  but it would be so much more sensible than what we have at the moment, where system calls are able to block on random subsets of things and there isn't a clean, simple way to just block on any set of things
19:42:14  All of the things you mentioned would be implemented using the same system call (and there is no distinction between timers, directories, files, etc; signals might be distinct if necessary but the others would just be capabilities with the same system call interface as any other)
19:42:29  (Linux has been moving towards a model of being able to convert arbitrary things you want to wait on into fds, and using epoll to block on them all at once ? but it doesn't quite work for everything, e.g. they couldn't make futexes work with it even though they tried)
19:43:10  oh no, somehow my client's encoding has changed away from UTF-8 and I have no idea where the setting is to change it back
19:44:16  testing – áéàè
19:44:20  that's better
19:44:48  ☢
19:49:24 -!- pool has quit (Read error: Connection reset by peer).
19:49:35  There was a quite interesting thread on that topic recently on Lobsters: https://lobste.rs/s/ko5i9y/if_you_could_redesign_linux_userland_from It turns out that there's a very real distinction between changes that are willing to negotiate syscalls and changes that take the syscalls as they are.
19:50:14  zzo38: Have you looked at seL4? I regret not actually putting time into it, but it seems like they got all of the capabilities done right.
19:51:30 -!- pool has joined.
20:01:06  korvo: I think it's OK to leave the kernel's system calls as they are, but there should be an API layer in between them and userspace that enforces sensible usage
20:05:26  I have seen seL4 and my ideas have some similarities but also differences
20:12:38  korvo: your link reminds me of another thing I wanted to do: having command-line arguments grant capabilities
20:12:46 -!- tromp has joined.
20:13:01  i.e. a program can't naturally read files, but can if you specify them as command-line arguments (this would need some rules for when a command-line argument was a file and when it wasn't)
20:13:36  the nice thing is that I think you can do that in a way that's mostly compatible with programs that don't understand the convention
20:15:21  (the hard part is allowing programs to read the dependencies they depend on, although I think that's regular enough to be special-caseable)
20:20:25  ais523: The trick is to understand that a string can still grant an unguessable capability, as long as it's in some hyperbolically-large (and thus exponentially expensive to search) space. Doesn't work for Realtalk/Dynamicland books, which are in Euclidean space; but it *does* work for URLs. There's a W3C about this: https://www.w3.org/TR/capability-urls/
20:21:05  korvo: oh, I was thinking in terms of user interface as used by humans, rather than in terms of program-program communication
20:21:36  you don't need to use unguessable strings when you can just say /dev/fd/10 or whatever (which is guessable, but won't work if the capability hasn't been given)
20:23:19  It's too bad that we can't name capabilities easily when we pass them. I was thinking about using envp; there'd be an envvar like MY_CAP=42 and a passed FD 42. But that feels like too much of a hack for some reason, even though envp's part of the process calling convention.
20:24:38  No wonder that big message-passing actor systems (gRPC at Google, Workers at Cloudflare) use some sort of extremely restricted flat-buffer format (PBs, Capn Proto). Slightly less of a wonder that Capn Proto explicitly has a "capability" type which is just for opaque pointers but comes with calling-convention rules for networked usage.
20:24:50  a related idea I've had for a while is that of a "typed main()" where the entry point to a program gets to choose its own arguments and types for them, rather than being a list of strings
20:25:09  and this would include the capabilities that it needs
20:25:31  then there would be some automated way to translate this into a command-line argument parser so that humans could use it
20:25:59  Wyvern does that although I don't remember the syntax. Monte did it in a way that was optimized for human auditing; just read the main() directly: https://github.com/MostAwesomeDude/airbrus/blob/master/airbrus.mt#L102-L107
20:26:27  (This is an IRC bot but the principles are fully general. I also did some TUI widgets, distributed raytracing, HTTP, etc.)
20:27:12  korvo: ooh, so I wasn't the first person to have that idea, that makes me more confident that it's a good one
20:28:24  ais523: In the Bun runtime, which is like an ECMAScript dialect, there's CLI switches to disable various caps, so that if main() asks for a disabled cap then it'll immediately crash. pledge() in argv, basically. I want to say that wasmtime has that sort of thing, too, but I'm not sure.
20:29:11  It's a really cool fusion of ideas. The cap says what you *can* do, but the constraint/context says what you *can't* do, and the runtime never lets the cap violate the constraint.
20:29:11  korvo: right, that's equivalent to just not passing the argument in
20:29:30  and in most programs that gives you a usage error
20:30:04  Oh! Fil-C does this too. People have been talking about data racing and ragged/torn pointer accesses. The upshot is that Fil-C's fat pointers basically are cap/context pairs, with the cap being a plain pointer, and the language's safety is relative to the context rather than the caps.
20:30:37  ais523: Exactly! Monte literally raises the *same* key-not-found error that it would raise for an ordinary map lookup. I think it *is* an ordinary map TBH.
20:31:28  korvo: your terminology here contradicts the standard, most people call the shadow part the capability (the part in main memory is called an integer part or an address)
20:31:52  but right, it's the same concept
20:35:14  Yeah, I think that it's a consequence of being on the other side of memory-safe-by-default. It's possible in Python to sandbox an imported module s.t. it won't corrupt memory, but all of the issues of improper access are still there, and Python can't be sandboxed in general without removing most of the object model.
20:39:39  In the E framing, a fat pointer's got a "script", which is like all of the compiled methods, and a "closure", which is just a list of caps. These are both machine pointers, and improper access is prevented wholly by the script being safely-loaded code. So to even have access to an E system is to be limited by these safety rules and never mishandle a pointer.
20:40:21  In the CHERI framing, though, the code can literally have any sequence of bytes and instruct the machine to do anything whatsoever. So of course the cap and the pointer are distinct, because the instructions are about pointers and not caps.
20:41:21  I've always said that Nix is what we call a *transitional* cap-aware system. It can, when restricted to a certain view, be cap-safe; but really that depends on a discipline where we never look under the hood at the actual path. Vixen would be like this too. But also so is Apache when it's got a webroot; path traversal is generally not okay.
20:41:44  so I think there are two main distinctions here: a) shadow capabilities versus tracing capabilities, b) pointers being one machine word versus two machine words
20:41:56  So maybe there's a sense of *path-safety* that we haven't quite figured out, s.t. cap-safety implies path-safety but not vice versa.
20:42:09  korvo: this is the same problem as SQL injection I think
20:42:35  it is certainly possible to have sound programs that use string concatenation to substitute into their SQL, they just have to be super-careful to escape properly
20:42:38  that's what Apache is doing with paths
20:43:03  Isn't SQL injection about quoting? The problem here is that somebody could guess that a Nix store has a particular (common version of a) package and does a Living Off The Land setup.
20:43:11  but using parametrized queries is better, because then there's no chance that you forget to escape something and input gets interpreted as code
20:43:39  korvo: yes, but Apache is similar – I think it works by parsing the path to look for suspicious combinations of ../ and the like
20:43:52  which isn't quite the same problem as quoting but it has essentially the same solution
20:43:58  The biological model I've been thinking of is not viruses or bacteria but *obelisks*, very recently discovered RNA-world fragments. It's possible and common for a script in the Nix store to just wrap another script, setting the environment and etc.
20:44:52  ais523: Yeah. We could analogize that to a form of memory-safety where it's possible to canonicalize a pointer, and relative paths are like segmented/etc. pointers. So path traversal is like pointer forgery.
20:45:09  right
20:45:30  the distinction is between an environment where capabilities *can't* be forged, and an environment where capabilities *aren't* forged
20:45:37  (they could be, just the code chooses not to do it)
20:46:01  you can make the latter into the former with a sufficiently powerful static analyser
20:46:24  Oh no. I hate this distinction. This is one of those things that I don't like at all. In Lojban, we call it {poi} vs {noi}; when is something logically constrained/restricted from occurring, vs. just coincidentally happening to never occur?
20:47:04  I don't like this because AFAICT there's no *logical* basis for telling these two environments apart. This has kept me up at night.
20:47:28  …and I've just realised that we've spent like 30 out of the last 40 years of programming trying to make the latter better rather than concentrating on the former, and that makes me sad too
20:48:00  I get what you're saying. We're talking about environments that are safe because they were correctly programmed, not because they were proven correct with a construction.
20:48:18  I think Chinese has this distinction too, there are 4 or 5 words for "not" and one of the distinctions made is this one
20:49:31 -!- pool has quit (Read error: Connection reset by peer).
20:51:35 -!- pool has joined.
20:52:51  and yes, this is about partial proofs I think – it is easier to prove that a program obeys certain rules than to prove it entirely correct (especially as the latter needs to you have a spec, and somehow be confident that the spec is correct)
20:53:27  a program can be programmed, by a sufficiently skilled programmer (which may not exist in practice), to obey the rules even if nothing is enforcing them
20:54:04  but it is better to have something that enforces the rules, ideally at compile time or even better library-check time, although runtime is better than nothing
20:54:11  ais523: Okay, so now I'm thinking about what a CHERI/Fil-C model for paths would look like. Absolute path access would have to be banned, I think. openat() and friends would work for passing around relative path fragments. Some sort of path importer might make sense; I think Fil-C has something like this, where an untrusted pointer (absolute path) can be runtime-checked (path-parsed) in the context of an existing cap (path prefix) to cast it
20:54:25  to a safe pointer (relative path + prefix).
20:55:31  so Fil-C's basic primitives are the same as the ones that Rust provides, and a subset of CHERI's (CHERI has a capability narrowing primitive, Fil-C doesn't meaning that it can't catch allocation-internal buffer overflows, Rust currently sort-of does but only by accident and there are plans to remove it)
20:56:04  To prevent a program from trying to repeatedly reinterpret a path against multiple different caps, I think that a failed cast would mean exit(). This is basically what we do in Python or Apache against path traversal.
20:56:28  that reminds me, I meant to argue that Rust would benefit from a capability narrower even though the only thing it would do in present rust is to add undefined behaviour, because that allows sanitisers to take advantage of the undefined behaviour to catch internal buffer overflows
20:57:23  korvo: well, the brute-force approach only works against probabilistic defences – I prefer determinstic defences for other reasons, but they'd also help in that situation
20:57:36  the issue with trying to block brute force with forced exits is that there are so many potential loopholes
20:57:54  like restarting the process, or spinning off daemons to do the brute-forcing, or the like
20:58:17  (and you might not want to take down the whole process if it's, e.g., a web server process that serves tens of thousands of concurrent users)
20:58:28  Monte doesn't have narrowing, but Monte has E-style auditing and transparent forwarding, so has other ways to attenuate caps. Vixen ought to have narrowing; I'm thinking of cribbing from zope.interface, which allows dynamic casting to an interface which can hide unrelated methods.
20:58:56  I think OpenBSD has some sort of rule along the lines of "if a setuid process hits a runtime security check, its effective user can't run setuid programs for 15 minutes" as an anti-brute-forcing measure
20:59:20  Well, just like with pledge(), we want violations to exit() because they signify that a contract has gone horribly wrong. I'm mostly thinking of Windows programmers who will search fifteen different locations for DLLs.
20:59:38  Oh wow, TIL. That is hilarious.
21:01:40  My system does not have "command-line arguments" (it has an "initial message" which is similar, though). The initial message is not text, and can include capabilities; you do not need to use text to grant capabilities, but instead can pass them directly.
21:02:23  ais523: Oh, I suppose E-style auditing is relevant. In E and Monte, and also OSs like KeyKOS and Genode, it's possible for one object to certify another object as having some structural property. This means that there's an auditing protocol which allows objects to consensually inspect each other.
21:02:57  zzo38: what is the interface for humans to start programs like?
21:03:26  korvo: now you've got me thinking about internal vs. external debuggers
21:03:46  KeyKOS has the most interesting one to me. A running "tenant" process can have an "apartment". If the "super" (superintendent? supervisor?) wants to inspect it, then the tenant receives a signal and gets some time to put their apartment in order before the inspection. They also have some limited rights during the inspection!
21:03:48  i.e. debuggers that try to work inside the capability system, versus debuggers that think in terms of VM internals and can just ignore capabilities
21:04:25  korvo: I'd be interested to know what the applications for that are
21:04:36  Multiple interfaces are possible, but the main one would be CAQL (Command, Automation, and Query Language). One part of the program file specifies the expected type of the initial message, so that the CAQL can do the necessary type checking and conversion as appropriate into the byte/capability sequence.
21:05:15  zzo38: Same idea in boot-to-Monte scripts that we never shared publically. Instead of starting a Monte REPL, start a Monte module; load the module into memory, start the JIT, and invoke the module's .run() method with argv, envp, all the usual goodies.
21:05:55  You could type an expression which evaluates to the appropriate capabilities and functions and files, or can copy them from other windows (using the mouse or using key combinations involving the [System] key or both), or a combination of these.
21:06:12  zzo38: OK, that's a bit different from what I was expecting but it does make sense
21:06:25  Microsoft have Powershell as a similar sort of interface
21:07:05  ais523: KeyKOS was very early on, and just like early cap machines (Burroughs S500 or whatever it was called?) there were a lot of skeuomorphisms that didn't make sense to carry forward. Back then, memory spaces were more uniform; the extreme of this was IBM's mainframe (390?) that structured *everything* as a relational database.
21:07:26  my plans were more along the lines of "when you install a program you specify capabilities that you are willing to grant it every time you run it, if you have them yourself" and then for any capabilities you don't grant it (but it needs) you have to specify them manually
21:08:02  and also to make the manual specification as easy as possible, e.g. an "open file" dialog box would allow you to both choose the file and grant the program permission to access it (as you would always want to do both together it would be combined into a single button, with an icon showing that you were granting a capability)
21:08:08  ...Sorry, that was an unhelpful history answer. Apartments make sense when you're running untrusted code. Think about how a modern cloud VM works; it has a similar inspection mechanism, usually delegated to the person renting the machine but also usable by the datacenter ops.
21:08:43  korvo: my cloud VM's equivalent of that is the serial console, but maybe it's old-fashioned
21:08:46  Actually I suppose it has *two* layers! A cloud *machine* in the rack is like an apartment, and the *VM* on the machine is also like an apartment. They have the same super/tenant relationship.
21:08:51  You would be able to do that with my system too, and the package manager would probably include that function; e.g. you could create your own function that calls it with the appropriate capabilities, if the file that defines the alias contains those capabilities to be granted.
21:08:59  (I assume the serial port is also virtualised)
21:09:45  ais523: A little. When I was working in a datacenter, we still had the idea of "pulling disks" on the hardware. We were just getting started with big VMs, we were doing Ganeti and Vagrant, and we didn't see the point of VMs. It was bare metal for customers all day.
21:09:56  korvo: it took a very long time for the world to settle on the current "flat memory model with an MMU enforcing permissions" design for CPUs
21:10:03  and although it is consensus, I also think it's wrong
21:10:25  But even then, if we needed to go pull a machine from a rack, we'd first ping the owner on IRC to make sure that they were cool, give them some time to settle daemons and park disks and even $(shutdown), and *then* pull the machine for screwdriver time.
21:10:41  I think VMs only started making sense fairly recently
21:11:01  because the bottlenecks have changed over time
21:11:33  As Fred Durst memorably said, "It's all about the para-virt hyper-virt cloud shift".
21:11:40  a little over a decade ago, I was teaching a course in operating systems development (which was mostly writing Linux kernel modules)
21:11:59  we tested the students' programs on bare metal and reimaged the computers afterwards
21:12:44  Lore is that Google was first to containers, figuring them about about a decade ahead of everybody else. (I'm allowed to share this.) Lore is that from 1998-2008 Google believed containers were a trade-secret competitive advantage.
21:12:47  I'm not sure what decision caused that policy, rather than using virtualisation
21:13:03  (I wasn't involved in it, there was probably a good reason but I don't know what it was)
21:13:42  IIRC there's a paper from like 1988, 1989, that has an explicit proof that a CPU only supports safe paravirt/hypervirt when its ISA's instructions cleanly decompose into one of several safe possibilities. I don't recall the authors or title but it's pretty influential in CPU design.
21:14:04  it's kind-of shocking how much containers are like VMs in practice despite being almost entirely unrelated technologies implementation-wise
21:14:42  So lore is that during the 90s Intel slowly adopted the lessons from this paper and then Google implemented containers basically as soon as the ISAs could safely do it. Whether this is true or not, TBH sounds kind of extraordinary to me. But it *does* have good historical support.
21:15:26  I think of containers as more needing kernel support than hardware support
21:15:48  like, the only thing you really need from the hardware is a decent MMU, and maybe the ability to trap on a few problematic instructions
21:16:00  ais523: TBH it might just have been standard Linux practices. I did bare-metal for Linux driver development and VMs were never in the discussion. For GPUs, VMs were mostly involved because VMWare wanted to do GPU passthrough, and they had their own internal folks writing the VM drivers.
21:16:07  virtual machines need a bit more, but still not that much
21:16:29  korvo: now I'm wondering whether it was to make life easier for the students
21:16:44  so that they wouldn't have to worry about whether they were inside or outside the VM
21:17:15  It certainly wasn't to make life easier for the TAs, sounds like.
21:17:32  oh no, it was actually pretty easy for me, especially as I didn't have to do the reimaging myself
21:18:15  and I was already used to walking around computer labs, there are loads of reasons a computer science TA has to do that
21:19:19  Datacenter theory on the ground definitely hasn't caught up with economics of the cloud. I remember a boss whose main standard for whether a machine was being used well was whether the CPUs were pegged; we had a two-wrongs-are-right situation where he thought that a Python script was efficient because it pegged multiple cores.
21:20:01  But the cloud wants us to think of compute as a time-based unit that comes in discrete parcels and which we generally want to minimize. Totally different paradigm.
21:20:04  this is a direction-of-implication fallacy, right?
21:20:18  an ideally efficient program would be both CPU-bound and I/O-bound at the same time and thus would be pegging all the CPUs
21:20:36  but, just because a program is pegging the CPUs that doesn't guarantee that it's efficient
21:20:54  Ha, for sure. I think that for them it was even simpler than that: they paid for the machine and therefore they are gonna *use* that machine.
21:21:26  Especially when the university pays the power bill, in that situation.
21:21:45  I still remember being depressed by looking at a big compile with proprietary software and seeing that all four of the computer's cores were at 25%
21:22:05  like it was trying to spread the workload among cores but wasn't very good at it
21:23:38  seL4 has separate system calls for send, receive, wait. etc. My idea is that send, receive, wait, yield, locking, and transactions, are all the same system call, which can do all of these things at once. (There might be a small number of other system calls, although there also might not be needed; it is not sure yet.)
21:24:21  (This way, you can avoid some problems with needing to wait or send or receive each before the other that the order cannot be resolved, by instead specifying all of them simultaneously.)
21:24:49  zzo38: Yeah. I wonder what io_uring might look like for seL4. The kernel could have a sort of return-to-uring semantics that looks like a little bytecode interpreter, repeatedly dispatching messages without actually letting user code run.
21:32:59  a ‘typed main()’ where the entry point to a program gets to choose its own arguments” => what the, did zzo38 infect you somehow?
21:33:23  b_jonas: I came up with this on my own! although I'm not so surprised that zzo38 feels the same way
21:33:37  not just for that line but the rest of what you said about operating system interface design I mean
21:34:06  last time this topic of conversation came up I was surprised how much everyone in the channel was agreeing with each other
21:36:04  Note that if a program expects a capability of a specified type, it is also possible to specify any capability with the same interface. (You can also specify the low-level representation directly, but in that case the program is unlikely to work if it is incorrect, and might even crash immediately (although this will not cause the rest of the system to crash).)
21:40:23  ais523: Well, we're all from the same Unix-y tribe here: syscalls are good, files are decent but not universal, processes are a reasonable unit of work for most purposes. If anybody from the Inferno/plan9 tribe were here, they might say that we're completely wrong.
21:40:34  Well, maybe they'd have interesting things to say about paths even in that case, actually!
21:40:59  korvo: I care somewhat about progressively upgrading existing systems
21:41:18  I'd love to be able to replace the whole thing at once, but realistically I am not going to be able to write all that code at once and nobody would adopt it
21:41:27  so, whatever I come up with, it has to be able to mix with what we already have
21:42:02  and processes make a good abstraction boundary for doing that, because the existing software already understands and respects them
21:42:52  Yeah. That's basically why I stopped working on Monte. The E approach is too totalizing. It makes sense if you've heard of Toontalk or seen any of the virtual worlds that Disney has built; E was born from a hope that a single cap language would be the way that everybody negotiates smart contracts in the metaverse.
21:43:01  My own idea does not have file names and directory structures (although there are files), and reduces the number of syscalls, so there are these significant differences from UNIX. There are also differences with the user programs, such as it does not use Unicode, and the l10n and i18n is entirely different from existing systems, and the window management is different, etc.
21:43:46  likewise, whether or not files are a good abstraction, they're what we have and you need to be able to understand them to interoperate
21:43:46  And then, there would also be the hardware differences, such as tagged memory, a different keyboard than PC and Mac, a dedicated keyboard port (not using USB), connecting the mouse through the keyboard, etc.
21:44:05  “OpenBSD has some sort of rule along the lines of ‘if a setuid process hits a runtime security check, its effective user can't run setuid programs for 15 minutes’” => am I the only one who thinks that set?id programs are a historical thing that we should phase out and eventually start to forbid in our file system settings or kernel settings or something because they're a bad idea, and we should 
21:44:07  Implementation within other systems may be possible by the use of emulation, though.
21:44:11  replace it by the user sending a request to a process that's already running with the desired effective user, because an execed set?id program inherits all sorts of process state from its execer and it's hard to sanitize all of them?
21:45:03  b_jonas: I don't think so
21:45:26  I have something of a pathological and irrational hatred of constantly-running daemons, though, so I'm biased
21:45:27  b_jonas: Yes. s6 enables this sort of thing. In particular, there's a Nix distro called "sixos" that has just one setuid binary, doas.
21:45:30  b_jonas: I think that setuid is not the best idea but you would have to change the rest of the system too. Existing systems don't help much because it is still POSIX
21:45:44  (I find it hard to justify this and it may have been one of the things that indirectly caused the NH4 devteam to break up)
21:46:31  if you want to pass capabilities to the set?id programs, we now have a way to pass them to unrelated processes through a unix domain socket, which is much more precise then just having them inherit *every* obscure state that a process has in the operating system
21:46:56  ais523: Using the Smalltix convention, so that a long-running process is the stack frame for a long-running method activation, perhaps you'd be interested in E's "no stale stack frames" rule. It has other names, but that one stuck because it's so descriptive.
21:47:21  Yes, a unix domain socket is better, although some things are difficult due to the existing working of the system, which does not handle user permissions in that way.
21:47:54  E doesn't allow stack frames to be suspended. It doesn't have any way to generate a coroutine or iterator; users have to explicitly close over an iterator's state. So a stack frame can never be "stale"; it can never be in a state besides "active" or "about to be reaped".
21:49:48  “virtual machines need a bit more, but still not that much” => not that much in theory, but they need nested paging which is a performance nightmare for processors to implement I think
21:50:04  The obvious analogue is uninterruptible sleep, but maybe there's a more general concept of "no stale long-running processes" where a daemon has to be *doing* something in order to be resident. s6 has ways of parking FDs, and there's ye olde ipcd on basically any supervisor.
21:51:14  “the cloud wants us to think of compute as a time-based unit that comes in discrete parcels and which we generally want to minimize.” => yes, but only if by compute you mean mostly RAM allocated times time, because that seems the most expensive part in practice, more so than CPU use
21:52:56  b_jonas: No, I mean CPU. When a cloud orchestrator like k8s "allocates" a container, it's allocating CPU time on the scheduler. k8s promises to only use a certain amount of compute per node, but it really is allocated. RAM is also allocated this way, but it's a distinct resource.
21:54:45  Oh, I see what you're saying. Yeah, the most expensive resource has depended on market phenomena. Bandwidth is always expensive. Disks were expensive for a while after that one tsunami on Thailand. GPUs and SSDs were both expensive when they were first rolled out.
21:55:19  ais523: they don't have to be constantly running demon*s*, this is the case where systemd or something like a traditional inetd or webserver is useful, you have one program running as root that users can configure to be able to invoke any demon, and that top-level program is in a clean process state
21:55:22  korvo: to me, "no stale stack frames" is kind-of the default because I don't have a lot of experience with langauges that do let you suspend them
21:55:38  b_jonas: ooh, I see, a sort of local inetd
21:56:13  Trying to remember what you usually work with. Go, maybe? Anything with "segmented", "suspendable", or "copyable" stacks is suspect.
21:56:37  korvo: initially C and Perl, more recently Rust but generally synchronous and single-threaded Rust
21:57:17  And yeah, after doing so much Python and then learning E, I can't go back either. It's just...why would you call Somebody Else's Code, giving them *your* control of execution, and just *hoping* that it comes back to you?
21:57:37  Rust does have generators internally but hasn't figured out the interface to them or all the safety aspects yet; it also has async/await which gives you suspendable things that are vaguely like stack frames, but they're compiled into state machines and don't actually use the stack
21:57:58  and this has been quite controversial and doesn't really integrate into the language well
21:58:13  it's there because people needed it and the theory behind it is probably really interesting but hasn't been worked out yet
21:58:15  IIUC Rust async/await uses Pin under the hood? So it's not doing anything nasty. It's not any worse than lambdas.
21:58:59  yes, it's just sugar for a state machine, the only magic is that it can contain pointers to itself (which isn't normally allowed in Rust) and Pin is needed to make that safe
21:59:45  I realised fairly recently that this could be used as a way of defining the semantics of a self-referential Rust object, via representing it as a state machine with only one state
22:00:13  Closing over *values* is fine and safe, closing over *control flow* is probably not okay. E continuations are delimited; when their associated frame is reaped, they go inactive. They're also single-shot, so that they can only interrupt Somebody Else's Code *once* and can't forcibly make Somebody Else's Stack Frame go stale.
22:00:44  ok, then at least I have one weird operating system design belief
22:00:49  so one of the big problems with Rust async is that the state machine is an object, which means you can drop it
22:00:55  you all seem to have much more
22:01:26  and this is similar to the stale stack frame problem but different in that it behaves more like an unwind than a leak
22:02:51  b_jonas: I got radicalized by capability theorists. Honestly it's a miracle that I'm not doing blockchains.
22:03:48  `addquote  ok, then at least I have one weird operating system design belief   you all seem to have much more
22:03:52  1337)  ok, then at least I have one weird operating system design belief   you all seem to have much more
22:03:58  oh wow, great quote number
22:04:23  Monte has external iterators because internal iteration requires the user to trust Somebody Else's Collection.
22:05:01  sorry, I don't mean it as an insult, on a channel about esoteric languages people *should* get all sorts of strange operating system design ideas
22:05:06  I'm not convinced that "the best iterator interface" has been figured out yet
22:05:08  b_jonas: I know you don't
22:05:12  I thought it was an excellent summary
22:05:16  and funny at the same time
22:05:38  (out of interest, which weird belief is yours?)
22:06:06  b_jonas: I appreciated it! I *know* most of my beliefs are not mainstream, but I don't always have a good measurement for *how* radical they are.
22:06:38  the belief that unxi set?id programs are a bad idea because exec makes a process inherit too much state that is hard to sanitize
22:07:00  b_jonas: ah yes
22:07:03  I don't tihnk that's that weird
22:07:19  Like, in 2017 in https://corbinsimpson.com/words/globe.html I wrote a paraphrase of the standard reply that I got from people who *understood* caps fully: "That sounds like a very interesting project. It sounds too elegant and experimental to see much use, though." and "Your ideas are interesting and maybe you could find a professor willing to take on you and your project."
22:07:30  If a new computer is designed to have too much compatibility with others then this can limit any of the newer benefits that are added (and can also have other problems such as sexurity issues in some cases), which is one reason to avoid it; emulation can be used (in either direction) for cases where more compatibility is desired.
22:07:58  Now less than a decade later these ideas are so mainstream that they are getting into CPU design for the first time in decades. I don't feel like I shifted much since then!
22:08:59  I remember unexpected bugs because some parent process execed a program with a signal blocked. Many programs that want to exec on unix already pre-fork, make the child do all the real work and have the parent do the fork-execs, because it's hard to make sure that the fork-execed don't accidentally inherit the wrong state. There are multiple libraries to help you in this. 
22:09:02  one thing I have realised is that an "is this a pointer?" bit is actually really useful – I am less convinced of the value of shadow capabilities though
22:09:23  but the pointer bit makes GCs much simpler and probably more efficient too
22:10:07  b_jonas: I think that your justification is a little weird, but consider that for distros the argument is more like "setuid is bad because it requires our installer to do extra steps" or "setuid is bad because our immutable distro is fundamentally incompatible with setuid semantics". At best it's like "setuid is bad because malware can Live Off The Land".
22:10:29  So maybe your justification is too sane for distro development!
22:10:36  b_jonas: OK, so I had a problem related to that – I was thinking about passing capabilities to child processes, and thinking of a model of "everything is opened CLOEXEC by default and we dup-as-non-CLOEXEC in the child after forkign"
22:10:55  and then was trying to work out how to soundly combine this with vfork
22:11:25  and this doesn't seem to be a mainstream belief, because unixes are starting to use sudo, which is specifically a wrapper to centralize part the hard work of sanitizing the inherited process environment for a set?id program. not all parts of course, some have to be done in libc, and you can't *really* sanitize everything, for the same reason as you can't have a webserver plugin or antivirus remove the 
22:11:31  "unsafe" parts of requests, and if you try you just get those silly things like when you can't type a less-than sign into a webforum because the plugin thinks it's an XSS attack
22:12:38  b_jonas: "starting" is wrong, they're gradually moving away from sudo in favour of less ridiculous replacements
22:12:58  from my point of view, like the only security benefit of sudo is having each user use a separate password to elevate to root
22:13:04 * korvo imagining: affine file descriptors
22:13:17  (and needing to log in as a user first before becoming root)
22:13:29  all its other features are just security snares, and some of them are ridiculous
22:13:48  ais523: at least the part that everything is opened CLOEXEC by default and you explicitly fcntl them to non-CLOEXEC when needed is I think pretty normal. non-CLOEXEC is just the historical default that's hard to change.
22:13:57  ais523: that's true, that is a good thing about sudo
22:14:05  I think other people are noticing that too, there have been a spate of less featureful sudo replacements recently
22:14:51  b_jonas: so the problem with dupping in the child is that dup returns a file descriptor, which under POSIX rules you can't actually store anywhere after calling vfork
22:16:13  I would hope that a collaborative document and discussion can be made for the system I intended to design, and then it can partially or fully be made (and the parts might be made indpendendently, or similar ideas on other systems (which can be similar enough to be interoperable with some parts)), either as emulation or as FPGA or as hardware (or a combination of these), etc.
22:16:20  ais523: in theory posix_spawn is trying to solve this because a wrapper in libc can break that rule by using architecture-dependent magic,
22:16:29  but I'm still not sure if I like posix_spawn or not
22:16:35  b_jonas: that was my thought too
22:17:08  then I realised a) the reason I was stuck on this in the first place was for writing a libc alternative, so I wouldn't be able to use posix_spawn anyway and b) posix_spawn is really confusing
22:17:28  (A combination would be to e.g. make the keyboard and connect to GPIO or using an adapter to USB (or MIDI or Ethernet or whatever else), and use an emulator on the computer for other parts of the system; the parts could then also be used independently with an alternative implementation.)
22:17:35  interestingly, Rust's process creation API is basically a more Rust-idiomatic version of posix_spawn because it was hard to ensure safety otherwise
22:17:53  um so? if you're writing a libc alternative you can add a posix_spawn alternative into it, can't you?
22:18:23  b_jonas: yes but it doesn't solve the original problem of not really understanding what is and isn't safe under vfork
22:19:59  yeah, vfork is hard
22:20:42  at least on Linux vfork is fairly simple because it still does COW memory like regular fork does, it's just a change to the scheduling algorithm
22:21:01  but I at least appreciate the elgance of posix_spawn that it can solve two problems with the same interface: one that vfork is hard to use, the other is that it can be a portable interface that works on both unix-like operating systems and systems that can't fork
22:21:34  yes
22:21:56  I like the idea of posix_spawn, it's just that C rather gets in the way
22:22:11  the Rust version is quite nice to use just because the language makes that sort of API more reasonable
22:22:12  it's just that I don't want to use this because the system I use that doesn't fork is Win32, and it's different from posix-like systems in many other ways than just not being able to fork, which is why I don't need this specific portability solution
22:22:51  yeah, there's a python version too
22:23:18  I did some amount of serious programming on DOS, which also doesn't fork
22:23:30  but I'm not sure whether I tried to create processes there using any language other than bash
22:23:48  …I have just realised that "ais523 is the sort of person who uses a DOS fork of bash" says a huge amount about me
22:23:55  err, DOS port of bash
22:25:44  I haven't used that, but I do have an old version of joe the text editor compiled for DOS which I found useful. I can even distribute its binary if anyone wants. my config file isn't very good so some of the bindings may need to be changed, but it does work me as a basic text editor that's not as bloated as most that I have access to on DOS are, which is why I inlcuded it in my one floppy sized DOS boot 
22:25:50  floppy 
22:27:10  I'm trying to remember whether I used Emacs on DOS
22:27:12  I think I did?
22:28:29  the visual editors that I mostly used in DOS are DOS's edit, which is in the same binary as QBASIC and so is somewhat big but was on an earlier version of that floppy; the editors in the GUI development environment for turbo pascal and borland C, which are bundled with a whole development environment with a full GUI interactive debugger in both source and assembly level; and ncedit which would work well 
22:28:35  on the boot floppy because it already has norton commander but it's not capable enough
22:29:08  ais523: I don't know, but you did nethack on DOS so emacs on DOS doesn't sound too unbelievable
22:29:26  (Another way to provide some compatibility would be optional hardware modules, e.g. the processors (or FPGA) for MSX and other systems)
22:29:43  b_jonas: oddly I'm not sure I ever played NetHack on DOS myself
22:29:56  the TAS is doing it on the DOS version purely for emulation accuracy reaosns
22:30:05  (I even submitted a patch to the emulator to get it to emulate NetHack correctly)
22:31:20  exactly, that version is more canonical than having to pick from many unix version, and for a TAS you want a canonical version that behaves the same for everyone. canonical behavior is easier for games on old video consoles.
22:32:17  and the technology for efficient accurate DOS emulation was already available back when you all started the TAS
22:32:54  Deterministic behaviour is also one of the things I intended for my computer design; proxy capabilities can be used for situations where the I/O would otherwise be non-deterministic, in order to force it to be deterministic.
22:33:30  zzo38: deterministic behavior is harder in general than for just the nethack TAS
22:34:34  Yes, I know it is harder in general, which is why I thought to redesign the entire computer to support it
22:35:07  but I think this isn't only about deterministic behavior, but *canonical* behavior, that is, it's deterministic and we want to show our sleeves empty so we didn't rig the behavior in a way that unfairly helps our TAS
22:35:59  OK, that is also valid, and I think that proxy capabilities might be helpful for that too.
22:36:48  because I can specify deterministic behavior with a C interpreter that makes sure that dereferencing invalid pointers in the interpreted program doesn't cause UB in the interpreter, but I can do it in a way where I can cause any invalid memory access read the exact values that I want, and that would be an unfair advantage for a TAS
22:37:14  now admittedly this would be more powerful for some other games than for nethack, but even so it's a good goal
22:37:20 -!- tromp has quit (Quit: My iMac has gone to sleep. ZZZzzz…).
22:38:00  It will not work with C in general unless it is a specific version with a specific compiler running on a specific system, I think.
22:38:41  sure, but you can make it good enough to support enough of C that you can build and run nethack with it
22:39:52   because I can specify deterministic behavior with a C interpreter that makes sure that dereferencing invalid pointers in the interpreted program doesn't cause UB in the interpreter ← can't you just turn off ASLR?
22:40:25  ais523: I don't understand the context
22:40:45  I expect it will be possible with my system, although some parts of the program will probably need to be changed (because e.g. fopen is unavailable, so you will need to use fopencookie instead; and you will also need to make it work with the I/O, although you could just use a terminal emulator without the ability to automatically respond, perhaps)
22:40:51  turn off ASLR where? for the interpreter, for the interpreted program, for the program compiled and ran with a normal C environment, and why?
22:40:58  b_jonas: if you want deterministic UB in C you can just remove the random inputs, any given compile will generate a particular asm and the asm is deterministic
22:41:11  so you turn off ASLR rather than using an interpreter
22:41:25  admittedly this wouldn't work so well with DOS, which has no MMU and so programs kind-of have to be relocatable
22:42:10  ais523: sure, but you can be much more subtle in how you rig the execution, because you can pick the compiler and compiler option and the libc and curses implementation, and even some of the operating system behavior might influence nethack
22:42:43  so I think it's very hard to get a canonical behavior for a unix version of nethack
22:44:14  whereas DOS has a canonical version, DOS 6.2, and a canonical minimal set of drivers that you load (it's not the *usual* set, the usual set is to use the windows 3.11 version of himem.sys rather than DOS's, but Windows have more than one version so it's less canonical)
22:44:31  DOS 6.22 sorry
22:44:55 -!- tromp has joined.
22:45:18  more easier to agree on one environment that you use to run all DOS games for which this works for TASing purposes
22:46:24  like, the C behavior on unix will depend on at least how libc's malloc behaves
22:46:36  and probably on more than just malloc
22:47:00  b_jonas: so it becomes a bit less canonical due to the DPMI extender
22:47:16  I see
22:47:20  which takes on some of the roles that libc+the kernel would normally be responsible for
22:47:25  and perhaps the BIOS
22:47:28  the usual DPMI extender is Windows but it doesn't emulate well
22:47:42  and the DOS behavior can depend on how the file system is layed out,
22:47:54  for TASing, the decision is fairly simple: FreeDOS as the BIOS because we can emulate it legally, and HDPMI32 as the extender because it's the only one that emulates correctly
22:48:06  and may depend on what exact version of CPU you have if you can get the program to execute arbitrary code
22:48:14  (and even then I had to add a feature to the emulator to make it emulate correctly)
22:48:49  tasvideos.org already has a standard "emulated DOS system" for TASing on so I didn't need to worry about things like the CPU version and frequency
22:48:55  oh, that actually makes more sense even if I didn't use FreeDOS for running emulated DOS games
22:49:41  I always just used my DOS 6.22 installation that's derived from that first DOS installation that I started when I got my first own PC (as separate from the one PC from the family)
22:50:13  obviously it changed a lot since, but there's an unbroken line and the DOS and Windows 3.11 installation is the exact same
22:51:36  “tasvideos.org already has a standard ‘emulated DOS system’” => that's great, then DOS is even more of an advantage. do they have any standard Windows systems, or is that too hard because of licensing issues?
22:51:52  no, Windows TASing is actually really janky
22:51:56  and keeps breaking all the time
22:52:07  oh sure, but that's for other reasons too 
22:52:15  because it isn't an emulator, it's basically done using the Windows version fo LD_PRELOAD
22:52:20  like delivering the inputs deterministically
22:52:32  so you have to rely on whatever software+kernel setup the users happen to be running
22:53:43  yeah, and for that reason I'm so glad Celeste added a built-in reason to read game control input from a file
22:53:50  s/reason/way/
22:54:26  funnily enough, I kind-of invented TASing on my own before learning about it being a thing
22:54:36  I had written my own computer game, and wrote a replay format for it
22:54:47  but instead of recording player input, I created the replays by brute force
22:55:05  that sounds more of the "zzo38 infected you" thing
22:55:16  even if it's retroactive
22:56:25  I wanted to see what an optimal level playthrough was like
22:56:52  the thing is, I didn't know whether my computer had enough memory to hold all the possible states a game could be in (and I was brute-forcing basically via Dijkstra's algorithm, although I didn't know it at the time)
22:57:12  so I stored the brute-forcing progress in the largest bit of memory I knew about, which was video RAM
22:57:22  and so I got to see the brute-forcing in action on screen
22:58:29  The replay format is something I intend to make in Super ZZ Zero game engine, although it is something which is not currently implemented. (Hopefully this can be used for regression testing as well as for other purposes.)
23:00:15  hehe
23:00:42  Maybe *that* is the biggest divide here. I'm an athletic speedrunner but not really a TAS'er.
23:02:10  hehe, I'm not sure if that counts as the *biggest* divide
23:05:14  I also wanted to know if the design of a VM code for a music file, I have some opcodes that have a variant that includes a wait and some opcodes do not have such a variant. The range of opcodes that have such a variant is not many unused left, and I put the ones for one, two, or three MIDI bytes in the waiting range and the one for arbitrary size data in the non-waiting range.
23:05:20  Is this the best way to assign them?
23:05:33  (You can see https://raw.githubusercontent.com/zzo38/superzz0/refs/heads/trunk/music.doc for the actual document, if you want to see it)
23:07:56 -!- tromp has quit (Quit: My iMac has gone to sleep. ZZZzzz…).
23:49:48 -!- pool has quit (Read error: Connection reset by peer).
23:50:19 -!- pool has joined.
23:59:58  [[Language list]]  https://esolangs.org/w/index.php?diff=167715&oldid=167643 * PrySigneToFry * (+40)