2024-09-21 00:02:32 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 00:04:07 +0200 | weary-traveler | (~user@user/user363627) |
2024-09-21 00:07:27 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 265 seconds) |
2024-09-21 00:09:19 +0200 | weary-traveler | (~user@user/user363627) (Remote host closed the connection) |
2024-09-21 00:10:22 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 00:10:24 +0200 | libertyprime | (~libertypr@118-92-68-68.dsl.dyn.ihug.co.nz) |
2024-09-21 00:11:03 +0200 | weary-traveler | (~user@user/user363627) |
2024-09-21 00:12:26 +0200 | talismanick | (~user@2601:644:937c:ed10::ae5) |
2024-09-21 00:13:51 +0200 | neuroevolutus | (~neuroevol@37.19.200.139) (Ping timeout: 256 seconds) |
2024-09-21 00:16:39 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 260 seconds) |
2024-09-21 00:18:19 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 00:19:06 +0200 | mikess | (~mikess@user/mikess) |
2024-09-21 00:20:31 +0200 | peterbecich | (~Thunderbi@syn-047-229-123-186.res.spectrum.com) (Ping timeout: 264 seconds) |
2024-09-21 00:23:21 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 252 seconds) |
2024-09-21 00:24:56 +0200 | machinedgod | (~machinedg@d50-99-47-73.abhsia.telus.net) |
2024-09-21 00:31:58 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 00:35:43 +0200 | ell | (~ellie@user/ellie) (Quit: Ping timeout (120 seconds)) |
2024-09-21 00:36:05 +0200 | ell | (~ellie@user/ellie) |
2024-09-21 00:36:37 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 248 seconds) |
2024-09-21 00:37:40 +0200 | mjrosenb | (~mjrosenb@pool-96-232-177-77.nycmny.fios.verizon.net) (Ping timeout: 252 seconds) |
2024-09-21 00:39:05 +0200 | mjrosenb | (~mjrosenb@pool-96-232-177-77.nycmny.fios.verizon.net) |
2024-09-21 00:42:45 +0200 | mikess | (~mikess@user/mikess) (Quit: mikess) |
2024-09-21 00:46:25 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 00:47:24 +0200 | mikess | (~mikess@user/mikess) |
2024-09-21 00:47:45 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 00:52:33 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 248 seconds) |
2024-09-21 00:52:42 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 252 seconds) |
2024-09-21 00:54:16 +0200 | <Inst> | monochrom: |
2024-09-21 00:54:23 +0200 | <Inst> | sorry, here's how to show the behavior |
2024-09-21 00:54:26 +0200 | <Inst> | import Debug.Trace |
2024-09-21 00:55:37 +0200 | <Inst> | x <|>> y = traceWith (\u -> show u <> " was evaluated on the left") x <|> y |
2024-09-21 00:55:46 +0200 | <Inst> | Just 3 <|>> Nothing <|>> Nothing |
2024-09-21 00:56:30 +0200 | <Inst> | also, I just discovered you can declare operators in function arguments |
2024-09-21 00:57:49 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 01:03:06 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 246 seconds) |
2024-09-21 01:03:29 +0200 | <Inst> | > with (****) a b = a **** b |
2024-09-21 01:03:31 +0200 | <lambdabot> | <hint>:1:17: error: parse error on input ‘=’ |
2024-09-21 01:03:31 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 01:03:54 +0200 | <Inst> | well, it works in 9.10 ghci :( |
2024-09-21 01:08:21 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 246 seconds) |
2024-09-21 01:08:45 +0200 | Oxf1ac | (~0xf1ac@62.4.42.168) |
2024-09-21 01:09:00 +0200 | <Inst> | tomsmeding: you CAN stylistically decide to use >>= to make the data flow more obvious, afaik everyone decided to just write functional python with do and <- instead |
2024-09-21 01:09:27 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 01:09:52 +0200 | <monochrom> | do-notation still desugars to right-associative uses of >>= |
2024-09-21 01:12:47 +0200 | Oxf1ac | (~0xf1ac@62.4.42.168) (Remote host closed the connection) |
2024-09-21 01:12:55 +0200 | <monochrom> | It is fair to say that infixr is better for >>, <|>, >=> in most use cases, and the standard library made the wrong choice. |
2024-09-21 01:13:07 +0200 | <monochrom> | But this is getting blown out of proportion. |
2024-09-21 01:13:11 +0200 | Oxf1ac | (~0xf1ac@62.4.42.168) |
2024-09-21 01:13:57 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 248 seconds) |
2024-09-21 01:18:07 +0200 | <monochrom> | Not to mention that "foo <|> (bar <|> x)" is not that hard to write if you find the infixl unsatisfactory. |
2024-09-21 01:18:38 +0200 | <Inst> | ehhh, just pointing out infelicities, it's not a big deal tbh |
2024-09-21 01:18:47 +0200 | <Inst> | it's a good reason not to abuse >>= and =<< for golfing |
2024-09-21 01:19:01 +0200 | <monochrom> | "Does >>= leak?" is not making a big fuzz? |
2024-09-21 01:19:18 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 01:19:52 +0200 | <Inst> | i suppose i should apologize for "baby's first exposure to thinking space and spaceleaks with laziness", but it would do no good |
2024-09-21 01:20:27 +0200 | <Inst> | that said, just out of curiosity, when do you introduce Debug.Trace, monochrom? |
2024-09-21 01:24:18 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 265 seconds) |
2024-09-21 01:25:18 +0200 | <monochrom> | Being novice in technical matters is not the issue I'm complaining about. |
2024-09-21 01:25:57 +0200 | <monochrom> | The dark pattern of always going hyperbole is. |
2024-09-21 01:26:35 +0200 | <Inst> | criticism acknowledged |
2024-09-21 01:32:56 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 01:36:14 +0200 | Squared | (~Square@user/square) |
2024-09-21 01:37:48 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 252 seconds) |
2024-09-21 01:43:16 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 01:43:39 +0200 | acidjnk | (~acidjnk@p200300d6e72cfb13044e7157fd3ef949.dip0.t-ipconnect.de) (Ping timeout: 252 seconds) |
2024-09-21 01:46:32 +0200 | Oxf1ac | (~0xf1ac@62.4.42.168) (Quit: WeeChat 4.4.2) |
2024-09-21 01:48:45 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 01:49:18 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 246 seconds) |
2024-09-21 01:50:07 +0200 | <Inst> | monochrom: I should have been more careful in wording and asked whether >>= leaks in direct use, i'm still pouring over GHC core output to check whether or not it does on O2 or higher optimizations |
2024-09-21 01:50:23 +0200 | <Inst> | and yeah i'm aware of the () desugaring of do |
2024-09-21 01:52:17 +0200 | <Inst> | the other realistic issue is, that from what i've seen, thinking lazily isn't prioritized in most haskell books i've seen, and there's been commercial users of haskell that've dropped Haskell because they weren't proficient in laziness |
2024-09-21 01:53:27 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 01:53:54 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 248 seconds) |
2024-09-21 01:58:08 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 265 seconds) |
2024-09-21 01:58:10 +0200 | <Inst> | also, another question |
2024-09-21 01:58:36 +0200 | <Inst> | actually, forget it, maybe another time |
2024-09-21 02:04:35 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 02:04:40 +0200 | <probie> | You can evaluate that question thunk at a later time |
2024-09-21 02:06:35 +0200 | <Inst> | it's more like weirdness with GHCI, possibly not an issue with ghc |
2024-09-21 02:07:13 +0200 | <Inst> | if i bang a let declaration in a do block, do traceShowId over a number, it doesn't evaluate, if I traceShowId something else, it evaluates |
2024-09-21 02:07:53 +0200 | <Inst> | it looks like it's wonkiness related to default types, because if I affix a type annotation, it evaluates |
2024-09-21 02:09:49 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 260 seconds) |
2024-09-21 02:10:09 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 02:15:52 +0200 | peterbecich | (~Thunderbi@syn-047-229-123-186.res.spectrum.com) |
2024-09-21 02:20:19 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 02:22:56 +0200 | ZharMeny | (~ZharMeny@user/ZharMeny) (Quit: ERC 5.5.0.29.1 (IRC client for GNU Emacs 29.4)) |
2024-09-21 02:25:30 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 276 seconds) |
2024-09-21 02:32:20 +0200 | califax | (~califax@user/califx) (Remote host closed the connection) |
2024-09-21 02:33:59 +0200 | califax | (~califax@user/califx) |
2024-09-21 02:36:07 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 02:40:52 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 252 seconds) |
2024-09-21 02:51:51 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 02:53:19 +0200 | peterbecich | (~Thunderbi@syn-047-229-123-186.res.spectrum.com) (Ping timeout: 252 seconds) |
2024-09-21 02:55:07 +0200 | troojg | (~troojg@user/troojg) |
2024-09-21 02:56:38 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 252 seconds) |
2024-09-21 03:04:01 +0200 | <cheater> | what |
2024-09-21 03:07:40 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 03:12:21 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 248 seconds) |
2024-09-21 03:21:40 +0200 | pavonia | (~user@user/siracusa) |
2024-09-21 03:22:55 +0200 | Unicorn_Princess | (~Unicorn_P@user/Unicorn-Princess/x-3540542) (Remote host closed the connection) |
2024-09-21 03:23:27 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 03:24:54 +0200 | Oxf1ac | (~Oxf1ac@62.4.42.168) |
2024-09-21 03:27:36 +0200 | CrunchyFlakes | (~CrunchyFl@ip1f13e94e.dynamic.kabel-deutschland.de) (Read error: Connection reset by peer) |
2024-09-21 03:28:31 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 265 seconds) |
2024-09-21 03:30:16 +0200 | CrunchyFlakes | (~CrunchyFl@ip1f13e94e.dynamic.kabel-deutschland.de) |
2024-09-21 03:35:38 +0200 | Oxf1ac | (~Oxf1ac@62.4.42.168) (WeeChat 4.4.2) |
2024-09-21 03:35:54 +0200 | gvg_ | (~dcd@user/gvg) |
2024-09-21 03:36:58 +0200 | gvg | (~dcd@user/gvg) (Ping timeout: 252 seconds) |
2024-09-21 03:39:15 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 03:44:19 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 260 seconds) |
2024-09-21 03:44:57 +0200 | Fijxu_ | (~Fijxu@user/fijxu) (Ping timeout: 252 seconds) |
2024-09-21 03:48:37 +0200 | <probie> | % do{let {!x=trace "Hello" 42}; putStrLn "World"} |
2024-09-21 03:48:37 +0200 | <yahb2> | World |
2024-09-21 03:48:45 +0200 | <probie> | % do{let {!x=trace "Hello" (42 :: Int)}; putStrLn "World"} |
2024-09-21 03:48:45 +0200 | <yahb2> | Hello ; World |
2024-09-21 03:48:59 +0200 | Fijxu | (~Fijxu@user/fijxu) |
2024-09-21 03:49:00 +0200 | <probie> | That isn't type defaulting |
2024-09-21 03:49:20 +0200 | <probie> | % do{let {x=trace "Hello" (42 :: Int)}; x `seq` putStrLn "World"} |
2024-09-21 03:49:20 +0200 | <yahb2> | Hello ; World |
2024-09-21 03:49:30 +0200 | <probie> | % do{let {x=trace "Hello" 42}; x `seq` putStrLn "World"} |
2024-09-21 03:49:30 +0200 | <yahb2> | Hello ; World |
2024-09-21 03:51:12 +0200 | <probie> | It's that `x` has type `Num a => a`, which is "pretty much" a function, and therefore already in WHNF since it's a lambda |
2024-09-21 03:54:12 +0200 | Squared | (~Square@user/square) (Ping timeout: 252 seconds) |
2024-09-21 03:54:20 +0200 | <Inst> | thanks probie |
2024-09-21 03:54:33 +0200 | <Inst> | but if you do this on ghc, it works |
2024-09-21 03:55:01 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 03:55:17 +0200 | Tuplanolla | (~Tuplanoll@91-159-69-59.elisa-laajakaista.fi) (Quit: Leaving.) |
2024-09-21 03:55:19 +0200 | <geekosaur> | in a sense that is defaulting |
2024-09-21 03:56:27 +0200 | <geekosaur> | ghci has NoMonomorphismRestriction, so it doesn't resolve things like (Num a => a) immediately. ghc doesn't, so it gets defaulted to Int and is no longer a function taking a Num dictionary |
2024-09-21 03:56:30 +0200 | Guest19 | (~Guest57@syn-075-131-084-201.res.spectrum.com) |
2024-09-21 03:57:14 +0200 | <geekosaur> | if you compile with -XNoMonomorphismRestriction, you should get the same behavior as ghci |
2024-09-21 03:58:03 +0200 | <geekosaur> | if you run it in "ghci -XMonomorphismRestriction", you should get the same behavior as ghc |
2024-09-21 03:59:57 +0200 | Guest19 | (~Guest57@syn-075-131-084-201.res.spectrum.com) (Client Quit) |
2024-09-21 03:59:58 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 245 seconds) |
2024-09-21 04:02:33 +0200 | <Inst> | thanks geekosaur |
2024-09-21 04:03:42 +0200 | <geekosaur> | this kind of confusion is more or less why the monomorphism restriction exists and is the default; x there "looks like" a value, but without the MMR it's actually a function |
2024-09-21 04:04:15 +0200 | <Inst> | also, curious, can you still get unsafePerformIO to segfault with the example code? |
2024-09-21 04:04:38 +0200 | <geekosaur> | I saw you bring that up in #ghc but I haven't lookmed |
2024-09-21 04:05:01 +0200 | <Inst> | it's weird, but probably why it's just unsafe, i.e, might be platform specific |
2024-09-21 04:05:49 +0200 | <Inst> | thanks anyways |
2024-09-21 04:06:00 +0200 | <Inst> | I used to get it to crash, but I guess that's why it's unsafe |
2024-09-21 04:06:08 +0200 | <Inst> | undefined behavior depending on platform and kernel version |
2024-09-21 04:07:25 +0200 | <geekosaur> | I think the example code was "broken" by ghc's runtime representations changing in 8.10.5+ to support Apple AArch64 |
2024-09-21 04:07:40 +0200 | <geekosaur> | but that's just a suspicion |
2024-09-21 04:07:46 +0200 | <geekosaur> | (it didn't core here) |
2024-09-21 04:07:52 +0200 | <Inst> | i swapped to 8.x via ghcup |
2024-09-21 04:08:55 +0200 | <Inst> | still fails to crash, I suspect it's something to do with linux kernel updates |
2024-09-21 04:09:25 +0200 | <geekosaur> | keep in mind that I'm on Ubuntu 22.04, so my kernel is practically ancient |
2024-09-21 04:11:59 +0200 | <Inst> | iirc it does crash in windows, but i sort of lost my windows drive :( |
2024-09-21 04:12:41 +0200 | <geekosaur> | the problem they're talking about can't be fixed as such (it might be made slightly less likely to happen in certain specific cases, but the general problem is not fixable) |
2024-09-21 04:13:05 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Remote host closed the connection) |
2024-09-21 04:13:35 +0200 | <geekosaur> | as the discussion says, if you have unsafePerformIO, you have unsafeCoerce and what happens if you use it as such will be up to the whim of the RTS |
2024-09-21 04:15:27 +0200 | <geekosaur> | the example code may now be too simplistic to demonstrate the problem, but I'm sure it won't need much tweaking to reveal it again |
2024-09-21 04:17:03 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 04:19:23 +0200 | peterbecich | (~Thunderbi@syn-047-229-123-186.res.spectrum.com) |
2024-09-21 04:26:35 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 04:31:55 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 264 seconds) |
2024-09-21 04:34:30 +0200 | td_ | (~td@i53870926.versanet.de) (Ping timeout: 246 seconds) |
2024-09-21 04:36:21 +0200 | td_ | (~td@i5387092D.versanet.de) |
2024-09-21 04:40:48 +0200 | machinedgod | (~machinedg@d50-99-47-73.abhsia.telus.net) (Ping timeout: 246 seconds) |
2024-09-21 04:42:23 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 04:43:13 +0200 | <Inst> | this is weird |
2024-09-21 04:43:43 +0200 | <Inst> | 234288 unsafeCoerce-ed to System.IO.Handle gets you the crash I'm looking for |
2024-09-21 04:43:50 +0200 | <Inst> | but other integers don't produce the same effects |
2024-09-21 04:44:08 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Remote host closed the connection) |
2024-09-21 04:44:43 +0200 | JuanDaugherty | (~juan@user/JuanDaugherty) |
2024-09-21 04:45:08 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) |
2024-09-21 04:45:20 +0200 | terrorjack4 | (~terrorjac@2a01:4f8:c17:dc9f::) (Quit: The Lounge - https://thelounge.chat) |
2024-09-21 04:46:01 +0200 | <Inst> | okay, Integers (mostly) seem to produce the desired crash on unsafeCoerce to System.IO.Handle (using unsafePerformIO) |
2024-09-21 04:47:18 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) (Ping timeout: 265 seconds) |
2024-09-21 04:47:36 +0200 | terrorjack4 | (~terrorjac@static.48.15.202.116.clients.your-server.de) |
2024-09-21 04:49:43 +0200 | morb | (~morb@pool-108-41-100-120.nycmny.fios.verizon.net) (Ping timeout: 265 seconds) |
2024-09-21 04:53:12 +0200 | <geekosaur> | that's not too surprising, it very likely depends on the internal GMP representation |
2024-09-21 04:53:33 +0200 | <geekosaur> | that's more or less what you're inviting with unsafeCoerce in any form |
2024-09-21 04:54:05 +0200 | <Inst> | iirc it should be safe to use unsafePerformIO for read-only operations, right? as long as you ensure the write is done beforehand |
2024-09-21 04:54:26 +0200 | <Inst> | i'm more trying to figure out when it's safe to use unsafeCoerce |
2024-09-21 04:54:54 +0200 | <geekosaur> | even read-only is unsafe if you coerced an unboxed value into a boxed one |
2024-09-21 04:55:24 +0200 | <geekosaur> | because reading it will follow what it thinks is a pointer |
2024-09-21 04:55:50 +0200 | <geekosaur> | @quote monochrom unsafeCoerce.*Either |
2024-09-21 04:55:50 +0200 | <lambdabot> | monochrom says: isTrue = (unsafeCoerce :: Either a b -> Bool) . (unsafeCoerce :: Maybe c -> Either a b) . (unsafeCoerce :: Bool -> Maybe c) |
2024-09-21 04:56:50 +0200 | <geekosaur> | if (a) all types are boxed (b) all types have at least as many constructors as the starting type does, you can generally get away with it |
2024-09-21 04:56:51 +0200 | <Inst> | i mean without coercion in unsafePerformIO, i.e, a way to avoid passing large parameters around |
2024-09-21 04:57:34 +0200 | <geekosaur> | unsafePerformIO only matters insofar as it can give you a polymorphic IORef, which implicitly unsafeCoerces anything taken out of it |
2024-09-21 04:57:56 +0200 | <Inst> | iirc i used unsafePerformIO as an optimization pass |
2024-09-21 04:58:09 +0200 | <geekosaur> | it's the unsafeCoerce part, however you got it, that is problematic |
2024-09-21 04:58:10 +0200 | merijn | (~merijn@204-220-045-062.dynamic.caiway.nl) |
2024-09-21 04:58:44 +0200 | <Inst> | i thought the main reason unsafePerformIO was considered unsafe was because Haskell gives very weak guarantees on evaluation order of pure functions? |
2024-09-21 04:58:56 +0200 | <geekosaur> | and re "large parameters", if they are boxed, you're passing a pointer |