@SanderSkjegstad@lea_fac There is something missing from Casey's voice though, I think maybe some lower frequencies. It sounds kinda like a very 70 year old man's voice, or am I tripping?
Uniform buffers suck in general. Making a lot of small buffers to store a single struct is a bit wasteful, as the API implementation now has to have a tracking data structure, probably even hash tables, god forbid.
Pointers in shaders were supported since like mid-2010ish hardware. You can just allocate all of your "uniforms" from a single buffer, and only pass a single pointer to a shader, that way you can access those uniforms by offset, as long as the access is uniform.
I'm considering of adding ability to generate structs during compile time to my language. The idea seems fine to me in some cases. Yes, there is a complexity concern and careful control of the struct layout is more difficult, but for some things that are not crucial it is probably fine. But I'm having trouble coming up with some (even vague) examples of where this might be useful, so I'm still on a fence about it.
The LSP/IDE should not have an issue with it, as the compile time code that generates the struct should already have been ran. You IDE should have an option to show an alternative view of the struct - show all of the generated members, as it already should have a struct layout visualizer, if it is worth anything.
The compilation time shouldn't be a big problem in theory, but this is C++ and the implementations are so complex, that you can't really expect much here.
People are worried about the syntax of reflection, but I’m afraid of something else. I expect reflection to be abused on a massive scale, to the point where no LSP will be able to find a type definition for you, and compile time will be comparable to a flight to the Andromeda Nebula.
C++ has been tunred more and more into an abomination with every standard since C++11, it is became a joke.
I don't even care to do research, but do they even support runtime reflection (introspection only, as you can't change the structs at runtime)?
@SebAaltonen I can't seem to find any of the previous SIGGRAPH talks, only some strange bits and pieces. I assume they are not recording any and not interested in publishing any of them? kinda sucks..
Wanted to give the handmade/data-oriented style a shot, so rewrote the codebase in pure c, no c++ stl or c++ features.
Over 1k lines gone, and look at the files! 87 files down to 13. identical functionality. The biggest win (and the reason I did this in the first place) is that compile times went from ~9seconds down to ~240ms.
Ok, NOW i'm starting to understand the anti-oop folks, this is wild
@Anthony_Bonato Wow, really cool. So 1 conflicts with 2, 1+2 being false conflicts with 3. So 1,2,3 cannot be true means that 4 cannot be true also. Which makes 5 true, which in turn makes 6 false because 5 and 6 is the same and 6 being true makes 5 false.
So the anwser is 5.
@skdh So if we measure only the momentum and the position is still uncertain, do we get the interference pattern in a double-slit experiment? If so we could figure out which slit the electron went through, just by looking at which slit the measured momentum vector points, no?
What I don't fully understand is - in order to keep the patch application async with the UI, while the UI is still able to append patches and render the buffer, you would have to have a second copy of the big buffer, in a kind of a double-buffer swap scheme, right? Which naturally doubles the memory requirement..
And you would have to have another copy of EOL map/cache for this also?
I bought a Keychron M6 two weeks ago, the best mouse I've ever used, very happy. No garbo software to install, has type-c, 2.4 ghz dongle and pairs with up to 3 BT devices.
Really comfy for my hand, no pain using it all day. The side scroll wheel is a little stiff, but I don't need it really. I just wish the forward/back buttons were a smidge larger. Cannot yet report on battery life, but been using it for a week now since the last time I plugged it in.
I've did a bit of Scheme at uni, and never done Common LISP, even though I'm aware of the curse of lisp macros and hoping to avoid that :)
My main driving force is to fix problems with C/C++, so with this macro system I'm trying to make macros be part of the language's semantics instead of being lexical preprocessing/replacement tricks.
The cusom iteration stuff is being done with crazy macros in C, where people usually #define my_for() to be able to mimic the for loop at the usage site - and then do even crazier things on top of that because C lacks a way to break/continue from nested loops.
So my starting point was the idea to represent as much of the craziness people do with macros in C as language features, but now as I've explored the first steps of making macros - it will become a central point of a bunch of smaller features that will make macros more powerful. And the core macro system would itself be used as workhorse of a bunch of other, more constrained/focused tiny features.
On memory - there's multiple things that can be done here.
1. In the detailed compilation info on the first screenshot - the current projected memory usage is 345 Mb per mil LoC. I think that number is a little low, it will be closer to half a gig probably. That is around ~5 gigs per 10 million LoC - is that too much? But still I have little confidence in that number, we'll have to see when I get to try to make a bigger (~100k LoC) project to see how that number scales.
2. Currently as the compiler is written in in=>process=>output style, the memory footprint can be reduced by throwing away all of the input data for the previous pass, which I'm not doing atm.
3. There is no dependency between the procedure bodies (unless inlining pass is performed), so in a limit, it would be possible to keep all of the info about global symbols like structs/procedure headers/other types and just the body of a single procedure that is being processed at a time. I'm not doing any kind of dependency graph to figure out what each procedure really depends on - that is going to kill the compilation speed.
I've looked at D a long time ago, and was interested in it, but never really got to try for some reason. The only thing I remember that pushed me away - was the GC. Now that I have my own language in a quite usable state - I don't really care about using any other languages, except whatever I have to use for my job.
This is what made me decide that C++ just sucks and the reason I've started to work on my own lang.
The work goes a bit slow im my spare time, unfortunately, and it is very far from production quality but it is progressing and quite usable for simple things.
I would like to work on a bigger test project soon to see how the performance of my compiler scales, but knowing how almost linear it is, the extrapolation has some merit.
It is currently single threaded and the architecture is maintained in a state, where it would be quite easy to parallelize. And LLVM is dog slow, I need to do something about it, most likely I will make my own x86 backend at some point.
These are the numbers on my 9800x3d for a simple vulkan 3d app (the loc includes all imported modules, including vulkan bindings):
It might not be clear from the screenshot above, but I'm playing around with an idea of allowing the user to use the macro system to build custom control flow constructs. Mainly it was meant as a solution for how the user can define iteration over custom data structures, but grew into something a bit more generic during design space exploration. It is in progress, things might change.
So the :while is a label of the code block, and the body! is the expansion/insertion of the implicitly passed code agrument. There is a label alias [:while] part, mapping the :myLoop label to the :while one, so that break myLoop; turns into a break while; upon insertion.
There a bunch of (hopefully useful) powerful features still in the design phase.
I'm just trying things out to see what sticks basically.
In pursuit of "performance without going insane", I've settled on a very simple design - just classic linear parser => sema => opt => backend. Each pass is written input => process => output style, so the input always stays immutable. The compiler sees all of the app code at once (minus the libs that are linked of course). The app code consists of a set of modules, and each module can have multiple source files, linked by imports into a graph of modules. Also I'm being very careful with the internals to make sure that the compiler will be parallelizable at some point in the future, when I get to doing that.
The language is native, C-like, my view on "what C++ should have been" kind of a thing. Mainly targeting desktop/server app dev + emedded MCU dev.
Language has all of the basics like procedures, structs/unions, enums, type aliases, defer statement, parametric polymorphism for structs/procedures, procedure overloading, operator overloading (still in design phase), hygenic macros (a few tiny things not done yet), limited compile-time evaluation (in design). It doesn't support cpp-like oop directly (should be able to emulate it with macros & defer).
I've made sure to be very careful with syntax design to make it both easy to understand and trivial to parse in a single pass without compromises like order of definitions mattering.
@ce_epistafi Шашлик виходить дуже круто, особливо курячий. А картоплю ніяк посмажити не може, треба нарізати дуже тонкими полосками і після 20хв в грилі починають підгорати зверху, а всередині ще тверді.
Identify the set of operations that you intend to do perform with the data, design the data format in a way that makes the operations do optimal memory access patterns. Profit from 1000+x performance increase compared to RDMSes, more predictable performance (even real-time perf guarantee if you are into that sort of a thing), and much simpler code that only does what is needed that is a lot easier to validate (or even prove).
You'll get mad at me for saying this...but public transportation is so obviously more economically efficient than having your own car, I think it's going to be the default soon.
Your car / truck is idle 90% of the day. Meanwhile, buses targets what 5%, maybe at worst 10% idle.
you’ll get mad at me for saying this…but cloud gaming is so obviously more economically efficient than physical hardware I think it’s going to be the default soon.
your home console / pc is idle 90%+ of the day. meanwhile, data centers targets what, 5%, maybe at worst 10% idle.
every second a cloud gamer isn’t gaming, that hardware is being used for someone else, training, etc.
I think there should be a new measurement, something like cost-per effective FLOP hour that takes into account the TCO + effective utilization.
If a gamer spends $500 on a GPU, uses it for 3 years, but it’s only fully active ~5% of that period…the cost-per relative FLOP hour is crazy high! Meanwhile, a $50,000 datacenter GPU might have a *LOWER* cost-per FLOP hour just because the effective utilization is 90+%.