Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 03:21:51 UTC, jfondren wrote: On Thursday, 30 September 2021 at 03:13:28 UTC, jfondren wrote: As provided, loadSymbol without the "static if": 965K libhipengine_api.a with `mixin(loadSymbol("name"))` instead of a template: 749K libhipengine_api.a The difference goes down to 66K vs. 60K with `dub -brelease --compiler=gdc`. ldc's not as slim but still much better than dmd, and -brelease is actually much less significant. So dmd's the main culprit for the bloat here. huh. But since you have importPaths-ldc perhaps you weren't using dmd to begin with. Yup. The mixin(loadSymbol("")) seems the best way to do. I believe that should be the option for loading separated symbols while loadSymbols version is the best for loading a lot of symbols(IDK how expensive is mixing a lot of functions) as it costs 1KB per instantiation. I'm actually using DMD and LDC, dmd compiles a bit faster, but I use ldc for deploying it. Never used GDC.
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 03:13:28 UTC, jfondren wrote: As provided, loadSymbol without the "static if": 965K libhipengine_api.a with `mixin(loadSymbol("name"))` instead of a template: 749K libhipengine_api.a The difference goes down to 66K vs. 60K with `dub -brelease --compiler=gdc`. ldc's not as slim but still much better than dmd, and -brelease is actually much less significant. So dmd's the main culprit for the bloat here. huh. But since you have importPaths-ldc perhaps you weren't using dmd to begin with.
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 02:31:50 UTC, Hipreme wrote: https://github.com/MrcSnm/HipremeEngine/tree/hotload/api You may try messing at the module api.graphics.g2d.renderer2d There is a function called initG2D Try changing it from loadSymbols to each one loadSymbol. You can just dub at the folder api. The version I checked out, 2874073b54, doesn't have a loadSymbols. As provided, loadSymbol without the "static if": 965K libhipengine_api.a with `mixin(loadSymbol("name"))` instead of a template: 749K libhipengine_api.a https://gist.github.com/jrfondren/d776ccffb105f464b53c53712656a1d3 That's probably disappointing, since it's a much less pleasant interface, but what you could do is take the both entire `extern(C) void function() beginSprite; ... loadSymbol!beginSprite;` blocks and put them in one string literal that you process with a function and mixin once. Now instead of an annoying macro alternative you have a DSL for DLL-extern functions.
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 02:22:35 UTC, jfondren wrote: On Thursday, 30 September 2021 at 01:44:57 UTC, jfondren wrote: On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` If symName is always a string literal, then you don't need to append a "\0"; string literals always have a trailing NUL after them, and they autoconvert to const(char)[] so you don't need the .ptr either. Playing around with this, with a mock-up of your code, doesn't change object size at all. Is the actual source available, that you're seeing this with? https://github.com/MrcSnm/HipremeEngine/tree/hotload/api You may try messing at the module api.graphics.g2d.renderer2d There is a function called initG2D Try changing it from loadSymbols to each one loadSymbol. You can just dub at the folder api.
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 01:44:57 UTC, jfondren wrote: On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` If symName is always a string literal, then you don't need to append a "\0"; string literals always have a trailing NUL after them, and they autoconvert to const(char)[] so you don't need the .ptr either. Playing around with this, with a mock-up of your code, doesn't change object size at all. Is the actual source available, that you're seeing this with?
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 02:09:50 UTC, Hipreme wrote: I could reduce by almost 100kb of code by instead of using the former option, I use: yes this is what id o you can list the Ts in an interface too. see my simpledisplay.d `interface GL` for example I do still don't think that this should be the answer, as the alias problem is not yet solved. It takes a lot of size for functions that could be only syntactic sugar, where C would be a lot better well it must generate functions for each thing there by definition and since you call them at runtime it can't cut them out either. so this is kinda meh you MIGHT be able to do a tempalte that forwards to a single runtime function though. but i seriously need to g2g maybe can look tomorrow
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 02:02:19 UTC, Hipreme wrote: Instead of writing myFunction = cast(typeof(myFunction))_loadSymbol(_dll, "myFunction"); I could write loadSymbol!myFunction; But if no other way is found of doing that, I will do the massive rewriting. --- void function() x; void load(void* thing, string name) { // this lhs cast is the magic, the rhs cast unneeded in reality cuz GetProcAddress returns void* naturally * cast(void**) thing = cast(void*) 0xdeadbeef; } void main() { // no cast here but yes repeated name load(, "foo"); // casts needed here just to do the comparison assert(cast(void*) x == cast(void*) 0xdeadbeef); } --- A little void casting inside the function can do the trick. You will have to pass the name separately though. im off to bed ttyl
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` The main problem is that this function is costing 2KB per instantiation, which is something pretty high. Specially if I inline, there is almost no cost when compared to its inline version. Trying to use pragma(inline, true) didn't do anything too. If I understood correctly, mixin template would be some way to actually inline anything. The problem is that I can't have any kind of expression inside it, so, that's the only way I could think in how to do it. Optimization seems to don't take care of that behaviour too. I would like to know which approach could I take for making something like C's #define for that. As this function could be really rewritten as a macro if I were coding in C, the cost is too high for a function that would be only a syntactic sugar I could reduce by almost 100kb of code by instead of using the former option, I use: ``` void loadSymbols(Ts...)() { static foreach(s; Ts) s = cast(typeof(s))_loadSymbol(_dll, s.stringof); } ``` Then instead of making a call for each one, I just pass a list of templates, this would only create one instantiation per need. I do still don't think that this should be the answer, as the alias problem is not yet solved. It takes a lot of size for functions that could be only syntactic sugar, where C would be a lot better
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 02:02:19 UTC, Hipreme wrote: On Thursday, 30 September 2021 at 01:56:42 UTC, Basile B. wrote: On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` The main problem is that this function is costing 2KB per instantiation, which is something pretty high. Specially if I inline, there is almost no cost when compared to its inline version. Trying to use pragma(inline, true) didn't do anything too. cant you just use a regular functions ? loading happens at runtime right ? The entire reason to having that function is having that syntax which would pretty much do the monkey's job for me: Instead of writing myFunction = cast(typeof(myFunction))_loadSymbol(_dll, "myFunction"); I could write loadSymbol!myFunction; But if no other way is found of doing that, I will do the massive rewriting. Anyway, I don't think the problem is not in the way I'm doing, but the output, as that template could easily be inlined well ok. Maybe try to see if overloads void loadSymbol(alias s)() void loadSymbol(alias s, string symName)() helps. That save the static if. In addition there's the null sentinel that can save a bit of memory, as you've been suggested.
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 01:56:42 UTC, Basile B. wrote: On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` The main problem is that this function is costing 2KB per instantiation, which is something pretty high. Specially if I inline, there is almost no cost when compared to its inline version. Trying to use pragma(inline, true) didn't do anything too. cant you just use a regular functions ? loading happens at runtime right ? The entire reason to having that function is having that syntax which would pretty much do the monkey's job for me: Instead of writing myFunction = cast(typeof(myFunction))_loadSymbol(_dll, "myFunction"); I could write loadSymbol!myFunction; But if no other way is found of doing that, I will do the massive rewriting. Anyway, I don't think the problem is not in the way I'm doing, but the output, as that template could easily be inlined
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` The main problem is that this function is costing 2KB per instantiation, which is something pretty high. Specially if I inline, there is almost no cost when compared to its inline version. Trying to use pragma(inline, true) didn't do anything too. cant you just use a regular functions ? loading happens at runtime right ?
Re: 0 cost template instantiation
On Thursday, 30 September 2021 at 01:09:47 UTC, Hipreme wrote: I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` If symName is always a string literal, then you don't need to append a "\0"; string literals always have a trailing NUL after them, and they autoconvert to const(char)[] so you don't need the .ptr either.
0 cost template instantiation
I have a template function that all it does is given a symbol, it loads a dll for its type + its name: ``` void loadSymbol(alias s, string symName = "")() { static if(symName == "") s = cast(typeof(s))_loadSymbol(_dll, (s.stringof~"\0").ptr); else s = cast(typeof(s))_loadSymbol(_dll, (symName~"\0").ptr); } ``` The main problem is that this function is costing 2KB per instantiation, which is something pretty high. Specially if I inline, there is almost no cost when compared to its inline version. Trying to use pragma(inline, true) didn't do anything too. If I understood correctly, mixin template would be some way to actually inline anything. The problem is that I can't have any kind of expression inside it, so, that's the only way I could think in how to do it. Optimization seems to don't take care of that behaviour too. I would like to know which approach could I take for making something like C's #define for that. As this function could be really rewritten as a macro if I were coding in C, the cost is too high for a function that would be only a syntactic sugar
Re: Loading assimp
On Wednesday, 29 September 2021 at 02:47:09 UTC, Mike Parker wrote: On Tuesday, 28 September 2021 at 16:30:09 UTC, Eric_DD wrote: I am trying to use a newer version of Assimp. I have found a assimp-vc140-mt.dll (v3.3.1) which I renamed to assimp.dll When running my executable it throws a derelict.util.exception.SharedLibLoadException: "Failed to load one or more shared libraries: assimp.dll - %1 is not a valid Win32 application. Assimp64.dll - The specified module could not be found" Any idea what's going on? Are 64bit dlls not supported? I'm not maintaining the package anymore, but this is an error from the system loader and has nothing to do with the binding itself. It's the sort of error that usually pops up when trying to load a 32-bit DLL into a 64-bit program, or vice versa. Are you sure it's a 64-bit DLL? why my messages are not sent?
Re: Why sometimes stacktraces are printed and sometimes not?
On 9/29/21 6:57 AM, JN wrote: What makes the difference on whether a crash stacktrace gets printed or not? Sometimes I get a nice clean stacktrace with line numbers, sometimes all I get is "segmentation fault error -1265436346" (pseudo example) and I need to run under debugger to get the crash location. segmentation faults are memory access errors. It means you are accessing a memory address that is not valid for your application. If you are accessing the wrong memory, it means something is terribly wrong in your program. Note that on Windows in 32-bit mode, I believe you get a stack trace. On Linux, there is the undocumented `etc.linux.memoryhandler` which allows you to register an error-throwing signal handler. Signals are not really easy to deal with in terms of properly throwing an exception. This only works on Linux, so I don't know if it's possible to port to other OSes. I've also found sometimes that it doesn't work right, so I only enable it when I am debugging. -Steve
Re: Why sometimes stacktraces are printed and sometimes not?
On 9/29/21 8:15 AM, Steven Schveighoffer wrote: On Linux, there is the undocumented `etc.linux.memoryhandler` Sorry, it's `etc.linux.memoryerror` Here is the code: https://github.com/dlang/druntime/blob/master/src/etc/linux/memoryerror.d -Steve
Re: Loading assimp
On Tuesday, 28 September 2021 at 20:09:41 UTC, Eric_DD wrote: On Tuesday, 28 September 2021 at 19:59:09 UTC, russhy wrote: On Tuesday, 28 September 2021 at 16:30:09 UTC, Eric_DD wrote: I am trying to use a newer version of Assimp. I have found a assimp-vc140-mt.dll (v3.3.1) which I renamed to assimp.dll When running my executable it throws a derelict.util.exception.SharedLibLoadException: "Failed to load one or more shared libraries: assimp.dll - %1 is not a valid Win32 application. Assimp64.dll - The specified module could not be found" Any idea what's going on? Are 64bit dlls not supported? try to rename it to Assimp64.dll Nah :) Already tried that. It just swaps the file names in the error message. Derelict is kinda old anyways, to make sure we use up to date stuff, try to migrate to bindbc one https://github.com/Sobaya007/bindbc-assimp https://code.dlang.org/packages/bindbc-assimp If i were you i'd compile the project myself, so you know what your DLL is https://github.com/assimp/assimp https://github.com/assimp/assimp/blob/master/Build.md
Re: Loading assimp
On Tuesday, 28 September 2021 at 16:30:09 UTC, Eric_DD wrote: I am trying to use a newer version of Assimp. I have found a assimp-vc140-mt.dll (v3.3.1) which I renamed to assimp.dll When running my executable it throws a derelict.util.exception.SharedLibLoadException: "Failed to load one or more shared libraries: assimp.dll - %1 is not a valid Win32 application. Assimp64.dll - The specified module could not be found" Any idea what's going on? Are 64bit dlls not supported? If using dub you can build your D programs with dub -a x86 for a 32-bit executable dub -a x86_64 for a 64-bit executable (which is also the default thankfully). Your problem is very probably trying to load a 32-bit DLL into a 64 host program.
Why sometimes stacktraces are printed and sometimes not?
What makes the difference on whether a crash stacktrace gets printed or not? Sometimes I get a nice clean stacktrace with line numbers, sometimes all I get is "segmentation fault error -1265436346" (pseudo example) and I need to run under debugger to get the crash location.
Re: Using D "rocket" logo in outside presentation
On Wednesday, 29 September 2021 at 04:24:13 UTC, Chris Piker wrote: Hi D I'm to give a presentation to a combined NASA/ESA group in a few hours and would like to include a copy of the D "rocket" logo when mentioning new server side tools that I've written in D. Is such use of this particular [D logo](https://i0.wp.com/dlang.org/blog/wp-content/uploads/2021/08/logo_256.png?w=750=1) permissible? Thanks, it's [Attribution-ShareAlike 4.0 International (CC BY-SA 4.0)](https://creativecommons.org/licenses/by-sa/4.0/) so it's freely usable (give appropriate credit, dunno if saying it's the D logo is enough credit giving, but don't think I have seen that artwork been used with any other credit in context of dlang before) see https://github.com/dlang-community/artwork