Close

Through the Maze, Down the Rabbit Hole, Into the Labyrinth

A project log for Prometheus A.I.

One set of rings that will control all.

glgormanglgorman 07/18/2022 at 19:240 Comments

It goes something like this.  

 PASCALCOMPILER::THREAD_ENTRY gets called.  That calls  PASCALCOMPILER::COMPILER_MAIN, which leads to PASCALCOMPILER::BLOCK, which in turn brings us into PASCALCOMPILER::BODY which gets us into BODYPART::MAIN via the "rabbit hole" of doing a reinterpret_cast on the compiler object which in turn was Frankenstiened together via a custom allocator, rather than with the regular constructor object, which shouldn't be possible if the inheritance is based on a set of virtual base classes, but it does seem to be working, for now.  Then we cross the Rubicon into the Labyrinth that consists of mutually recursive calls back into DECLARATIONPART::MAIN, then back up to PASCALCOMPILER::BLOCK (!),, followed by a trip into PASCALCOMPILER::DECLARATIONS, which somehow finds DECLARATIONPART::MAIN again, where it finally falls to the center of the earth looking for a symbol that it doesn't find, via a SKIP loop - finally emitting ERROR 18 "Error in Declaration Part".

O.K., so now we have proof of concept: Pascal-style mutually recursive nested functions in C/C++, even though "local procedures are illegal" in C.

Time to say oh, la, la! and order a deluxe pizza?   Maybe.  Even though it is still quite a bit far off before I will be generating a binary that will run on the Propeller, Arduino, or a TTL-NOR computer. for that matter.  Yet there is something interesting that comes to mind.   Most of the code conversion was done in a word processor, using find and replace and then manually editing the prototypes, as previously discussed.  So I know there are other plenty of places where some block might not have gotten an extra left or right curly brace to properly match up and properly format some DO WITH this WHILE that mess, that might also have nested cases, etc.  So I simply added or deleted braces by eye, often without looking at the original source, just to get it to compile!  I mean, so whet?  Just give it the brains of Abby Normal, right?  Maybe Eliza could do a better job.

Maybe Eliza COULD do a better job!  Right now Eliza is pretty good at substitutions, but not so good at permutations, and re-arrangements.  Yet clearly something a little more sophisticated than diff and patch is needed, and yet grep isn't quite the right answer either.  Obviously, one could grep out the FOR loops, and the IF THENS, etc, and then one could compare the original code with the translated code, but I don't think that grep knows how to do that.  That's more like the task of running two or more lexers side by side, each of which is somehow an "expert" at some part of the structure while ignoring constructs that it doesn't understand.

Sort of like what GPT-3 tries to do - predict the next word in a sentence, based on an analysis of 100's of gigabytes of text, whether it is standard English or code.  Then there is also Microsoft's GitHub co-pilot - which I haven't tried yet - I don't know if it is even up and running, and in any case - can it use its AI to compare a mostly correct but a bit buggy Pascal source with the brand new but still seriously broken C version of the same program?  Probably not.

Yet - I knew that there was a reason for creating THIS mess, when I did, back around mid-summer 1997.

class text_object
{
    CCriticalSection critical;

public:
    bool m_bEnd;
    UINT    m_code_page;
    node_list<char*> m_nList;
    node<char*> *m_nPos;
    s_node<char*, language> m_sList;

public:
    text_object ();
    text_object (char *m_pText);
    text_object (const text_object ©);
    text_object (node_list<char *> *copyFrom);
    text_object (bTreeType<char*> **source);
    ~text_object ();
.
........etc ........

 It is a text object class, that encapsulates several types of data structures, which can be constructed from simple pointers to char, or from linked lists of pointers to char of two different types, depending on whether a "language" is specified, or else there is a binary tree variant.  And NOW - that gives me an idea - which hints at the two strands of DNA that make up a double helix concept, that is to say - without having to go fully Monty just yet with genetic algorithms when a "simple" Predict-o-Matic might be all that is required.

Or I could study the code and fix the bugs by hand?

BEGIN
  WITH (ingredients) 
     make("deluxe pizza");
     serve("deluxe pizza");
END;

No - I think I will go back to the plan of having Eliza learn how to debug this mess, and for a good reason!  Or, as Han Solo once said, "You know, sometimes, I surprise even myself!"  And here is why:

It just so happens that I have this C++ template for creating binary trees that I cooked up like I said, some 25 or so years ago.  So I go to work, figuring out how to use the operator form of placement new not just with the bTreeType nodes - but also with the data objects that they encapsulate so that I don't have to call malloc twice, filling up memory with the defacto linked list that malloc maintains for every object ever allocated, in the usual embodiment, in addition to another allocation for the object pointed to by the bTreeNode, which can really fill up memory fast on a microcontroller, at best - in addition to having to track additions, deletions, rearrangements, and often ending up with a fragmented heap that becomes useless for any large allocations.  So I tried creating a data type of bTreeType<pstring> where <pstring> is a simple 256 byte string that when it is allocated together with the bTreeType object, yields a 256+16 = 272 byte object, thus saving a pointer and an extra allocation.

Now, just for fun - allocate 256 of those all at once, by allocating a 69362 byte blob (binary large object), and then individually place AND initialize all 256 bTreeType<pstring> objects in the pre-allocated buffer using a for  loop.   Just for fun then - copy all of the Eliza response strings over into the individual strings, not just to verify that the allocations and placements are occurring correctly; but also because this sort of thing could come in useful for providing ways to manage things like VGA buffers, audio, p-machine memory and code spaces, etc., according to the memory model that will be need to be developed for the microcontroller - and I WOULD very much like for that to have some kind of virtual memory and or virtual protected mode that also supports multi-tasking.  Yes, on an Arduino, or a Propeller, or a NOR computer.

Now earlier, I was suggesting why not just grep out all of the FOR-DO constructs, IF-expr-THEN instances, and so on, which the Eliza algorithm seems to be pretty good and not only matching, but it is also pretty good at doing a lot of stuff that interestingly enough is also done by a more general pre-processor or lexer.  And that seems to be the methods of tokenizing, breaking apart, finding symbols, replacing symbols, pattern matching, reordering fragments, and reassembling those fragments into something else altogether.

It is as if Eliza should be saying "Don't  you believe that I can be as Turing complete as I need to be?"  Or perhaps Eliza wants to say "Perhaps you don't really want me to be Turing complete!".

Discussions