printing method overhaul

This commit is contained in:
dzaima 2023-01-09 01:14:33 +02:00
parent 381460e92e
commit a9c70d9d72
5 changed files with 58 additions and 41 deletions

View File

@ -252,7 +252,8 @@ B casrt_c1(B t, B x) {
B sys_c1(B t, B x);
B out_c1(B t, B x) {
if (isArr(x) && RNK(x)>1) thrF("•Out: Argument cannot have rank %i", RNK(x));
if (isAtm(x)) thrM("•Out: Argument must be a list");
if (RNK(x)>1) thrF("•Out: Argument cannot have rank %i", RNK(x));
printRaw(x); putchar('\n');
return x;
}

View File

@ -95,7 +95,6 @@ NOINLINE TStack* ts_e(TStack* o, u32 elsz, u64 am) { u64 size = o->size;
return n;
}
void fprint(FILE* f, B x);
void farr_print(FILE* f, B x) { // should accept refc=0 arguments for debugging purposes
ur r = RNK(x);
SGetU(x)
@ -108,27 +107,29 @@ void farr_print(FILE* f, B x) { // should accept refc=0 arguments for debugging
}
usz* sh = SH(x);
for (i32 i = 0; i < r; i++) {
if(i==0)fprintf(f, N64d,(u64)sh[i]);
else fprintf(f, ""N64d,(u64)sh[i]);
if(i!=0) fprintCodepoint(f, U'');
fprintf(f, N64d, (u64)sh[i]);
}
fprintf(f, "");
fprintCodepoint(f, U'');
} else if (ia>0) {
for (usz i = 0; i < ia; i++) {
B c = GetU(x,i);
if (!isC32(c) || (u32)c.u=='\n') goto reg;
if (!elChr(TI(x,elType))) {
for (usz i = 0; i < ia; i++) {
B c = GetU(x, i);
if (!isC32(c) || o2cG(c)<32) goto reg;
}
}
fprintf(f, "\"");
for (usz i = 0; i < ia; i++) fprintUTF8(f, (u32)GetU(x,i).u); // c32, no need to decrement
fprintsB(f, x);
fprintf(f, "\"");
return;
}
reg:;
fprintf(f, "");
fprintCodepoint(f, U'');
for (usz i = 0; i < ia; i++) {
if (i!=0) fprintf(f, ", ");
fprint(f, GetU(x,i));
}
fprintf(f, "");
fprintCodepoint(f, U'');
}
void fprint(FILE* f, B x) {
@ -136,9 +137,9 @@ void fprint(FILE* f, B x) {
NUM_FMT_BUF(buf, x.f);
fprintf(f, "%s", buf);
} else if (isC32(x)) {
if ((u32)x.u>=32) { fprintf(f, "'"); fprintUTF8(f, (u32)x.u); fprintf(f, "'"); }
else if((u32)x.u>15) fprintf(f, "\\x%x", (u32)x.u);
else fprintf(f, "\\x0%x", (u32)x.u);
if (o2cG(x)>=32) fprintsU32(f, (u32[3]){'\'', o2cG(x), '\''}, 3);
else if (o2cG(x)>=16) fprintf(f, "\\x%x", o2cG(x));
else fprintf(f, "\\x0%x", o2cG(x));
} else if (isVal(x)) {
#ifdef DEBUG
if (isVal(x) && (TY(x)==t_freed || TY(x)==t_empty)) {
@ -163,22 +164,7 @@ void fprint(FILE* f, B x) {
}
NOINLINE void fprintRaw(FILE* f, B x) {
if (isAtm(x)) {
if (isF64(x)) { NUM_FMT_BUF(buf, x.f); fprintf(f, "%s", buf); }
else if (isC32(x)) fprintUTF8(f, (u32)x.u);
else thrM("•Out: Unexpected argument type");
} else {
usz ia = IA(x);
SGetU(x)
for (usz i = 0; i < ia; i++) {
B c = GetU(x,i);
#if !CATCH_ERRORS
if (c.u==0 || noFill(c)) { fprintf(f, " "); continue; }
#endif
if (!isC32(c)) thrM("•Out: Unexpected element in argument");
fprintUTF8(f, (u32)c.u);
}
}
fprintsB(f, x);
}
NOINLINE void printRaw(B x) {

View File

@ -53,20 +53,45 @@ B utf8DecodeA(I8Arr* a) { // consumes a
return r;
}
void printUTF8(u32 c) {
if (c<128) printf("%c", c);
else if (c<=0x07FF) printf("%c%c" , 0xC0| c>>6 , 0x80|(c &0x3F) );
else if (c<=0xFFFF) printf("%c%c%c" , 0xE0| c>>12, 0x80|(c>>6 &0x3F), 0x80|(c &0x3F) );
else printf("%c%c%c%c", 0xF0| c>>18, 0x80|(c>>12&0x3F), 0x80|(c>>6&0x3F), 0x80|(c&0x3F));
}
void fprintUTF8(FILE* f, u32 c) {
void fprintCodepoint(FILE* f, u32 c) {
if (c<128) fprintf(f, "%c", c);
else if (c<=0x07FF) fprintf(f, "%c%c" , 0xC0| c>>6 , 0x80|(c &0x3F) );
else if (c<=0xFFFF) fprintf(f, "%c%c%c" , 0xE0| c>>12, 0x80|(c>>6 &0x3F), 0x80|(c &0x3F) );
else fprintf(f, "%c%c%c%c", 0xF0| c>>18, 0x80|(c>>12&0x3F), 0x80|(c>>6&0x3F), 0x80|(c&0x3F));
}
void fprintsU32(FILE* f, u32* s, usz len) {
for (usz i = 0; i < len; i++) fprintCodepoint(f, s[i]);
}
void fprintsB(FILE* f, B x) {
u8 xe = TI(x,elType);
usz ia = IA(x);
if (ia==0) return;
if (xe==el_c32) {
fprintsU32(f, c32any_ptr(x), ia);
} else {
incG(x);
if (!elChr(xe)) { x=chr_squeeze(x); xe=TI(x,elType); }
if (!elChr(xe)) {
#if !CATCH_ERRORS
SGetU(x)
for (usz i = 0; i < ia; i++) {
B c = GetU(x, i);
if (isC32(c)) fprintCodepoint(f, o2cG(c));
else if (c.u==0 || noFill(c)) fprintf(f, " ");
else thrM("Trying to output non-character");
}
return;
#endif
thrM("Trying to output non-character");
}
x = taga(cpyC32Arr(x));
fprintsU32(f, c32any_ptr(x), ia);
decG(x);
}
}
u64 utf8lenB(B x) { // doesn't consume; may error as it verifies whether is all chars
assert(isArr(x));
SGetU(x)

View File

@ -1,7 +1,9 @@
#pragma once
void printUTF8(u32 c);
void fprintUTF8(FILE* f, u32 c);
void fprintCodepoint(FILE* f, u32 v); // single codepoint
void fprintsUTF8(FILE* f, char* s); // UTF-8, null-terminated
void fprintsU32(FILE* f, u32* s, usz len); // unicode codepoints
void fprintsB(FILE* f, B x); // codepoints of x; doesn't consume; assumes argument is an array, doesn't care about rank, throws if its elements are not characters
u64 utf8lenB(B x); // doesn't consume; may error as it verifies whether is all chars
void toUTF8(B x, char* p); // doesn't consume; doesn't verify anything; p must have utf8lenB(x) bytes (calculating which should verify that this call is ok), add trailing null yourself

View File

@ -1339,6 +1339,9 @@ NOINLINE void vm_printPos(Comp* comp, i32 bcPos, i64 pos) {
// want to try really hard to print errors
if (!cbqn_initialized) goto native_print;
#if FORCE_NATIVE_ERROR_PRINT
goto native_print;
#endif
if (CATCH) goto native_print;
B s = emptyCVec();
@ -1355,7 +1358,7 @@ native_print:
usz srcL = IA(src);
SGetU(src)
usz srcS = cs; while (srcS>0 && o2cG(GetU(src,srcS-1))!='\n') srcS--;
usz srcE = srcS; while (srcE<srcL) { u32 chr = o2cG(GetU(src, srcE)); if(chr=='\n')break; fprintUTF8(stderr, chr); srcE++; }
usz srcE = srcS; while (srcE<srcL) { u32 chr = o2cG(GetU(src, srcE)); if(chr=='\n')break; fprintCodepoint(stderr, chr); srcE++; }
if (ce>srcE) ce = srcE;
cs-= srcS; ce-= srcS;
fputc('\n', stderr);
@ -1598,7 +1601,7 @@ NOINLINE void printErrMsg(B msg) {
SGetU(msg)
usz msgLen = IA(msg);
for (usz i = 0; i < msgLen; i++) if (!isC32(GetU(msg,i))) goto base;
fprintRaw(stderr,msg);
fprintRaw(stderr, msg);
return;
}
base: