make, swift3: fix parsing empty literal sequences.
[jackhill/mal.git] / basic / printer.in.bas
index 7eb0028..55c6360 100644 (file)
-REM PR_STR(AZ, PR) -> R$
+REM PR_STR(AZ, B) -> R$
 PR_STR:
-  RR$=""
+  R$=""
   PR_STR_RECUR:
-  T=Z%(AZ,0)AND15
-  REM PRINT "AZ: "+STR$(AZ)+", T: "+STR$(T)+", V: "+STR$(Z%(AZ,1))
+  T=Z%(AZ)AND 31
+  U=Z%(AZ+1)
+  REM PRINT "AZ: "+STR$(AZ)+", T: "+STR$(T)+", U: "+STR$(U)
   IF T=0 THEN R$="nil":RETURN
+  REM if metadata, then get actual object
+  IF T>=14 THEN AZ=U:GOTO PR_STR_RECUR
   ON T GOTO PR_BOOLEAN,PR_INTEGER,PR_UNKNOWN,PR_STRING_MAYBE,PR_SYMBOL,PR_SEQ,PR_SEQ,PR_SEQ,PR_FUNCTION,PR_MAL_FUNCTION,PR_MAL_FUNCTION,PR_ATOM,PR_ENV,PR_RECUR,PR_FREE
 
   PR_UNKNOWN:
-    R$="#<unknown>"
+    REM MEMORY DEBUGGING:
+    REM R$="#<unknown>"
     RETURN
   PR_RECUR:
-    AZ=Z%(AZ,1)
+    AZ=U
     GOTO PR_STR_RECUR
   PR_BOOLEAN:
     R$="true"
-    IF Z%(AZ,1)=0 THEN R$="false"
+    IF U=0 THEN R$="false"
     RETURN
   PR_INTEGER:
-    T5=Z%(AZ,1)
-    R$=STR$(T5)
-    IF T5<0 THEN RETURN
+    T$=STR$(U)
     REM Remove initial space
-    R$=RIGHT$(R$, LEN(R$)-1)
+    IF U>=0 THEN T$=RIGHT$(T$,LEN(T$)-1)
+    R$=R$+T$
     RETURN
   PR_STRING_MAYBE:
-    R$=S$(Z%(AZ,1))
+    R$=S$(U)
     IF LEN(R$)=0 THEN GOTO PR_STRING
     IF MID$(R$,1,1)=CHR$(127) THEN R$=":"+MID$(R$,2,LEN(R$)-1):RETURN
   PR_STRING:
-    IF PR=1 THEN PR_STRING_READABLY
+    IF B=1 THEN GOTO PR_STRING_READABLY
     RETURN
   PR_STRING_READABLY:
-    S1$=CHR$(92):S2$=CHR$(92)+CHR$(92):GOSUB REPLACE: REM escape backslash
-    S1$=CHR$(34):S2$=CHR$(92)+CHR$(34):GOSUB REPLACE: REM escape quotes
-    S1$=CHR$(13):S2$=CHR$(92)+"n":GOSUB REPLACE: REM escape newlines
+    S1$="\":S2$="\\":GOSUB REPLACE: REM escape backslash "
+    S1$=CHR$(34):S2$="\"+CHR$(34):GOSUB REPLACE: REM escape quotes "
+    #cbm S1$=CHR$(13):S2$="\n":GOSUB REPLACE: REM escape newlines
+    #qbasic S1$=CHR$(10):S2$="\n":GOSUB REPLACE: REM escape newlines
     R$=CHR$(34)+R$+CHR$(34)
     RETURN
   PR_SYMBOL:
-    R$=S$(Z%(AZ,1))
+    R$=S$(U)
     RETURN
   PR_SEQ:
-    IF T=6 THEN RR$=RR$+"("
-    IF T=7 THEN RR$=RR$+"["
-    IF T=8 THEN RR$=RR$+"{"
     REM push the type and where we are in the sequence
-    X=X+2
-    S%(X-1)=T
-    S%(X)=AZ
+    Q=T:GOSUB PUSH_Q
+    Q=AZ:GOSUB PUSH_Q
+    REM save the current rendered string
+    S$(S)=R$:S=S+1
     PR_SEQ_LOOP:
-      IF Z%(AZ,1)=0 THEN PR_SEQ_DONE
-      AZ=AZ+1
-      GOSUB PR_STR_RECUR
-      REM if we just rendered a non-sequence, then append it
-      IF T<6 OR T>8 THEN RR$=RR$+R$
+      IF Z%(AZ+1)=0 THEN GOTO PR_SEQ_DONE
+      AZ=Z%(AZ+2):GOSUB PR_STR:GOSUB PEEK_Q_1:T=Q
+      REM append what we just rendered it
+      S$(S-1)=S$(S-1)+R$
+
+      REM if this is a hash-map, print the next element
+      IF T=8 THEN GOSUB PEEK_Q:AZ=Z%(Q+3):GOSUB PR_STR:S$(S-1)=S$(S-1)+" "+R$
+
       REM restore current seq type
-      T=S%(X-1)
+      GOSUB PEEK_Q_1:T=Q
       REM Go to next list element
-      AZ=Z%(S%(X),1)
-      S%(X)=AZ
-      IF Z%(AZ,1)<>0 THEN RR$=RR$+" "
+      GOSUB PEEK_Q
+      AZ=Z%(Q+1)
+      Q=AZ:GOSUB PUT_Q
+      IF Z%(AZ+1)<>0 THEN S$(S-1)=S$(S-1)+" "
       GOTO PR_SEQ_LOOP
     PR_SEQ_DONE:
-      REM get type
-      T=S%(X-1)
+      REM restore the current string
+      S=S-1:R$=S$(S)
       REM pop where we are the sequence and type
-      X=X-2
-      IF T=6 THEN RR$=RR$+")"
-      IF T=7 THEN RR$=RR$+"]"
-      IF T=8 THEN RR$=RR$+"}"
-      R$=RR$
+      GOSUB POP_Q
+      GOSUB POP_Q:T=Q: REM get type
+      IF T=6 THEN R$="("+R$+")"
+      IF T=7 THEN R$="["+R$+"]"
+      IF T=8 THEN R$="{"+R$+"}"
       RETURN
   PR_FUNCTION:
-    T1=Z%(AZ,1)
-    R$="#<function"+STR$(T1)+">"
+    R$="#<fn"+STR$(U)+">"
     RETURN
   PR_MAL_FUNCTION:
     T1=AZ
-    AZ=Z%(T1+1,0):GOSUB PR_STR_RECUR
-    T7$="(fn* "+R$
-    AZ=Z%(T1,1):GOSUB PR_STR_RECUR
-    R$=T7$+" "+R$+")"
+    AZ=Z%(T1+2):GOSUB PR_STR
+    REM append what we just rendered it
+    S$(S)="(fn* "+R$:S=S+1
+    AZ=Z%(T1+1):GOSUB PR_STR
+    S=S-1
+    R$=S$(S)+" "+R$+")"
     RETURN
   PR_ATOM:
-    AZ=Z%(AZ,1):GOSUB PR_STR_RECUR
+    AZ=U:GOSUB PR_STR
     R$="(atom "+R$+")"
     RETURN
   PR_ENV:
-    R$="#<env"+STR$(AZ)+", data"+STR$(Z%(AZ,1))+">"
+    R$="#<env"+STR$(AZ)+", data"+STR$(U)+">"
     RETURN
   PR_FREE:
-    R$="#<free memory "+STR$(AZ)+", next"+STR$(Z%(AZ,1))+">"
+    R$="#<free"+STR$(AZ)+", next"+STR$(U)+">"
     RETURN
     
-REM PR_STR_SEQ(AZ, PR, SE$) -> R$
+REM PR_STR_SEQ(AZ, B, B$) -> R$
+REM   - B is print_readably
+REM   - B$ is the separator
 PR_STR_SEQ:
-  T9=AZ
-  R1$=""
+  V=AZ
+  S$(S)="":S=S+1
   PR_STR_SEQ_LOOP:
-    IF Z%(T9,1)=0 THEN R$=R1$:RETURN
-    AZ=T9+1:GOSUB PR_STR
+    IF Z%(V+1)=0 THEN S=S-1:R$=S$(S):RETURN
+    AZ=Z%(V+2):GOSUB PR_STR
     REM goto the next sequence element
-    T9=Z%(T9,1)
-    IF Z%(T9,1)=0 THEN R1$=R1$+R$
-    IF Z%(T9,1)<>0 THEN R1$=R1$+R$+SE$
+    V=Z%(V+1)
+    IF Z%(V+1)=0 THEN S$(S-1)=S$(S-1)+R$
+    IF Z%(V+1)<>0 THEN S$(S-1)=S$(S-1)+R$+B$
     GOTO PR_STR_SEQ_LOOP