Re: How to setup DLL and EXE projects in one VS solution
On 17.05.2017 18:56, Igor wrote: At the moment I have: EXEProject: app.d - it does loadlibrary of dllproj and uses data structures defined in dllproj.d (it imports dllproj). On the file system this file is under /platform/win32/ and is defined as module win32.app; DLLProject dllproj.d - exports functions and contains data structures those function use. On file system this file is under /source and is defined as module dllproj; EXEProject depends on DLLProject. DLL project compiles and builds DLL fine but, of course EXE project breaks with an error: module dllproj is in file dllproj.d which cannot be read. I could just copy all the structs from dllproj.d to app.d and remove the import and I guess it would all work but there has to be a better way to structure code so structs are only written in one place? You have to add an import path to the folder with dllproj inside to the project configuration of the exeproject. If you want to limit the imported code to the declarations, you can enable "generate interface headers" and add an import path to these instead. Sharing data or resources between executable and DLL is currently limited to separate ownership as each binary contains its own copy of the runtime. (There is currently work being done to have a shared runtime, though). You might also run into other cross module dependencies...
Re: How to setup DLL and EXE projects in one VS solution
On Wednesday, 17 May 2017 at 19:48:42 UTC, Igor wrote: On Wednesday, 17 May 2017 at 18:03:04 UTC, Igor wrote: What exactly do mean by "binding"? Also I am wondering if using extern(C) as opposed to extern(D) only affects name mangling or am I losing some DLang possibilities since I am only calling DLang DLL from DLang EXE? Look at these materials, there can be they will are useful. https://vk.com/vk_dlang?z=photo-471951_456239025%2Fwall-471951_2095 https://www.youtube.com/watch?time_continue=2&v=HTgJaRRfLPk
Re: How to setup DLL and EXE projects in one VS solution
On Thursday, 18 May 2017 at 07:10:54 UTC, Rainer Schuetze wrote: You have to add an import path to the folder with dllproj inside to the project configuration of the exeproject. If you want to limit the imported code to the declarations, you can enable "generate interface headers" and add an import path to these instead. Sharing data or resources between executable and DLL is currently limited to separate ownership as each binary contains its own copy of the runtime. (There is currently work being done to have a shared runtime, though). You might also run into other cross module dependencies... I tried just adding import paths to project and to di files and although compilation passes I still get link errors like: error LNK2019: unresolved external symbol _D10handmade_h10game_input6__initZ (handmade_h.game_input.__init) referenced in function _D8platform5win324main9myWinMainFPvPvPaiZi (int platform.win32.main.myWinMain(void*, void*, char*, int)) where game_input is a struct in interface file. I also tried adding the di file to the exeproject but it still doesn't work. It seems VisualD doesn't add di files to compiler invocation arguments like it does with *.d and *.def files.
Re: How to setup DLL and EXE projects in one VS solution
On Thursday, 18 May 2017 at 07:53:02 UTC, Igor wrote: I tried just adding import paths to project and to di files and although compilation passes I still get link errors like: error LNK2019: unresolved external symbol _D10handmade_h10game_input6__initZ (handmade_h.game_input.__init) referenced in function _D8platform5win324main9myWinMainFPvPvPaiZi (int platform.win32.main.myWinMain(void*, void*, char*, int)) where game_input is a struct in interface file. I also tried adding the di file to the exeproject but it still doesn't work. It seems VisualD doesn't add di files to compiler invocation arguments like it does with *.d and *.def files. .di files don't need to be passed to the compiler. They are neither compiled nor linked. The whole point of them is that they only provide the declarations, not the implementations. You still need to link to a compiled implementation, either in the form of an object or library file. I've never used Visual D (or DMD for that matter) to create a DLL, but I assume an import library should have been produced along with the DLL. Are you linking to it in your executable project?
alias this and struct initializer
Hi, I have some issues with struct initializer and alias this. In following example 1 and 2 is working but there is a syntax error for 3. I think as case 2 is working case 3 should work also. For me case 3 is looking much nicer than case 1. What do you think? void main() { // Working Request request1 = { definitions: {[ Definition("A", "B") ]} }; // Working Request request2; request2.definitions = [Definition()]; // cannot implicitly convert expression ([Definition("A", "B")]) of type Definition[] to Definitions Request request3 = { definitions: [ Definition("A", "B") ] }; } struct Request { Definitions definitions; } struct Definitions { private Definition[] _arr; alias values this; @property Definition[] values(){return _arr;} @property void values(Definition[] values){_arr = values;} } struct Definition { string attributeName; string attributeType; } Kind regards André
Re: How to move append to an array?
On Monday, 15 May 2017 at 21:38:52 UTC, Yuxuan Shui wrote: Suppose I have a struct A { @disable this(this); } x; How do I append it into an array? Do I have to do array.length++; moveEmplace(x, array[$-1]); ? Judging form the way you write the struct. It is of C/C++ style. With that said, it's not clear what you are trying to do. There is a basic reference about array here: http://dlang.org/spec/arrays.html And this works: cat arrayappend.d // arrayappend.d content unittest { auto a = [1, 2]; a ~= 3; assert( a == [1, 2, 3]); } // Finish content Running test: rdmd -unittest -main arrayappend.d No error message means the test passes.
Fails to use testFilename in unittest
There is a ongoing discussion about temp file over here: http://forum.dlang.org/thread/sbehcxusxxibmpkae...@forum.dlang.org I have a question about generating a temporary file to write test data. I can create my own file and use it but just want to use the existing tool for convenience. testFilename() is used all over phobos. So, I don't understand why it does not work on my code. The following code fails to compile. % cat testFile.d #!/usr/bin/env rdmd import std.stdio; unittest{ static import std.file; auto deleteme = testFilename(); scope(failure) printf("Failed test at line %d\n", __LINE__); scope(exit) std.file.remove(deleteme); // Do some stuffs with open or writing and reading of the temp file. assert(true); } void main(string [] args){ writeln("Main"); }
Re: Fails to use testFilename in unittest
This is the compile error message by the way: dmd -unittest ./testFile.d !6009 testFile.o: In function `_D8testFile14__unittestL4_1FZv': ./testFile.d:(.text._D8testFile14__unittestL4_1FZv+0x1a): undefined reference to `_D3std5stdio12testFilenameFNfAyamZAya' collect2: error: ld returned 1 exit status Error: linker exited with status 1
Re: Fails to use testFilename in unittest
On Thursday, May 18, 2017 09:40:33 biocyberman via Digitalmars-d-learn wrote: > There is a ongoing discussion about temp file over here: > http://forum.dlang.org/thread/sbehcxusxxibmpkae...@forum.dlang.org > > I have a question about generating a temporary file to write test > data. I can create my own file and use it but just want to use > the existing tool for convenience. testFilename() is used all > over phobos. So, I don't understand why it does not work on my > code. > > The following code fails to compile. > > >% cat testFile.d > #!/usr/bin/env rdmd > import std.stdio; > > unittest{ > >static import std.file; >auto deleteme = testFilename(); >scope(failure) printf("Failed test at line %d\n", __LINE__); > >scope(exit) std.file.remove(deleteme); > >// Do some stuffs with open or writing and reading of the temp > file. > assert(true); > > > > } > void main(string [] args){ >writeln("Main"); > > } Actually, it's not used all over the place in Phobos. It's only used std.stdio, where it's a private function in a version(unittest) block. It's not part of the public API. And other modules that need something similar have their own solution. std.stdio has version(unittest) string testFilename(string file = __FILE__, size_t line = __LINE__) @safe { import std.conv : text; import std.file : deleteme; import std.path : baseName; // filename intentionally contains non-ASCII (Russian) characters for test Issue 7648 return text(deleteme, "-детка.", baseName(file), ".", line); } and std.file has @property string deleteme() @safe { import std.conv : to; import std.path : buildPath; import std.process : thisProcessID; static _deleteme = "deleteme.dmd.unittest.pid"; static _first = true; if (_first) { _deleteme = buildPath(tempDir(), _deleteme) ~ to!string(thisProcessID); _first = false; } return _deleteme; } If you want to use anything like them, you'll need to declare them in your own code. - Jonathan M Davis
Re: Fails to use testFilename in unittest
On Thursday, 18 May 2017 at 09:49:26 UTC, Jonathan M Davis wrote: On Thursday, May 18, 2017 09:40:33 biocyberman via Digitalmars-d-learn wrote: [...] Actually, it's not used all over the place in Phobos. It's only used std.stdio, where it's a private function in a version(unittest) block. It's not part of the public API. And other modules that need something similar have their own solution. [...] That's exactly the code I looked at. And yes, I checked std.stdio to see many occurrences of testFilename.
Re: Fails to use testFilename in unittest
On Thursday, May 18, 2017 09:56:36 biocyberman via Digitalmars-d-learn wrote: > On Thursday, 18 May 2017 at 09:49:26 UTC, Jonathan M Davis wrote: > > On Thursday, May 18, 2017 09:40:33 biocyberman via > > > > Digitalmars-d-learn wrote: > >> [...] > > > > Actually, it's not used all over the place in Phobos. It's only > > used std.stdio, where it's a private function in a > > version(unittest) block. It's not part of the public API. And > > other modules that need something similar have their own > > solution. > > > > [...] > > That's exactly the code I looked at. And yes, I checked > std.stdio to see many occurrences of testFilename. My point is that it's a private function for testing std.stdio and not intended to be part of the public API or be used by anyone else (it's not even used anywhere else in Phobos). None of the functions in Phobos that do that sort of thing are in the public API. You can copy-paste testFilename (and std.file.deleteme, since it uses that) into your own code and use them if you like, but the ones in Phobos are just there for Phobos. The only unit testing-specific functionality that Phobos provides beyond what the language itself has is in std.exception with functions such as assertThrown. - Jonathan M Davis
Re: Cheetah: Keeping track of multiple connected clients
On Tuesday, 16 May 2017 at 21:56:16 UTC, aberba wrote: On Tuesday, 16 May 2017 at 17:49:07 UTC, bauss wrote: [...] It really awesome the way you responded quickly. About targeting a client, suppose I have clients A, B, and C. Message can be broadcast to all using above solution. But in case A want to sent message to B and not C, how does server detect the specific destination client's id? Does client.send(...) allow json string with target id from browser client? I'm trying to find a way to receive meesage in one language along with target client's id and send to the target after I have translated to another lang. To reframe my question, When client A sends a message meant for client B, is there a facility in cheetah to identify source and destination clients? (looked through the code, did not find any obvious info on properties of a client or a message event)
Re: alias this and struct initializer
On Thursday, 18 May 2017 at 08:40:39 UTC, Andre Pany wrote: I think as case 2 is working case 3 should work also. Nope, case 2 is assigning to an already constructed object and case 3 is constructing a new one. alias this is NEVER used in construction. It can only apply after the object already exists, just like subclasses vs interfaces. Once the object exists, you can assign a subclass to an interface, but you can't do SubClass obj = new Interface(); in theory, the compiler could see the left hand side and know it is supposed to be SubClass, but it doesn't - you need to construct the class explicitly. Same with alias this, it allows implicit conversion TO the type and assignment of the member through the existing variable (the existing variable must already be valid, it is already constructed, so it is no different than assigning any other public member), but not implicit conversion FROM the type since the new struct may have other members that need to be initialized too.
Re: Fails to use testFilename in unittest
On Thursday, 18 May 2017 at 10:05:41 UTC, Jonathan M Davis wrote: On Thursday, May 18, 2017 09:56:36 biocyberman via Digitalmars-d-learn wrote: [...] My point is that it's a private function for testing std.stdio and not intended to be part of the public API or be used by anyone else (it's not even used anywhere else in Phobos). None of the functions in Phobos that do that sort of thing are in the public API. You can copy-paste testFilename (and std.file.deleteme, since it uses that) into your own code and use them if you like, but the ones in Phobos are just there for Phobos. The only unit testing-specific functionality that Phobos provides beyond what the language itself has is in std.exception with functions such as assertThrown. - Jonathan M Davis Understood. I copied the code. Thanks
Re: Cheetah: Keeping track of multiple connected clients
On Thursday, 18 May 2017 at 11:44:57 UTC, aberba wrote: On Tuesday, 16 May 2017 at 21:56:16 UTC, aberba wrote: On Tuesday, 16 May 2017 at 17:49:07 UTC, bauss wrote: [...] It really awesome the way you responded quickly. About targeting a client, suppose I have clients A, B, and C. Message can be broadcast to all using above solution. But in case A want to sent message to B and not C, how does server detect the specific destination client's id? Does client.send(...) allow json string with target id from browser client? I'm trying to find a way to receive meesage in one language along with target client's id and send to the target after I have translated to another lang. To reframe my question, When client A sends a message meant for client B, is there a facility in cheetah to identify source and destination clients? (looked through the code, did not find any obvious info on properties of a client or a message event) Well it isn't based directly around Websockets, so for those to work you'd have to implement the websocket protocol or you could attempt to fork cheetah and wrap vibe.d's websocket implementation into it; if you don't have time or don't really know how to exactly, then I'd see if I can make time for it. However as for identifying the source, it really depends on how your packet protocol. Cheetah isn't meant to be a one-type only socket library and it's up to the user themselves to implement their packet protocol because it can vary from implementation to implementation. Some might sent raw json, some might sent xml, some might sent raw binary, some might sent http packets, you get me? I might come up with a generic version to attempt to fit them all, but it's quite a bit of work to do so, which is why right now it's up to the individual user to implement their packet protocol. I'd assume since you're using Websockets your protocol is probably json. After the whole handshake for websockets are done then it should be fairly simple to implement the message receiving. If you want to know how the exact implementation should be, then you can read here. https://tools.ietf.org/html/rfc6455 I assume you'll be able to find what you're looking for there. Reading it raw would be something like continuously receiving a static amount of byte like 1024 and then keep doing that until all chunks make up a proper json object, then you take the remaining bytes (Because they might hold next packet) and keep doing the same thing for the next object, then simply repeating. Then you can simply have a property in the object that has a client id (Which should correspond to the id the server has given the client.) As for how the client itself should know the id. You can simply send a packet to the client when it connects which contains the client id. If you want the above simplified, let me know.
Re: How to setup DLL and EXE projects in one VS solution
On 18.05.2017 09:53, Igor wrote: On Thursday, 18 May 2017 at 07:10:54 UTC, Rainer Schuetze wrote: You have to add an import path to the folder with dllproj inside to the project configuration of the exeproject. If you want to limit the imported code to the declarations, you can enable "generate interface headers" and add an import path to these instead. Sharing data or resources between executable and DLL is currently limited to separate ownership as each binary contains its own copy of the runtime. (There is currently work being done to have a shared runtime, though). You might also run into other cross module dependencies... I tried just adding import paths to project and to di files and although compilation passes I still get link errors like: error LNK2019: unresolved external symbol _D10handmade_h10game_input6__initZ (handmade_h.game_input.__init) referenced in function _D8platform5win324main9myWinMainFPvPvPaiZi (int platform.win32.main.myWinMain(void*, void*, char*, int)) That's what I meant with "other cross module dependencies". In this case it might work if you export _D10handmade_h10game_input6__initZ from your DLL with the help of a def-file, but that's not something that scales well. This talk will give you some details on the complications involved: https://www.youtube.com/watch?v=MQRHxI2SrYM
Re: alias this and struct initializer
On Thursday, 18 May 2017 at 12:56:09 UTC, Adam D. Ruppe wrote: On Thursday, 18 May 2017 at 08:40:39 UTC, Andre Pany wrote: [...] Nope, case 2 is assigning to an already constructed object and case 3 is constructing a new one. [...] Thanks for the explanation, that makes perfectly sense. Kind regards André
Re: How to setup DLL and EXE projects in one VS solution
On Thursday, 18 May 2017 at 18:00:02 UTC, Rainer Schuetze wrote: That's what I meant with "other cross module dependencies". In this case it might work if you export _D10handmade_h10game_input6__initZ from your DLL with the help of a def-file, but that's not something that scales well. This talk will give you some details on the complications involved: https://www.youtube.com/watch?v=MQRHxI2SrYM Thanks for the link Rainer. I actually watched that a few days ago but it didn't help me understand what I just figured out. It slipped my mind that structs in D are not just structs like the ones in C. In D they have default initializer which is actually a function and as you said I am not exporting that function and it doesn't scale well to hunt all hidden functions that you need to export for all common datatypes. Even if I did, since I am loading DLL and its functions dynamically using GetProcAddress, how could I even tell D to use loaded function pointer as initialization function for a type... Anyway I will stick with the solution of using a separate file where all common datatypes are defined in both projects and see how far I get with it.
How to check a struct exists at a particular memory address?
This might be a really silly question but: I've allocated some memory like this (Foo is a struct): this._data = cast(Foo*) calloc(n, Foo.sizeof); How can I then later check that there is a valid Foo at `this._data` or `this._data + n`?
Re: How to check a struct exists at a particular memory address?
On Thursday, 18 May 2017 at 20:20:47 UTC, Gary Willoughby wrote: This might be a really silly question but: I've allocated some memory like this (Foo is a struct): this._data = cast(Foo*) calloc(n, Foo.sizeof); How can I then later check that there is a valid Foo at `this._data` or `this._data + n`? Well... I think the right answer is that everything you do with memory should be very deterministic so you should just know where is what and not have a need to check :). The only thing that crosses my mind if you really need to check is to make sure you always write some specific big number just before each struct in memory as a flag that what follows is Foo and then you can check if that is set properly. I think you could do this by wrapping Foo in another struct whose first field is immutable long set to some specific value (that isn't zero) :) and then using that struct in place of Foo. Although I am not sure if compiler would optimize away checks if an immutable is equal to its init value...
Re: How to check a struct exists at a particular memory address?
On Thursday, 18 May 2017 at 21:09:06 UTC, Igor wrote: On Thursday, 18 May 2017 at 20:20:47 UTC, Gary Willoughby wrote: This might be a really silly question but: I've allocated some memory like this (Foo is a struct): this._data = cast(Foo*) calloc(n, Foo.sizeof); How can I then later check that there is a valid Foo at `this._data` or `this._data + n`? Well... I think the right answer is that everything you do with memory should be very deterministic so you should just know where is what and not have a need to check :). Agreed. I think I'll re-visit the design.
Re: How to check a struct exists at a particular memory address?
On Thursday, 18 May 2017 at 20:20:47 UTC, Gary Willoughby wrote: This might be a really silly question but: I've allocated some memory like this (Foo is a struct): this._data = cast(Foo*) calloc(n, Foo.sizeof); How can I then later check that there is a valid Foo at `this._data` or `this._data + n`? The normal way to do this is to have an int (or whatever, larger size means less likely to fall fowl on random data) that is initialised to a known "random" value. See the ELF magic headers for example.