Redbol Emulation Runs %pdf-maker.r...and now on the web!

The Rebol2-ish-or-Red emulation layer "Redbol" now runs on the web REPL! There's a lot of caveats at this early stage, but it's still pretty interesting.

It was first developed to build the static site, using the aging codebase from my early attempts at dialecting. (The code is now being deliberately held back, so I have an incentive to make the Redbol layer work.)

Now it's run on its second not-insignificant-codebase, Gabriele's %pdf-maker.r... (the older, single-file version on the rebol script archive). With only minor modifications, it successfully made a PDF from the dialect input:

layout-pdf [[textbox ["This is some text."]]]

(With that working, I'm now looking at questions of how to run it with zero modifications.)

Despite the small size of the input, it does exercise a lot of the code paths from start to finish to make a PDF file. I don't know that the rest of it (except possibly IMAGE! support) would exercise all that much more of the system.

Some points to raise:

  • The emulation is relatively slow. The focus is on understanding what the compatibility issues are, and not on optimization. Though I've mentioned that with Redbol as an extension, it would be able to do some of its work through natives.

  • Redbol still takes over the whole user context. It leaves all the lib definitions alone, but then skins the user context with its emulation. But this means any other code you run in the user context will get the Rebol2 rules. So it doesn't work with modules or running normal Ren-C code side-by-side. What we'd rather do is have you put your code in a module and say "this uses Redbol" and let just that module get the definitions...which is the kind of thing the module system should be able to do, but it was missing a lot of these design points. So this is a definite next step.

  • We have to decide about Latin1 Redbol support. Just because the default for LOAD/SAVE was Latin1 before, is that really what we want Redbol to do? This PDF case is an odd one because it actually is using the Latin1 encoding for an embedded table with font metrics information. Rather than modify Redbol's LOAD to take in and spit out Latin1, I just converted the table to UTF-8 and re-encoded it. Is this the better idea than bending over backwards on this compatibility point? Would people probably prefer a UTF-8 Everywhere Redbol?

  • R3-Alpha bitsets were incomplete and buggy. There was awareness of the issues involved in the representation that was chosen. Even so, the code to handle it was not written. I don't know exactly where on the schedule something like that is supposed to go--it would be nice if someone who was not me could write a coherent solution and do all the tests for it. It's a fairly standalone task. Anyway, the PDF maker uses them--I hacked around the case that was using the negated bitsets.

  • FORM is pretty different. Decimal numbers print to a different number of digits in Rebol2 vs. R3-Alpha and Red--which is frustrating in the PDF output because hex differs get thrown off and think there's more difference than there really is. ISSUE! formed without its # instead of with it. I have not been pleased that form [1 2 [3 4]] is "1 2 3 4" while append "" [1 2 [3 4]] is "123 4"...there's just a lot of random-seeming behavior, where it needs to be straightened out. But in an ad-hoc and as-needed manner, I'm adding the differences in behavior to Redbol. This makes good documentation of the behavior, if nothing else.

  • Things that depend on inheritance have to use METHOD. It used to be that if you had any function that happened to be referenced from an object, deriving from that object would cause it to rebind. It also deep copied every function in the process! Design-wise, Ren-C's METHOD uses the strategy of looking to its left to see what set-word! you are assigning it to, and then binds the generated function to the context of that set-word!. Right now this means such instances have to be changed to METHOD.

On this latter point, I'm getting to wonder if we do need to make enfixedness a property of ACTION!s instead of words. That way FUNC and DOES could be enfix and having some smarts about their left hand side being a skippable SET-WORD!...without people using them needing to know they are enfix. With these tricks it seems that it's coming to be so entwined in a function's meaning that for many of them, you can't really divorce their enfixedness from the definition.

Back when trying to avoid a separate OP! datatype, I was wary of the bit living in the function at all.
As a sample concern: I was thinking about a world where all functions were potentially enfix, but maybe would ignore their left argument. Yet if everything were enfix there would be no EVALUATE (e.g. "DO/NEXT")...because these fake enfix functions would be forcing the entire operation to completion. But there's been mountains of change since these questions were looked at...we have <skip>-able arguments and a lot more understanding.

But anyway, long story short is: Redbol has had its second demo codebase going and is on the web!


This is Gabriele's test document which generates the pdf-maker.r documentation

The more things we can do with the redbol dialect the more likely we are to displace r2 amongst die hard users. And even migrate them to ren-c!


In letting go of a laptop, I had some files that weren't formally github projects yet.

The tinkering to make pdf-maker go was one of those things. Here was the file I had for testing:

    Description: {
        For more examples:

        Larger test:

either system/version = [
    pdf-file: %simple-r2.pdf
    --: :??  ; Ren-C uses `--` as a more ergonomic form of Rebol2 `??`
    do %../ren-c/scripts/redbol.reb  ; Emulation for Rebol2
    pdf-file: %simple.pdf

do %pdf-maker.r

write/binary pdf-file layout-pdf [[textbox ["This is some text."]]]
call "vbindiff simple-r2.pdf simple.pdf"

The only change I made to pdf-maker itself was:

metrics: load decompress either system/version != [
     read %metrics.compressed.dat
] [64#{...

To instead say just:

metrics: load decompress 64#{...

But it ran and generated an identical file in Rebol2 to Ren-C with Redbol.

I want to add this to GitHub actions as a test at some point, at least just this simple example. People can delve deeper into it if they care.