https://forum.dlang.org/feed/postsLatest posts2024-03-29T11:57:43+00:00https://forum.dlang.org/post/zbbtjhojyncweijbinbr@forum.dlang.org[DIP Ideas] Re: statement unittest2024-03-29T11:53:52+00:002024-03-29T11:53:52+00:00Nicholas Wilson<div class="post-text markdown"><p>On Thursday, 21 March 2024 at 19:39:41 UTC, monkyyy wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>I have this code:</p>
<pre><code class="language-d">auto reduce(alias F,R)(R r)=>r.acc!F.last.front;
unittest{ assert(counter(10).reduce!((a,int b=0)=>a+b)==45);}
auto all(alias F,R)(R r)=>r.map!F.filter!(a=>!a).empty;
unittest{ assert([1,3,5,7,9].torange.all!(a=>a%2));}
auto any(alias F,R)(R r)=> ! r.filter!F.empty;
unittest{ assert([1,2,3,4,15].torange.any!(a=>a==15));}
auto count(R)(R r)=>r.reduce!((a,int b=0)=>b+1);
unittest{ assert(counter(10).filter!(a=>a%2).count==5);}
</code></pre>
<p>"unittest{ assert(..);}" should be reduceable to <code>unittest(...)</code></p>
<p>i.e. <code>unittest(1==1)</code> would compile</p></span>
<p>there should be no DIP required here, <code>unittest</code>s are function declarations, and so they <em>should</em> work as <code>unittest => assert(1==1);</code>. They don't currently though (purely a problem with the parser<a rel="nofollow" href="https://github.com/dlang/dmd/blob/e00869b27e3d9cabed2b6e73503561997398759c/compiler/src/dmd/parse.d#L521">1</a>), that seems like a bug, please file one.</p>
<p>explicitly checks for { }<br />
a similar problem exists for <code>parseUnitTest</code> that calls <code>parseStatement</code> that explicitly checks for <code>{}</code></p>
</div>https://forum.dlang.org/post/cllopqxrrgzfnuetwaxp@forum.dlang.org[General] Re: Side-Effect System in D2024-03-29T11:09:10+00:002024-03-29T11:09:10+00:00Dukc<div class="post-text markdown"><p>On Wednesday, 27 March 2024 at 07:47:02 UTC, Per Nordlöw wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Would be awesome to have Koka's side-effect system in D.</p>
<p>See <a rel="nofollow" href="https://koka-lang.github.io/koka/doc/book.html#sec-semantics-of-effects">https://koka-lang.github.io/koka/doc/book.html#sec-semantics-of-effects</a>.</p></span>
<p>Don't we have a pretty good appromixation of <code>pure</code>, well, <code>pure</code>? St can also be easily represented by giving the state object as an extra <code>ref</code> parameter.</p>
<p>As for <code>total</code>, I don't think it's practical. That would mean no divisions, no assertions, no normal array indexing.</p>
<p>Besides, often you do have values that are representable by types of the parameters but that indicate a bug in the caller side if they're ever passed. You'd want a total function only if what you're doing actually makes sense for all the possible (<code>@safe</code>) values. If that isn't the case, asserting on invalid values is the right thing to do as Walter always says, not coming up with some cover-up return value to make the function total.</p>
<p>For example, if you have a function computing an average over an integer array, it'd be a bad idea to make that total since you would have to return a made-up value for an empty array instead of asserting.</p>
<p>While there are certainly some cases where you could reasonably make a function total, like bitwise boolean logic, on the whole it's just not practical to attempt programming in a crash-safe manner in D. I don't have enough experience in Haskell to judge if it's practical there, but it at least gets closer. For the idea to be worthwhile, you need to be able to limit the possible values of variables with types in the majority of the cases. This means non-nullable and nullable types for everything, ints with value range information, float that can't be NaN, non-empty types for ranges, and so on. And it needs to be extremely easy to translate those types to each other.</p>
<p>D does not have that kind of type system and it doesn't look like a good direction of development for it. For example, because all D types need an <code>.init</code> value, it means a general-purpose non-empty range type would be very difficult to define in a practical manner. The language simply works very differently from what total programming style would ask for.</p>
</div>https://forum.dlang.org/post/edkixcbwpzyrkhkouibd@forum.dlang.org[DIP Ideas] Re: statement unittest2024-03-29T10:27:51+00:002024-03-29T10:27:51+00:00Dom DiSc<div class="post-text markdown"><p>On Saturday, 23 March 2024 at 16:28:14 UTC, Nick Treleaven wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>On Saturday, 23 March 2024 at 09:43:20 UTC, Dom DiSc wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>That's pretty much as short as your proposal and even more readable.</p></span>
<p>Then you can't have documented unittests for each function.</p></span>
<p>If you want to generate documentation from this, every test should at least have one line of comment (aka "Documentation"), so can't be a one-liner anyway.</p>
<p>And especially in the description of some closely related functions I would prefer one unittest block testing all of them over the scattered tests between each function declaration.</p>
</div>https://forum.dlang.org/post/uu5rpo$1457$1@digitalmars.com[DIP Ideas] Re: Mixin C2024-03-29T00:49:23-07:002024-03-29T00:49:23-07:00Walter Bright<pre class="post-text">On 3/7/2024 7:23 PM, Paul Backus wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>Mixin C would solve two big issues with the current ImportC approach: the poor preprocessor support,
</span>
I don't see how it would improve preprocessor support. C macros used in D code won't fare any better than they do now.
<span class="forum-quote"><span class="forum-quote-prefix">> </span>and the conflicts between `.c` and `.d` files in the compiler's import paths.
</span>
Frankly, I never understood why that was an issue. Change the name of one of them, or put them in different paths.
I appreciate the effort you've put into this. But I have to be blunt. I've seen this before. Here's what it looks like in practice:
<a rel="nofollow" href="https://elsmar.com/elsmarqualityforum/media/redneck-car-air-conditioning.1560/"><span class="forcewrap">https://</span><span class="forcewrap">elsmar.com/</span><span class="forcewrap">elsmarqua</span><span class="forcewrap">lityforum/</span><span class="forcewrap">media/</span><span class="forcewrap">redneck-</span><span class="forcewrap">car-air-</span><span class="forcewrap">conditioning.</span><span class="forcewrap">1560/</span></a>
D is a beautiful language to program in. Let's keep it that way!
<a rel="nofollow" href="https://www.joemacari.com/stock/ferrari-daytona-spyder/10004904"><span class="forcewrap">https://</span><span class="forcewrap">www.joem</span><span class="forcewrap">acari.com/</span><span class="forcewrap">stock/</span><span class="forcewrap">ferrari-</span><span class="forcewrap">daytona-</span><span class="forcewrap">spyder/</span><span class="forcewrap">10004904</span></a>
</pre>https://forum.dlang.org/post/uu5qft$1136$1@digitalmars.com[DIP Ideas] Re: Mixin C2024-03-29T00:27:04-07:002024-03-29T00:27:04-07:00Walter Bright<pre class="post-text">On 3/8/2024 10:03 AM, Paul Backus wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>There's currently no way to do this with ImportC
</span>
```
__declspec(nothrow) int foo();
```
</pre>https://forum.dlang.org/post/uu5q5s$1069$1@digitalmars.com[DIP Ideas] Re: Mixin C2024-03-29T00:21:43-07:002024-03-29T00:21:43-07:00Walter Bright<pre class="post-text">You can add unit tests for C code already:
```
import myccode; // <a href="/search?q=define">#define</a> cmacro(a) 2
unittest
{
assert(cmacro(1) == 2);
}
```
</pre>https://issues.dlang.org/show_bug.cgi?id=24466[Issues] [Issue 24466] `scope(exit)` should not be allowed in the main scope of `noreturn` functions2024-03-29T07:18:37+00:002024-03-29T07:18:37+00:00elpenguino+D@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24466"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24466</span></a>
elpenguino+D@gmail.com changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
CC| |elpenguino+D@gmail.com
--- Comment #1 from elpenguino+D@gmail.com ---
I don't think it's accurate to do that for all noreturn scopes. Consider:
```
noreturn v(int a) {
scope(exit) a++;
{
scope(exit) a++;
}
throw new Exception("Exception");
}
```
In this code, both scope guards should be executed.
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24466[Issues] [Issue 24466] New: `scope(exit)` should not be allowed in the main scope of `noreturn` functions2024-03-29T07:08:11+00:002024-03-29T07:08:11+00:00b2.temp@gmx.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24466"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24466</span></a>
Issue ID: 24466
Summary: `scope(exit)` should not be allowed in the main scope
of `noreturn` functions
Product: D
Version: D2
Hardware: All
OS: All
Status: NEW
Keywords: accepts-invalid
Severity: minor
Priority: P1
Component: dmd
Assignee: nobody@puremagic.com
Reporter: b2.temp@gmx.com
consider the following code
```d
noreturn v(int a)
{
scope(exit) a++; // cant be executed
{
scope(exit) a++; // this one is okay
}
assert(0);
}
```
There should be a sema error for the first scope guard as the defered expression statement cannot be executed.
--
</pre>https://forum.dlang.org/post/uu5p7j$sjj$1@digitalmars.com[General] Re: Side-Effect System in D2024-03-29T08:05:22+01:002024-03-29T08:05:22+01:00Timon Gehr<pre class="post-text">On 3/27/24 08:47, Per Nordlöw wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>Would be awesome to have Koka's side-effect system in D.
<span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>See <a rel="nofollow" href="https://koka-lang.github.io/koka/doc/book.html#sec-semantics-of-effects"><span class="forcewrap">https://</span><span class="forcewrap">koka-lang.</span><span class="forcewrap">github.io/</span><span class="forcewrap">koka/doc/</span><span class="forcewrap">book.html#sec-</span><span class="forcewrap">semantics-</span><span class="forcewrap">of-effects</span></a>.
</span>
I also think that this is a good approach for effects. However, it requires parametric polymorphism in the type system.
</pre>https://forum.dlang.org/post/ihahnpauasgnayejqkaj@forum.dlang.org[General] DIP Feedback2024-03-29T05:40:24+00:002024-03-29T05:40:24+00:00Mike Parker<div class="post-text markdown"><p>As a reminder, we've got some draft DIPs in the DIP Development forum waiting for feedback. Please take a look and give your thoughts:</p>
<p><a rel="nofollow" href="https://forum.dlang.org/group/dip.development">https://forum.dlang.org/group/dip.development</a></p>
<p>Rikki's DIP in particular:</p>
<p><a rel="nofollow" href="https://forum.dlang.org/thread/fikldqqeedfuasdutuda@forum.dlang.org">https://forum.dlang.org/thread/fikldqqeedfuasdutuda@forum.dlang.org</a></p>
<p>He's ready to submit it for evaluation, but there's been so little feedback on it in the forum, I want to give it a couple of more days. So please give it a look and share your thoughts on how it can improve.</p>
<p>And don't forget about the ideas percolating in the DIP Ideas forum:</p>
<p><a rel="nofollow" href="https://forum.dlang.org/group/dip.ideas">https://forum.dlang.org/group/dip.ideas</a></p>
<p>This new system only works with enough community participation. Please take a look at the drafts and ideas and share your feedback.</p>
<p>Thanks!</p>
</div>https://issues.dlang.org/show_bug.cgi?id=24465#c1[Issues] [Issue 24465] Tuple does not get a copy constructor when its members need it2024-03-29T01:54:06+00:002024-03-29T01:54:06+00:00Dlang Bot<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24465"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24465</span></a>
Dlang Bot <dlang-bot@dlang.rocks> changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
Keywords| |pull
--- Comment #1 from Dlang Bot <dlang-bot@dlang.rocks> ---
@jmdavis created dlang/phobos pull request #8963 "Fix bugzilla #24465: Make Tuple work with copy constructors" fixing this issue:
- Fix bugzilla #24465: Make Tuple work with copy constructors
If there's a constructor that looks like a copy constructor except that
it takes an rvalue instead of taking the argument by ref, then that type
can't have a copy constructor, and one of Tuple's constructors was
causing that problem. So, this fixes it so that it doesn't.
<a rel="nofollow" href="https://github.com/dlang/phobos/pull/8963"><span class="forcewrap">https://</span><span class="forcewrap">github.com/</span><span class="forcewrap">dlang/phobos/</span><span class="forcewrap">pull/8963</span></a>
--
</pre>https://forum.dlang.org/post/mailman.1276.1711675129.3719.digitalmars-d-learn@puremagic.com[Learn] Re: Unittests pass, and then an invalid memory operation happens after?2024-03-28T18:18:22-07:002024-03-28T18:18:22-07:00H. S. Teoh<pre class="post-text">On Thu, Mar 28, 2024 at 11:49:19PM +0000, Liam McGillivray via Digitalmars-d-learn wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>On Thursday, 28 March 2024 at 04:46:27 UTC, H. S. Teoh wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> > </span>The whole point of a GC is that you leave everything up to it to clean up. If you want to manage your own memory, don't use the GC. D does not force you to use it; you can import core.stdc.stdlib and use malloc/free to your heart's content.
<span class="forum-quote-prefix">> > </span>
<span class="forum-quote-prefix">> > </span>Unpredictable order of collection is an inherent property of GCs. It's not going away. If you don't like it, use malloc/free instead. (Or write your own memory management scheme.)
</span><span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>I disagree with this attitude on how the GC should work. Having to jump immediately from leaving everything behind for the GC to fully manual memory allocation whenever the GC becomes a problem is a problem, which gives legitimacy to the common complaint of D being "garbage-collected". It would be much better if the garbage collector could be there as a backup for when it's needed, while allowing the programmer to write code for object destruction when they want to optimize.
</span>
Take a look at the docs for core.memory.GC. There *is* a method GC.free that you can use to manually deallocate GC-allocated memory if you so wish. Keep in mind, though, that manually managing memory in this way invites memory-related errors. That's not something I recommend unless you're adamant about doing everything the manual way.
<span class="forum-quote"><span class="forum-quote"><span class="forum-quote"><span class="forum-quote-prefix">> > > </span>Anyway, I suppose I'll have to experiment with either manually destroying every object at the end of every unittest, or just leaving more to the GC. Maybe I'll make a separate `die` function for the units, if you think it's a good idea.
</span><span class="forum-quote-prefix">> > </span>
<span class="forum-quote-prefix">> > </span>I think you're approaching this from a totally wrong angle. (Which I sympathize with, having come from a C/C++ background myself.) The whole point of having a GC is that you *don't* worry about when an object is collected. You just allocate whatever you need, and let the GC worry about cleaning up after you. The more you let the GC do its job, the better it will be.
</span><span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>Now you're giving me conflicting advice. I was told that my current destructor functions aren't acceptable with the garbage collector, and you specifically tell me to leave things to the GC. But then I suggest that I "leave more to the GC" and move everything from the Unit destructor to a specialized `die` function that can be called instead of `destroy` whenever they must be removed from the game, which as far as I can see is the only way to achieve the desired game functionality while following your and Steve's advice and not having dangling references. But in response to that, you tell me "I think you're approaching this from the wrong angle". And then right after that, you *again* tell me to "just let the GC worry about cleaning up after you"? Even if I didn't call `destroy` at all during my program, as far as I can see, I would still need the `die` function mentioned to remove a unit on death.
</span>
I think you're conflating two separate concepts, and it would help to distinguish between them. There's the lifetime of a memory-allocated object, which is how long an object remains in the part of the heap that's allocated to it. It begins when you allocate the object with `new`, and ends with the GC finds that it's no longer referenced and collects it.
There's a different lifetime that you appear to be talking about: the logical lifetime of an in-game object (not to be confused with an "object" in the OO sense, though the two may overlap). The (game) object gets created (comes into existence in the simulated game world) at a certain point in game time, until something in the game simulation decides that it should no longer exist (it got destroyed, replaced with another object, whatever). At that point, it should be removed from the game simulation, and that's probably also what you have in mind when you mentioned your "die" function.
And here's the important point: the two *do not need to coincide*. Here's a concrete example of what I mean. Suppose in your game there's some in-game mechanic that's creating N objects per M turns, and another mechanic that's destroying some of these objects every L turns. If you map these creations/destructions with the object lifetime, you're looking at a *lot* of memory allocations and deallocations throughout the course of your game. Memory allocations and deallocations can be costly; this can become a problem if you're talking about a large number of objects, or if they're being created/destroyed very rapidly (e.g., they are fragments flying out from explosions). Since most of these objects are identical in type, one way of optimizing the code is to preallocate them: before starting your main loop, say you allocate an array of say, 100 objects. Or 1000 or 10000, however many you anticipate you'll need. These objects aren't actually in the game world yet; you're merely reserving the memory for them beforehand. Mark each of them with a "live"-ness flag that indicates whether or not they're actually in the game. Then during your main loop, whenever you need to create a new object of that type, don't allocate memory for it; just find a non-live object in this array, set its fields to the right values, and mark it "live". Now it's a object in the game. When the object is destroyed in-game, don't deallocate it; instead, just set its "live" flag to false. Now you can blast through hundreds and thousands of these objects without incurring the cost of allocating and deallocating them every time. You also save on GC cost (there's nothing for the GC to collect, so it doesn't need to run at all).
Don't get confused by the "object" terminology; an in-game object is not necessarily the same thing as a class object in your program. In fact, sometimes it's advantageous to treat them as separate things.
[...]
<span class="forum-quote"><span class="forum-quote"><span class="forum-quote-prefix">> > </span>As far as performance is concerned, a GC actually has higher throughput than manually freeing objects, because in a fragmented heap situation, freeing objects immediately when they go out of use incurs a lot of random access RAM roundtrip costs, whereas a GC that scans memory for references can amortize some of this cost to a single period of time.
</span><span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>By "manually freeing objects", do you mean through `destroy`? If so that's actually quite disappointing, as D is often described as a "systems programming language", and I thought it would be fun to do these optimizations of object destruction, even if I have the garbage collector as a backup for anything missed. Or did you mean with `malloc` and `free`?
</span>
By "manually freeing objects" I mean what you typically do when you're using malloc/free.
Note that in D, you *can* actually "manually manage" some objects this way by calling GC.free. I don't recommend this, though. It's not how the GC is intended to be used, and it can lead to memory safety problems. My advice remains the same: just let the GC do its job. Don't "optimize" prematurely. Use a profiler to test your program and identify its real bottlenecks before embarking on these often needlessly complicated premature optimizations that may turn out to be completely unnecessary.
[...]
<span class="forum-quote"><span class="forum-quote-prefix">> </span>Well, I suppose that's fine for when the GC problem is specifically over slowness. I'm quite new to D, so I don't really know what it means to "preallocate before your main loop". Is this a combination of using `static this` constructors and `malloc`? I haven't used `malloc` yet. I have tried making static constructors, but every time I've tried them, they caused an error to happen immediately after the program is launched.
</span>
I gave an example of preallocation above. It's not specific to GC or malloc/free; it's a general principle of reducing the number of allocations inside your main loop. If you can reserve beforehand the memory you know you'll need later, it will generally perform better than if you keep allocating on-the-fly. Allocation and deallocation (or GC collection) always come with a cost; so you want to avoid doing this inside a hot loop, like your main game loop (assuming it's running every frame -- otherwise it's a non-issue and you shouldn't worry about it). Allocating N objects beforehand and then gradually using them as needed, is always better than starting with 0 objects and allocating each one individually inside your hot loop.
[...]
<span class="forum-quote"><span class="forum-quote-prefix">> </span>I suppose I can turn the `Tile` object into a struct, which I suppose will mean replacing all it's references (outside the map's `Tile[][] grid`) with pointers. I have thought about this before, since tiles are fundamentally associated with one particular map, but I chose objects mostly so I can easily pass around references to them.
</span>
The correct design will depend on how you're using them, so I can't give you a specific recommendation here.
If you're conscious of performance, however, I'd say avoid references where you can. Since maps presumably will always exist while the game is going on, why bother with references at all? Just use a struct to store the coordinates of the tile, and look it up in the map. Or if you need to distinguish between tiles belonging to multiple simultaneous maps, then store a reference to the parent map along with the coordinates, then you'll be able to find the right Tile easily. This way your maps can just store an array of Tile structs (single allocation), instead of an array of Tile objects (M*N allocations for an M×N map).
<span class="forum-quote"><span class="forum-quote-prefix">> </span>I've already been using structs for the stuff with a short lifespan.
</span>
Good.
[...]
<span class="forum-quote"><span class="forum-quote-prefix">> </span>I want to ask about `@nogc`. Does it simply place restrictions on what I can do? Or does it change the meaning of certain lines? For example, does it mean that I can still create objects, but they will just keep piling up without being cleaned up?
</span>
@nogc does not change runtime behaviour. It's a static enforcement that prevents your code from doing anything that might trigger GC allocations at all. So using anything that will trigger a GC allocation, such as using `new` or appending to an array with `~`, will cause a compile error. I don't recommend using it (a pretty substantial chunk of the language and stdlib will become unavailable to you), but if you absolutely, totally, 100% want to abstain from using the GC at all, @nogc is your ticket to ensure that you didn't accidentally do so. The compiler will enforce it at compile-time.
T
<span class="forum-signature">--
Music critic: "That's an imitation fugue!"
</span></pre>https://forum.dlang.org/post/yihrmankrcjsmbnoxyai@forum.dlang.org[DIP Ideas] Re: Mixin C2024-03-29T00:56:49+00:002024-03-29T00:56:49+00:00max haughton<div class="post-text markdown"><p>On Friday, 8 March 2024 at 03:23:12 UTC, Paul Backus wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>What if instead of importing C files like D modules, we could write bits of C code directly in the middle of our D code, like we do with inline ASM?</p>
<p>[...]</p></span>
<p><a rel="nofollow" href="https://github.com/dlang/dmd/pull/14114">https://github.com/dlang/dmd/pull/14114</a></p>
</div>https://forum.dlang.org/post/teyhgjkchdxrkkyapcjr@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-29T00:47:20+00:002024-03-29T00:47:20+00:00Salih Dincer<div class="post-text markdown"><p>On Friday, 29 March 2024 at 00:04:14 UTC, Serg Gini wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>On Thursday, 28 March 2024 at 23:15:26 UTC, Salih Dincer wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>There is no such thing as parallel programming in D anyway. At least it has modules, but I didn't see it being works. Whenever I use toys built in foreach() it always ends in disappointment</p></span>
<p>I think it just works :)<br />
Which issues did you have with it?</p></span>
<p>A year has passed and I have tried almost everything! Either it went into an infinite loop or nothing changed at the speed. At least things are not as simple as openMP on the D side! First I tried this code snippet: futile attempt!</p>
<pre><code class="language-d">struct RowlandSequence {
import std.numeric : gcd;
import std.format : format;
import std.conv : text;
long b, r, a = 3;
enum empty = false;
string[] front() {
string result = format("%s, %s", b, r);
return [text(a), result];
}
void popFront() {
long result = 1;
while(result == 1) {
result = gcd(r++, b);
b += result;
}
a = result;
}
}
enum BP {
f = 1, b = 7, r = 2, a = 1, /*
f = 109, b = 186837516, r = 62279173, //*/
s = 5
}
void main()
{
RowlandSequence rs;
long start, skip;
with(BP) {
rs = RowlandSequence(b, r);
start = f;
skip = s;
}
rs.popFront();
import std.stdio, std.parallelism;
import std.range : take;
auto rsFirst128 = rs.take(128);
foreach(r; rsFirst128.parallel)
{
if(r[0].length > skip)
{
start.writeln(": ", r);
}
start++;
}
}
</code></pre>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/mailman.1275.1711672667.3719.digitalmars-d-learn@puremagic.com[Learn] Re: Setting up a final switch from a list2024-03-28T18:37:21-06:002024-03-28T18:37:21-06:00Jonathan M Davis<pre class="post-text">On Thursday, March 28, 2024 4:21:03 PM MDT Salih Dincer via Digitalmars-d- learn wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>How can we add all members of an enum type to a list without duplicating code?
</span>
As the documentation for EnumMembers explains, you can use std.meta.NoDuplicates to strip out duplicates if you want to do something like generate a switch statement from the list of enum members.
<a rel="nofollow" href="https://dlang.org/phobos/std_traits.html#EnumMembers"><span class="forcewrap">https://</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">phobos/</span><span class="forcewrap">std_traits.</span><span class="forcewrap">html#En</span><span class="forcewrap">umMembers</span></a>
- Jonathan M Davis
</pre>https://forum.dlang.org/post/qeglemurqamdjinqwxge@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-29T00:04:14+00:002024-03-29T00:04:14+00:00Serg Gini<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 23:15:26 UTC, Salih Dincer wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>There is no such thing as parallel programming in D anyway. At least it has modules, but I didn't see it being works. Whenever I use toys built in foreach() it always ends in disappointment</p></span>
<p>I think it just works :)<br />
Which issues did you have with it?</p>
</div>https://forum.dlang.org/post/bxxwsjmentourbigojho@forum.dlang.org[Learn] Re: Unittests pass, and then an invalid memory operation happens after?2024-03-28T23:49:19+00:002024-03-28T23:49:19+00:00Liam McGillivray<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 04:46:27 UTC, H. S. Teoh wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>The whole point of a GC is that you leave everything up to it to clean up. If you want to manage your own memory, don't use the GC. D does not force you to use it; you can import core.stdc.stdlib and use malloc/free to your heart's content.</p>
<p>Unpredictable order of collection is an inherent property of GCs. It's not going away. If you don't like it, use malloc/free instead. (Or write your own memory management scheme.)</p></span>
<p>I disagree with this attitude on how the GC should work. Having to jump immediately from leaving everything behind for the GC to fully manual memory allocation whenever the GC becomes a problem is a problem, which gives legitimacy to the common complaint of D being "garbage-collected". It would be much better if the garbage collector could be there as a backup for when it's needed, while allowing the programmer to write code for object destruction when they want to optimize.</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Anyway, I suppose I'll have to experiment with either manually destroying every object at the end of every unittest, or just leaving more to the GC. Maybe I'll make a separate <code>die</code> function for the units, if you think it's a good idea.</p></span>
<p>I think you're approaching this from a totally wrong angle. (Which I sympathize with, having come from a C/C++ background myself.) The whole point of having a GC is that you <em>don't</em> worry about when an object is collected. You just allocate whatever you need, and let the GC worry about cleaning up after you. The more you let the GC do its job, the better it will be.</p></span>
<p>Now you're giving me conflicting advice. I was told that my current destructor functions aren't acceptable with the garbage collector, and you specifically tell me to leave things to the GC. But then I suggest that I "leave more to the GC" and move everything from the Unit destructor to a specialized <code>die</code> function that can be called instead of <code>destroy</code> whenever they must be removed from the game, which as far as I can see is the only way to achieve the desired game functionality while following your and Steve's advice and not having dangling references. But in response to that, you tell me "I think you're approaching this from the wrong angle". And then right after that, you <em>again</em> tell me to "just let the GC worry about cleaning up after you"? Even if I didn't call <code>destroy</code> at all during my program, as far as I can see, I would still need the <code>die</code> function mentioned to remove a unit on death.</p>
<p>It would be nice if you can clarify your message here. Right now I'm confused. I see no way to take your advice without also doing the <code>die</code> function.</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>As far as performance is concerned, a GC actually has higher throughput than manually freeing objects, because in a fragmented heap situation, freeing objects immediately when they go out of use incurs a lot of random access RAM roundtrip costs, whereas a GC that scans memory for references can amortize some of this cost to a single period of time.</p></span>
<p>By "manually freeing objects", do you mean through <code>destroy</code>? If so that's actually quite disappointing, as D is often described as a "systems programming language", and I thought it would be fun to do these optimizations of object destruction, even if I have the garbage collector as a backup for anything missed. Or did you mean with <code>malloc</code> and <code>free</code>?</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Now somebody coming from C/C++ would immediately cringe at the thought that a major GC collection might strike at the least opportune time. For that, I'd say:</p>
<p>(1) don't fret about it until it actually becomes a problem. I.e., your program is slow and/or has bad response times, and the profiler is pointing to GC collections as the cause. Then you optimize appropriately with the usual practices for GC optimization: preallocate before your main loop, avoid frequent allocations of small objects (prefer to use structs rather than classes), reuse previous allocations instead of allocating new memory when you know that an existing object is no longer used.</p></span>
<p>Well, I suppose that's fine for when the GC problem is specifically over slowness. I'm quite new to D, so I don't really know what it means to "preallocate before your main loop". Is this a combination of using <code>static this</code> constructors and <code>malloc</code>? I haven't used <code>malloc</code> yet. I have tried making static constructors, but every time I've tried them, they caused an error to happen immediately after the program is launched.</p>
<p>I've used C++, but I haven't gotten much done with it. It was PHP where I made the biggest leap in my programming skills. This game is the furthest I've gone at making a complex program from the <code>main</code> loop up.</p>
<p>I suppose I can turn the <code>Tile</code> object into a struct, which I suppose will mean replacing all it's references (outside the map's <code>Tile[][] grid</code>) with pointers. I have thought about this before, since tiles are fundamentally associated with one particular map, but I chose objects mostly so I can easily pass around references to them.</p>
<p>I've already been using structs for the stuff with a short lifespan.</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>(2) Use D's GC control mechanisms to exercise some control over when collections happen. By default, collections ONLY ever get triggered if you try to allocate something and the heap has run out of memory. Ergo, if you don't allocate anything, GC collections are guaranteed not to happen. Use GC.disable and GC.collect to control when collections happen. In one of my projects, I got a 40% performance boost by using GC.disable and using my own schedule of GC.collect, because the profiler revealed that collections were happening too frequently. The exact details how what to do will depend on your project, of course, but my point is, there are plenty of tools at your disposal to exercise some degree of control.</p></span>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>always resort to the nuclear option: slap @nogc on main() and</p></span>
<p>I want to ask about <code>@nogc</code>. Does it simply place restrictions on what I can do? Or does it change the meaning of certain lines? For example, does it mean that I can still create objects, but they will just keep piling up without being cleaned up?</p>
</div>https://forum.dlang.org/post/htbfrgxfwkbuncbfnmwa@forum.dlang.org[Learn] Re: Two chunks but No allocation2024-03-28T23:26:41+00:002024-03-28T23:26:41+00:00Salih Dincer<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 23:08:54 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>You can drop and take from the folded values range.</p>
<p>I got <code>[1, 0.666667, 0.625, 0.619048, 0.618182, 0.618056, 0.618037, 0.618034, 0.618034, 0.618034]</code> from the above code.</p></span>
<p>Thank you so much...</p>
<p>I solved the problem: r.back doesn't work because recurrence() runs forever and you need to use it with take. In other words, the range functions up to the map must have members such as length() and opSlice().</p>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/ykpcfiqfnzysnzchlvuq@forum.dlang.org[Learn] Re: range.chunks(2) error2024-03-28T23:21:37+00:002024-03-28T23:21:37+00:00Salih Dincer<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 17:50:17 UTC, Salih Dincer wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Hi,</p>
<p>When I use the chunks() template with iota(), for instance, with chunks(2), I can access both r.front and r.back. However, in a range of my own type (named iras in the code below), only r.front is working. I think the error given by r.back is not a bug related to chunks, is it?</p></span>
<p>It's really nice to solve a problem on your own. Turns out I needed to add save, opSlice, length and opDollar members to the range.</p>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/rjtzznblijbsdomrllhg@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-28T23:15:26+00:002024-03-28T23:15:26+00:00Salih Dincer<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 20:18:10 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>I didn't know that OpenMP programming could be that easy.<br />
Binary size is 16K, same order of magnitude, although somewhat less.<br />
D advantage is gone here, I would say.</p></span>
<p>There is no such thing as parallel programming in D anyway. At least it has modules, but I didn't see it being works. Whenever I use toys built in foreach() it always ends in disappointment :)</p>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/lcyhqzbquljbtadjquxa@forum.dlang.org[Learn] Re: Two chunks but No allocation2024-03-28T23:08:54+00:002024-03-28T23:08:54+00:00rkompass<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 03:54:05 UTC, Salih Dincer wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>On Wednesday, 27 March 2024 at 20:50:05 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>This works:</p></span>
<p>I decided to give the full code. Maybe then it will be better understood what I mean. I actually pointed out the indirect solution above but it's a bit ugly and I'm sure there must be a better way?</p></span>
<p>I didn't look exactly at you code but at the ranges problem.</p>
<p>Perhaps this is of help:</p>
<pre><code class="language-d">import std.stdio;
import std.range;
import std.algorithm;
void main() {
auto fib = (real a, real b) => recurrence!"a[n-1] + a[n-2]"(a, b);
auto golden3 = fib(1,1).chunks(2).map!(r => r.fold!((a, e) => a/e)).take(10);
writeln(golden3);
}
</code></pre>
<p>I thought what you wanted (and what I found to be an interesting problem) was to convert the subranges delivered by <code>chunks(2)</code> to values that still are generated lazily, without saving them in an array (which converts the range type to a higher one), according to original range.</p>
<p>You can drop and take from the folded values range.</p>
<p>I got <code>[1, 0.666667, 0.625, 0.619048, 0.618182, 0.618056, 0.618037, 0.618034, 0.618034, 0.618034]</code> from the above code.</p>
</div>https://forum.dlang.org/post/mailman.1274.1711665923.3719.digitalmars-d-learn@puremagic.com[Learn] Re: Difference between chunks(stdin, 1) and stdin.rawRead?2024-03-28T15:44:58-07:002024-03-28T15:44:58-07:00H. S. Teoh<pre class="post-text">On Thu, Mar 28, 2024 at 10:10:43PM +0000, jms via Digitalmars-d-learn wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>On Thursday, 28 March 2024 at 02:30:11 UTC, jms wrote:
</span>[...]
<span class="forum-quote"><span class="forum-quote-prefix">> </span>I think I figured it out and the difference is probably in the mode.
<span class="forum-quote-prefix">> </span>This documentation
<span class="forum-quote-prefix">> </span><a rel="nofollow" href="https://learn.microsoft.com/en-us/cpp/c-runtime-library/reference/fread?view=msvc-170"><span class="forcewrap">https://</span><span class="forcewrap">learn.</span><span class="forcewrap">microsoft.com/</span><span class="forcewrap">en-us/cpp/</span><span class="forcewrap">c-runtime-</span><span class="forcewrap">library/</span><span class="forcewrap">reference/</span><span class="forcewrap">fread?view=</span><span class="forcewrap">msvc-170</span></a>
<span class="forum-quote-prefix">> </span>mentions that "If the given stream is opened in text mode,
<span class="forum-quote-prefix">> </span>Windows-style newlines are converted into Unix-style newlines. That
<span class="forum-quote-prefix">> </span>is, carriage return-line feed (CRLF) pairs are replaced by single line
<span class="forum-quote-prefix">> </span>feed (LF) characters."
<span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>And rawRead's documention mentions that "rawRead always reads in binary mode on Windows.", which I guess should have given me a clue. chunks must be using text-mode.
</span>
It's not so much that chunks is using text-mode, but that you opened the file in text mode. On Windows, if you don't want crlf translation you need to open your file with File(filename, "rb"), not just File(filename "r"), because the latter defaults to text mode.
T
<span class="forum-signature">--
There's light at the end of the tunnel. It's the oncoming train.
</span></pre>https://forum.dlang.org/post/jacfwqvccjvaeucuutnu@forum.dlang.org[Learn] Re: Setting up a final switch from a list2024-03-28T22:21:03+00:002024-03-28T22:21:03+00:00Salih Dincer<div class="post-text markdown"><p>On Thursday, 10 August 2023 at 08:33:13 UTC, Christian Köstlin wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>I think one part of the original question (now fanished in the nntp backup) was how to get all enum members into a list without duplicating code.</p>
<pre><code class="language-d">import std.traits : EnumMembers;
import std.stdio : writeln;
import std.algorithm : map;
import std.conv : to;
enum alphabet {
a, b, c, d
}
void main()
{
writeln(EnumMembers!alphabet);
writeln([EnumMembers!alphabet]);
writeln([EnumMembers!alphabet].map!(a => "test" ~a.to!string));
}
</code></pre>
<p>results in</p>
<pre><code class="language-d">abcd
[a, b, c, d]
["testa", "testb", "testc", "testd"]```
</code></pre></span>
<p>How can we add all members of an enum type to a list without duplicating code?</p>
<p>I wonder if this is something we'll see soon as the D language feature?</p>
<p>In the D programming language, this can be achieved using features provided by the language such as __traits and AliasSeq. For instance, the EnumMembers trait from the std.traits module returns all members of an enum type as a tuple. This tuple contains the enum members in sequence, allowing for iteration over them or conversion into a list.</p>
<p>Finally, utilizing these language features to avoid code duplication and write cleaner, more maintainable code is a good practice. Sorry to resurrect this old thread, but what do you think; people living in 2024 ?</p>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/xjtgjywmgkebtskcohhq@forum.dlang.org[Learn] Re: Difference between chunks(stdin, 1) and stdin.rawRead?2024-03-28T22:10:43+00:002024-03-28T22:10:43+00:00jms<pre class="post-text">On Thursday, 28 March 2024 at 02:30:11 UTC, jms wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>Why in the below silly program am I reading both the \r and \n characters when using rawRead in block a, but when looping by 1 byte chunks in block b only appear to be reading the \n characters?
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>I'm on Windows 11 using DMD64 D Compiler v2.107.1 if that matters, but I'm thinking this maybe has something to do with stdin in general that I'm not aware of. Any pointers to understanding what's going on would be appreciated.
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>import std.stdio;
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>void main() {
<span class="forum-quote-prefix">> </span> int i;
<span class="forum-quote-prefix">> </span>a: {
<span class="forum-quote-prefix">> </span> i = 0;
<span class="forum-quote-prefix">> </span> writeln("\nin a");
<span class="forum-quote-prefix">> </span> ubyte[1] buffer;
<span class="forum-quote-prefix">> </span> while (true) {
<span class="forum-quote-prefix">> </span> i++;
<span class="forum-quote-prefix">> </span> stdin.rawRead(buffer);
<span class="forum-quote-prefix">> </span> if (buffer[0] == 13) {
<span class="forum-quote-prefix">> </span> write("CR");
<span class="forum-quote-prefix">> </span> } else if (buffer[0] == 10) {
<span class="forum-quote-prefix">> </span> write("LF");
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> if (i > 5) {
<span class="forum-quote-prefix">> </span> goto b;
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span>b: {
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span> writeln("\n\nin b");
<span class="forum-quote-prefix">> </span> i = 0;
<span class="forum-quote-prefix">> </span> foreach (ubyte[] buffer; chunks(stdin, 1)) {
<span class="forum-quote-prefix">> </span> i++;
<span class="forum-quote-prefix">> </span> if (buffer[0] == 13) {
<span class="forum-quote-prefix">> </span> write("cr");
<span class="forum-quote-prefix">> </span> } else if (buffer[0] == 10) {
<span class="forum-quote-prefix">> </span> write("lf");
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> if (i > 5) {
<span class="forum-quote-prefix">> </span> goto a;
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>}
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>Output:
<span class="forum-quote-prefix">> </span>in a
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>CRLF
<span class="forum-quote-prefix">> </span>CRLF
<span class="forum-quote-prefix">> </span>CRLF
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>in b
<span class="forum-quote-prefix">></span>
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>lf
<span class="forum-quote-prefix">> </span>in a
</span>
I think I figured it out and the difference is probably in the mode. This documentation <a rel="nofollow" href="https://learn.microsoft.com/en-us/cpp/c-runtime-library/reference/fread?view=msvc-170"><span class="forcewrap">https://</span><span class="forcewrap">learn.</span><span class="forcewrap">microsoft.com/</span><span class="forcewrap">en-us/cpp/</span><span class="forcewrap">c-runtime-</span><span class="forcewrap">library/</span><span class="forcewrap">reference/</span><span class="forcewrap">fread?view=</span><span class="forcewrap">msvc-170</span></a> mentions that "If the given stream is opened in text mode, Windows-style newlines are converted into Unix-style newlines. That is, carriage return-line feed (CRLF) pairs are replaced by single line feed (LF) characters."
And rawRead's documention mentions that "rawRead always reads in binary mode on Windows.", which I guess should have given me a clue. chunks must be using text-mode.
</pre>https://forum.dlang.org/post/gbkldssvkuqbhyvjbrai@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-28T21:35:05+00:002024-03-28T21:35:05+00:00Sergey<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 20:18:10 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>D advantage is gone here, I would say.</p></span>
<p>It's hard to compare actually.<br />
Std.parallelism has a bit different mechanics, and I think easier to use. The syntax is nicer.</p>
<p>OpenMP is an well-known and highly adopted tool, which is also quite flexible, but usually used with initially sequential code. And the syntax is not very intuitive.</p>
<p>Interesting point from Dr Russel here: <a rel="nofollow" href="https://forum.dlang.org/thread/qvksmhwkaxbrnggsvtxe@forum.dlang.org">https://forum.dlang.org/thread/qvksmhwkaxbrnggsvtxe@forum.dlang.org</a></p>
<p>However since 2012 OpenMP also got some development and improvement and HPC world is pretty conservative. So it is one of the most popular tool in the area: <a rel="nofollow" href="https://www.openmp.org/wp-content/uploads/sc23-openmp-popularity-mattson.pdf">https://www.openmp.org/wp-content/uploads/sc23-openmp-popularity-mattson.pdf</a><br />
With MPI.. But probably with AI and GPU revolution the balance will shift a bit to CUDA-like technologies.</p>
</div>https://issues.dlang.org/show_bug.cgi?id=24465[Issues] [Issue 24465] New: Tuple does not get a copy constructor when its members need it2024-03-28T21:06:11+00:002024-03-28T21:06:11+00:00issues.dlang@jmdavisProg.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24465"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24465</span></a>
Issue ID: 24465
Summary: Tuple does not get a copy constructor when its members
need it
Product: D
Version: D2
Hardware: All
OS: All
Status: NEW
Severity: normal
Priority: P1
Component: phobos
Assignee: nobody@puremagic.com
Reporter: issues.dlang@jmdavisProg.com
An example:
---
import std.typecons;
void main()
{
Tuple!(int, S) t;
foo(t);
}
struct S
{
int i;
this(ref return scope inout(S) rhs) scope @trusted inout pure nothrow
{
this.i = rhs.i;
}
}
void foo(Tuple!(int, S))
{
}
---
It fails with
---
bug.d(6): Error: function `foo` is not callable using argument types
`(Tuple!(int, S))`
bug.d(6): `struct Tuple` does not define a copy constructor for
`Tuple!(int, S)` to `Tuple!(int, S)` copies
bug.d(19): `bug.foo(Tuple!(int, S))` declared here
---
I _think_ that the problem is that this constructor
---
this(U)(U another)
if <span class="forcewrap">(areBuildCom</span><span class="forcewrap">patibleTuples!</span><span class="forcewrap">(typeof(this),</span> U))
{
field[] = another.field[];
}
---
is managing to serve as an rvalue constructor, which unfortunately, is incompatible with copy constructors (I'm not convinced that it should be, but it is). But regardless of what the exact reason that it's currently failing is, it should work to create and copy Tuples which contain types with copy constructors.
--
</pre>https://issues.dlang.org/show_bug.cgi?id=22239#c5[Issues] [Issue 22239] Can't migrate from postblits if they are used without frame pointer2024-03-28T20:43:29+00:002024-03-28T20:43:29+00:00Jonathan M Davis<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=22239"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">22239</span></a>
Jonathan M Davis <issues.dlang@jmdavisProg.com> changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
CC| |issues.dlang@jmdavisProg.co
| |m
--- Comment #5 from Jonathan M Davis <issues.dlang@jmdavisProg.com> ---
When trying to add a copy constructor to a type in an existing code base, I've been seeing a lot of errors about not having a frame pointer (particularly from std.algorithm code), which has been incredibly annoying to deal with, and it has made no sense to me that a frame pointer would even be needed, since the only difference is that a copy constructor has been added (though honestly, the whole frame pointer stuff is incredibly confusing in general). So, I'm _guessing_ that this is the issue that I've been hitting, but man, it would be nice if the compiler didn't decide that it needed a frame pointer that it can't have just because a type that's involved got a copy constructor added to it.
--
</pre>https://issues.dlang.org/show_bug.cgi?id=20876#c10[Issues] [Issue 20876] generated constructor always inout regardless of ability of fields to use inout2024-03-28T20:34:09+00:002024-03-28T20:34:09+00:00Jonathan M Davis<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=20876"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">20876</span></a>
Jonathan M Davis <issues.dlang@jmdavisProg.com> changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
CC| |issues.dlang@jmdavisProg.co
| |m
Hardware|x86_64 |All
OS|Linux |All
--- Comment #10 from Jonathan M Davis <issues.dlang@jmdavisProg.com> ---
This really needs to be improved so that we're not just creating an inout copy constructor when an implicit copy constructor needs to be generated. It simply does not work when the member variable with a copy constructor has a different signature, and with all of the situations where the programmer has _zero_ control over the type with the implicit constructor (e.g. it's a Voldemort range type from a function in Phobos or some other library), we really need to be able to rely on implicit copy constructors actually working with other signatures.
At this point, it's turning out to be shockingly difficult to add a copy constructor to a type that's core to the code base that I work on at work, and the fact that implicit constructor generation is so simplistic (and therefore fails so easily) is a major contributing factor. And right now, I'm forced to use an inout constructor even though that's _really_ not what I should be using in this case, because the implicit constructor generation doesn't work with anything else.
IMHO, we really need to look at having the compiler generate the full set of copy constructors that are necessary to work with the member variables and not just a single one that tries to work in general but really doesn't. There are just too many situations where you don't control the code with the implicit constructor and therefore can't make it do the right thing, whereas in almost all cases like that it should be very possible for the compiler to generate a set of copy constructors that actually work - but instead, it just punts on the issue and tries a single inout copy constructor.
This isn't the only issue that causes major problems with copy constructors, but it's a significant one.
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24464[Issues] [Issue 24464] New: [REG 2.107.0] CTFE error when trying to allocate an array in betterC mode2024-03-28T20:30:30+00:002024-03-28T20:30:30+00:00spoov0.707@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24464"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24464</span></a>
Issue ID: 24464
Summary: [REG 2.107.0] CTFE error when trying to allocate an
array in betterC mode
Product: D
Version: D2
Hardware: All
OS: All
Status: NEW
Keywords: betterC, CTFE
Severity: regression
Priority: P1
Component: dmd
Assignee: nobody@puremagic.com
Reporter: spoov0.707@gmail.com
```
int f()() => new int[](1)[0];
pragma(msg, f());
```
Compiling the code above with DMD 2.106.1 using the command
dmd -c -betterC test.d
produces the correct result
0
Since DMD 2.107.0 the following error gets generated:
test.d(1): Error: expression `new int[](1u)` allocates with the GC and cannot
be used with switch `-betterC`
test.d(2): Error: CTFE failed because of previous errors in `f`
test.d(2): while evaluating `pragma(msg, f())`
--
</pre>https://forum.dlang.org/post/vlhyykljejapubhaeqof@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-28T20:18:10+00:002024-03-28T20:18:10+00:00rkompass<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 14:07:43 UTC, Salih Dincer wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>On Thursday, 28 March 2024 at 11:50:38 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Turning back to this: Are there similarly simple libraries for C, that allow for<br />
parallel computation?</p></span>
<p>You can achieve parallelism in C using libraries such as OpenMP, which provides a set of compiler directives and runtime library routines for parallel programming.</p>
<p>Here’s an example of how you might modify the code to use OpenMP for parallel processing:</p>
<pre><code class="language-c"> . . .
#pragma omp parallel for reduction(+:result)
for (int s = ITERS; s >= 0; s -= STEPS) {
result += leibniz(s);
}
. . . ```
To compile this code with OpenMP support, you would use a command like gcc -fopenmp your_program.c. This tells the GCC compiler to enable OpenMP directives. The #pragma omp parallel for directive tells the compiler to parallelize the loop, and the reduction clause is used to safely accumulate the result variable across multiple threads.
SDB@79
</code></pre></span>
<p>Nice, thank you.<br />
It worked endlessly until I saw I had to correct the <code>for</code> to<br />
<code>for (int s = ITERS; s > ITERS-STEPS; s--)</code><br />
Now the result is:</p>
<pre><code>3.1415926535897936
Execution time: 0.212483 (seconds).
</code></pre>
<p>This result is sooo similar!</p>
<p>I didn't know that OpenMP programming could be that easy.<br />
Binary size is 16K, same order of magnitude, although somewhat less.<br />
D advantage is gone here, I would say.</p>
</div>https://forum.dlang.org/post/kdikfsffwggohnlsdqbv@forum.dlang.org[Learn] range.chunks(2) error2024-03-28T17:50:17+00:002024-03-28T17:50:17+00:00Salih Dincer<div class="post-text markdown"><p>Hi,</p>
<p>When I use the chunks() template with iota(), for instance, with chunks(2), I can access both r.front and r.back. However, in a range of my own type (named iras in the code below), only r.front is working. I think the error given by r.back is not a bug related to chunks, is it?</p>
<pre><code class="language-d">import std.array, std.algorithm,
std.range,
std.stdio;
void main()
{
auto rng1 = iota!real(24.0, 1321.0, 16.5).take(8);
auto rng2 = iras!real(24.0, 1321.0, 16.5).take(8);
auto noError = rng1.chunks(2)
.map!(r =>
r.back - r.front);
assert(noError.equal([16.5, 16.5, 16.5, 16.5]));
/*
auto error = rng2.chunks(2)
.map!(r =>
r.back - r.front);/*
main.d(18): Error: none of the overloads of template
`std.range.primitives.back` are callable using
argument types `!()(Take!(InclusiveRange))`*/
}
/*
* iras v3
* (inclusiveRange) Source:
* https://forum.dlang.org/post/bnnxentwstkjnxkychro@forum.dlang.org
*/
</code></pre>
<p>The same problem occurs here:</p>
<pre><code class="language-d">struct Range(T)
{
T n = 3;
bool empty;
alias back = front;
auto front() => n.cube - n * 0.5;
auto popFront() => n += 2;
auto backFront() => n -= 2;
}
</code></pre>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/mailman.1269.1711647152.3719.digitalmars-d-learn@puremagic.com[Learn] Re: Opinions on iterating a struct to absorb the decoding of a CSV?2024-03-28T10:32:04-07:002024-03-28T10:32:04-07:00H. S. Teoh<pre class="post-text">On Thu, Mar 28, 2024 at 05:23:39PM +0000, Andy Valencia via Digitalmars-d-learn wrote: [...]
<span class="forum-quote"><span class="forum-quote-prefix">> </span> auto t = T();
<span class="forum-quote-prefix">> </span> foreach (i, ref val; t.tupleof) {
<span class="forum-quote-prefix">> </span> static if (is(typeof(val) == int)) {
<span class="forum-quote-prefix">> </span> val = this.get_int();
<span class="forum-quote-prefix">> </span> } else {
<span class="forum-quote-prefix">> </span> val = this.get_str();
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> }
<span class="forum-quote-prefix">> </span> return t;
<span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>So you cue off the type of the struct field, and decode the next CSV field, and put the value into the new struct.
<span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>Is there a cleaner way to do this? This _does_ work, and gives me very compact code.
</span>
This is pretty clean, and is a good example of DbI. I use the same method in my fastcsv experimental module to transcribe csv to an array of structs:
<a rel="nofollow" href="https://github.com/quickfur/fastcsv"><span class="forcewrap">https://</span><span class="forcewrap">github.com/</span><span class="forcewrap">quickfur/</span><span class="forcewrap">fastcsv</span></a>
T
<span class="forum-signature">--
Today's society is one of specialization: as you grow, you learn more and more about less and less. Eventually, you know everything about nothing.
</span></pre>https://forum.dlang.org/post/lameqoksspcmnpvxsjir@forum.dlang.org[Learn] Opinions on iterating a struct to absorb the decoding of a CSV?2024-03-28T17:23:39+00:002024-03-28T17:23:39+00:00Andy Valencia<pre class="post-text">I wanted a lightweight and simpler CSV decoder. I won't post the whole thing, but basically you instantiate one as:
struct Whatever {
...
}
...
f = File("path.csv", "r");
auto c = CSVreader!Whatever(f);
foreach (rec; c) { ...
CSVreader is, of course, templated:
struct CSVreader(T) {
...
}
and the innermost bit of CSVreader is:
auto t = T();
foreach (i, ref val; t.tupleof) {
static if (is(typeof(val) == int)) {
val = this.get_int();
} else {
val = this.get_str();
}
}
return t;
So you cue off the type of the struct field, and decode the next CSV field, and put the value into the new struct.
Is there a cleaner way to do this? This _does_ work, and gives me very compact code.
</pre>https://issues.dlang.org/show_bug.cgi?id=24463[Issues] [Issue 24463] New: scope(failure) with a break/continue breaks safety2024-03-28T16:48:25+00:002024-03-28T16:48:25+00:00elpenguino+D@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24463"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24463</span></a>
Issue ID: 24463
Summary: scope(failure) with a break/continue breaks safety
Product: D
Version: D2
Hardware: All
OS: All
Status: NEW
Keywords: accepts-invalid, safe
Severity: critical
Priority: P1
Component: dmd
Assignee: nobody@puremagic.com
Reporter: elpenguino+D@gmail.com
```
void main() @safe {
do {
scope(failure) break;
assert(0);
} while(0);
}
```
```
void main() @safe {
do {
scope(failure) continue;
assert(0);
} while(0);
}
```
Essentially the same issue as <a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24460[Issues] [Issue 24460] scope(failure) with a goto breaks safety2024-03-28T16:48:25+00:002024-03-28T16:48:25+00:00elpenguino+D@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
elpenguino+D@gmail.com changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
See Also| |<a rel="nofollow" href="https://issues.dlang.org/sh">https://issues.dlang.org/sh</a>
| |ow_bug.cgi?id=24463
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24460[Issues] [Issue 24460] scope(failure) with a goto breaks safety2024-03-28T16:46:34+00:002024-03-28T16:46:34+00:00elpenguino+D@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
elpenguino+D@gmail.com changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
See Also| |<a rel="nofollow" href="https://issues.dlang.org/sh">https://issues.dlang.org/sh</a>
| |ow_bug.cgi?id=24462
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24462[Issues] [Issue 24462] New: scope(failure) with a throw expression breaks safety2024-03-28T16:46:34+00:002024-03-28T16:46:34+00:00elpenguino+D@gmail.com<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24462"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24462</span></a>
Issue ID: 24462
Summary: scope(failure) with a throw expression breaks safety
Product: D
Version: D2
Hardware: All
OS: All
Status: NEW
Keywords: accepts-invalid, safe
Severity: critical
Priority: P1
Component: dmd
Assignee: nobody@puremagic.com
Reporter: elpenguino+D@gmail.com
```
void main() @safe {
try {
scope(failure) throw new Exception("");
assert(0);
} catch (Exception) {}
}
```
Essentially the same issue as <a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
--
</pre>https://forum.dlang.org/post/uu40op$258g$1@digitalmars.com[General] Re: Memory safe in D2024-03-29T04:01:45+13:002024-03-29T04:01:45+13:00Richard (Rikki) Andrew Cattermole<pre class="post-text">
On 28/03/2024 7:24 AM, Lance Bachmeier wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>On Wednesday, 27 March 2024 at 17:07:57 UTC, Meta wrote:
<span class="forum-quote-prefix">> </span>
<span class="forum-quote"><span class="forum-quote-prefix">>> </span>I say this all as someone who would love to have a robust typestate system for D, but it just ain't gonna happen. D is just not the language for it. Your best bet is to either propose it for OpenD, or fork it and implement it yourself.
</span><span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>I'd say the best strategy would be to write up some examples using real code showing large benefits. Then it might have a chance. The current proposal not only assumes the reader is familiar with the concepts, but that they can envision substantial benefits in their own code. I had no more idea of the benefits after reading the proposal than I did before.
</span>
First example has been added, thanks to Razvan's recent Rust link:
However because it doesn't enable you to do anything new, and only ever checks against certain logic errors it has been very difficult for me to create examples it needs a different head space which I expected to deal with later, oh well.
```d
T* makeNull(T)() @safe {
return null;
}
void useNull() @safe {
int* var = makeNull!int();
// var is in type state initialized as per makeNull return state
*var = 42;
// segfault due to var being null
}
```
What we want to happen instead:
```d
T* makeNull(T)(/* return'initialized */) @safe {
return null;
// type state default is more than the type state initialized
// so it is accepted
}
void useNull() @safe {
int* var = makeNull!int();
// var is in type state initialized as per MakeNull return state
// perform load via var variable
// this will error due to initialized is less than the nonnull type state
// Error: Variable var is in type state initialized which could be null, cannot write to it
*var = 42;
}
```
To fix, simply check for null!
```d
void useNull() @safe {
int* var = makeNull!int();
// var is in type state initialized as per MakeNull return state
if (var !is null) {
// in scope, assume var is in type state nonnull
*var = 42;
}
}
```
</pre>https://issues.dlang.org/show_bug.cgi?id=24460#c2[Issues] [Issue 24460] scope(failure) with a goto breaks safety2024-03-28T14:37:35+00:002024-03-28T14:37:35+00:00RazvanN<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
--- Comment #2 from RazvanN <razvan.nitu1305@gmail.com> ---
Scratch that. The problem is that you are not rethrowing the exception/error if you use a goto.
--
</pre>https://issues.dlang.org/show_bug.cgi?id=24460#c1[Issues] [Issue 24460] scope(failure) with a goto breaks safety2024-03-28T14:29:50+00:002024-03-28T14:29:50+00:00RazvanN<pre class="post-text"><a rel="nofollow" href="https://issues.dlang.org/show_bug.cgi?id=24460"><span class="forcewrap">https://</span><span class="forcewrap">issues.</span><span class="forcewrap">dlang.org/</span><span class="forcewrap">show_bug.</span><span class="forcewrap">cgi?id=</span><span class="forcewrap">24460</span></a>
RazvanN <razvan.nitu1305@gmail.com> changed:
What |Removed |Added
<span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span><span class="forcewrap">----------</span><span class="forcewrap">---------</span>
CC| |razvan.nitu1305@gmail.com
--- Comment #1 from RazvanN <razvan.nitu1305@gmail.com> ---
This doesn't seem like a safety violation. Rather that the scope failure should not catch the assert error.
--
</pre>https://forum.dlang.org/post/ahhypeurplzpvjixkxvz@forum.dlang.org[Learn] Re: Why is this code slow?2024-03-28T14:07:43+00:002024-03-28T14:07:43+00:00Salih Dincer<div class="post-text markdown"><p>On Thursday, 28 March 2024 at 11:50:38 UTC, rkompass wrote:</p>
<span class="forum-quote"><span class="forum-quote-prefix">> </span><p>Turning back to this: Are there similarly simple libraries for C, that allow for<br />
parallel computation?</p></span>
<p>You can achieve parallelism in C using libraries such as OpenMP, which provides a set of compiler directives and runtime library routines for parallel programming.</p>
<p>Here’s an example of how you might modify the code to use OpenMP for parallel processing:</p>
<pre><code class="language-c">#include <stdio.h>
#include <time.h>
#include <omp.h>
#define ITERS 1000000000
#define STEPS 31
double leibniz(int i) {
double r = (i == ITERS) ? 0.5 * ((i % 2) ? -1.0 : 1.0) / (i * 2.0 + 1.0) : 0.0;
for (--i; i >= 0; i -= STEPS)
r += ((i % 2) ? -1.0 : 1.0) / (i * 2.0 + 1.0);
return r * 4.0;
}
int main() {
double start_time = omp_get_wtime();
double result = 0.0;
#pragma omp parallel for reduction(+:result)
for (int s = ITERS; s >= 0; s -= STEPS) {
result += leibniz(s);
}
// Calculate the time taken
double time_taken = omp_get_wtime() - start_time;
printf("%.16f\n", result);
printf("%f (seconds)\n", time_taken);
return 0;
}
</code></pre>
<p>To compile this code with OpenMP support, you would use a command like gcc -fopenmp your_program.c. This tells the GCC compiler to enable OpenMP directives. The #pragma omp parallel for directive tells the compiler to parallelize the loop, and the reduction clause is used to safely accumulate the result variable across multiple threads.</p>
<p>SDB@79</p>
</div>https://forum.dlang.org/post/uu3rsl$1nd6$1@digitalmars.com[General] Re: Blazingly 🔥 fast 🚀 memory vulnerabilities, written in 100% safe Rust. 🦀2024-03-29T02:38:29+13:002024-03-29T02:38:29+13:00Richard (Rikki) Andrew Cattermole<pre class="post-text">On 29/03/2024 2:35 AM, RazvanN wrote:
<span class="forum-quote"><span class="forum-quote-prefix">> </span>Just for fun: <a rel="nofollow" href="https://github.com/Speykious/cve-rs"><span class="forcewrap">https://</span><span class="forcewrap">github.com/</span><span class="forcewrap">Speykious/</span><span class="forcewrap">cve-rs</span></a>
<span class="forum-quote-prefix">> </span>
<span class="forum-quote-prefix">> </span>"cve-rs allows you to introduce common memory vulnerabilities (such as buffer overflows and segfaults) into your Rust program in a memory safe manner."
</span>
You gotta love a lack of type state analysis and value tracking lol.
</pre>https://forum.dlang.org/post/pqdgexncwjlargnhygyn@forum.dlang.org[General] Blazingly 🔥 fast 🚀 memory vulnerabilities, written in 100% safe Rust. 🦀2024-03-28T13:35:27+00:002024-03-28T13:35:27+00:00RazvanN<div class="post-text markdown"><p>Just for fun: <a rel="nofollow" href="https://github.com/Speykious/cve-rs">https://github.com/Speykious/cve-rs</a></p>
<p>"cve-rs allows you to introduce common memory vulnerabilities (such as buffer overflows and segfaults) into your Rust program in a memory safe manner."</p>
</div>