World: r3wp
[!REBOL3 Extensions] REBOL 3 Extensions discussions
older | first |
Robert 14-Mar-2011 [2478] | No, but the same callback code works from an other place where it's the same thread as R3. |
Andreas 14-Mar-2011 [2479x4] | well, then that's looks pretty much like the problem |
the immediate solution is to have a piece of code, running in the same thread as the R3 host, which is used to initiate all callbacks | |
everwhere else, instead of initiating callbacks directly, you hand over control to this thread running this piece of code initiating the callback for you. that'll require basic inter-thread communication, is kaj already mentioned above | |
the real solution is to have R3 do this kind of thread synchronisation internally | |
Robert 14-Mar-2011 [2483x4] | Well, to get this code started I need to call it from R3, but than I can't return to R3 otherwise I get a new thread dealing with it. So this is not possible. |
The other option is to poll from R3 in regular intervalls. But as we miss timers at the moment, this won't work too. | |
But I could trigger a poll via callback sending an integer! :-) It's two rounds than but that would work. | |
Because the interger callback works. | |
Andreas 14-Mar-2011 [2487] | i assume you currently have roughly the following flow: - R3 calls into extension (via RX_Call) - extension calls into library, passing an extension-internal "activity" handler along - the library calls the extension's activity handler - the extension activity handler initiates a callback into R3 |
Robert 14-Mar-2011 [2488x2] | - R3 call init-lib - init-lib installs a listener, setups a C-level callback handler (CBH) and returns - the listener is sometimes triggered, calls the CBH (new thread) - CBH prepares Rebol callback, calls Rebol callback (and here it crashes with string!, not with integer!), continues and ends |
Ok, the callback / pull combo works :-) Not nice, but workaround. | |
Andreas 14-Mar-2011 [2490] | good to know :) |
Robert 14-Mar-2011 [2491] | To complete the sequence from above: - Rebol exectues the rebol side callback function, which make a synchronous call to the lib, getting all buffered messages and continues to process them |
Robert 25-Mar-2011 [2492x8] | I have a very strange effect: The init_block gets a c filename attached. The .r file that is used to generate the .h header file of course doesn't inlcude it. And the generated init_block numbers don't include it too. |
So, this happens at compile / run-time. | |
When entering RX_Init the init_block string allready has the c filename appended. | |
How can this be? I mean it's a const-char array. | |
Ok, so I found out that the last number wasn't 0. When generating the header file I get this as last line: 116, 105, 97, 108, 105, 122, 101, 100, 34, 10, }; This is the line makeing problems. When I change it to: 116, 105, 97, 108, 105, 122, 101, 100, 34, 10, 0 }; it works. | |
Seems the R3 script I use has a bug, there is a strange line: to-cstr: either system/version/4 = 3 [ ; Windows format: func [str /local out] [ out: make string! 4 * (length? str) out: insert out tab forall str [ out: insert out reduce [to-integer first str ", "] if zero? ((index? str) // 10) [out: insert out "^/^-"] ] ;remove/part out either (pick out -1) = #" " [-2][-4] head out ] ][ | |
The one commented. Than it works. | |
Is there an offical place to get the latest verison of this header converter script? | |
Kaj 25-Mar-2011 [2500] | The host kit is the only place I know of |
Oldes 25-Mar-2011 [2501] | Can someone explain me, why is Carl using such an 'encryption' and why not just to use it as const char like I do here: https://github.com/Oldes/R3-extension-FMOD/blob/master/main.c#L417 Is it because he wants to be compatible with some old compilers? |
Andreas 25-Mar-2011 [2502] | Oldes, yes, it's about compiler compatibility. |
Oldes 25-Mar-2011 [2503x2] | And compilers are affected? |
btw it's really strange.. I would thought that that's a basic thing. To be able easily define a string. | |
Andreas 25-Mar-2011 [2505x11] | Some compilers might be. |
Usually, MSVC is the problem, in such cases. | |
C90 requires compilers to support _single_ string literals (i.e. one quote "...") of at least 509 characters. | |
(C90 ~= C89 ~= "ANSI C") | |
C99 raides that minimum to 4095 characters. | |
And MSVC doesn't support C99. | |
Then there's also a limit how big concatenated strings can get (i.e. "..." "..." "..."). Which is 65k in MSVC, IIRC. | |
So, if you don't do extremely long lines and a 65k+ init string, you should be fine with string literals even in MSVC. | |
Which is why I don't care either :) String literals ftw! | |
Btw, here's my variation of a header generator script: https://github.com/earl/r3-zmq/blob/master/make-ext-header.r3 It has the nice advantage that it automatically generates a dispatch table for your commands, enabling a clean and concise RX_Call like: https://github.com/earl/r3-zmq/blob/master/zmqext.c#L31-35 | |
For example, take the zmqext extension specification: https://github.com/earl/r3-zmq/blob/master/zmqext.r3 This is the header file generated by above generator script: https://gist.github.com/e22a35049ae56324004a | |
shadwolf 6-Apr-2011 [2516] | rebol.org the script library is so well done that everyone use github :P. |
BrianH 28-Sep-2011 [2517] | I vaguely recall that someone was working on ODBC support for R3. Did that ever become usable? Is there a link to this work? |
Pekr 28-Sep-2011 [2518] | http://www.diefettenjahresindvorbei.de/odbc/odbc-docs.html |
BrianH 28-Sep-2011 [2519] | Thanks! I've been using R2/Command to do the database access and R3 to process the data. All in the same script, using a trick I'll post to the Windows group. |
BrianH 1-Oct-2011 [2520] | There's a couple bugs in the REBOL portion of the ODBC extension mentioned above. I'll try to make a patching wrapper module. |
BrianH 3-Oct-2011 [2521x5] | This module loader for the odbc.dll extension handles the bug in its open handler that prevented it from using block specs with a target: REBOL [ title: "ODBC Extension Patch" type: module options: [private] needs: [%odbc.dll] ] odbc: import 'odbc system/schemes/odbc/actor/open: func [port [port!] /local result] bind [ port/state: context [access: 'write commit: 'auto] result: open-connection port/locals: make database-prototype [] case [ string? select port/spec 'host [ajoin ["dsn=" port/spec/host]] string? select port/spec 'target [port/spec/target] 'else [cause-error 'access 'invalid-spec port/spec] ] all [block? result lit-word? first result apply :cause-error result] port ] odbc |
Unfortunately, there's an error in its fallback behavior that makes it a bit difficult to use. In its docs, section 3.7: If there is no applicable REBOL datatype to contain a SQL value, the value will be returned as a string. The binary data is returned in a value of the string! type, rather than of the binary! type, which results in a corrupted string that you can't do anything with. If the value was returned as a binary then we could perform the conversions ourselves. I ran into this problem when returning SQL values of the tinyint and text types. | |
I love the method for triggering errors from the native core though :) | |
core -> code | |
It just occured to me that the import statement above could have potentially unwanted side effects on the user context. Replace this: odbc: import 'odbc with this: odbc: import/no-user/no-lib 'odbc | |
Robert 4-Oct-2011 [2526] | I love the method for triggering errors from the native code though :) - Brian, can you elaborate on this? I'm interested in what you there? |
BrianH 4-Oct-2011 [2527:last] | The method is pretty simple. Normally the functions return data in a particular format. Upon an error though they just return a block with 3 elements, the first two of which are lit-words, the last could be anything; this is passed directly to apply :cause-error. The error block can be recognized and handled easily with this code in the REBOL functions that wrap the natives: all [block? result lit-word? first result apply :cause-error result] It's similar to the way error handling is done in the low-level sys load functions, particularly sys/load-header. Upon an error, instead of a block the function returns a word! value, which can be passed to cause-error by the calling function, using code like this: set [hdr: code:] load-header/required data if word? hdr [cause-error 'syntax hdr source] Word values are easier to handle safely than error values. Note that the argument provided to cause-error in this case is different from that provided to load-header: This lets you trigger errors with information that load-header isn't provided, giving your errors more context that is useful to the programmer. Not exactly the same thing as the ODBC driver, but close. |
older | first |