Return Styles: Pseud0ch, Terminal, Valhalla, NES, Geocities, Blue Moon. Entire thread

Understanding void.h

Name: Anonymous 2016-01-25 19:02

So i've checked FV github to see it was empty.
Apparently FV is too stupid to use git and keeps void.h in gists.
From https://gist.github.com/FrozenVoid/87e6ad6212ac9ce496e0

1.The thing you notice first is everything depends on _VFUNC which actually does nothing but concatenate with ##
Its in varmacro.h and the system is based on http://stackoverflow.com/questions/11761703/overloading-macro-on-number-of-arguments bruteforce approach that creates a macro for every number of arguments. Its cute but limited to 63 arguments and requires writing 63 macros each time: he used this approach in early commits in the gist file.
What FV has done is to replace the 63 macros per macro with apply: same 63 macros but they carry a function macro as first argument and switch to next apply(N-1) with remaining arguments. There are several of these apply functions, most of them i couldn't understand, before writing some test code.
apply.h and apply2.h are the largest files in there along with argmacro.h.

2. _Generic abuse. If you preprocess the files which use p() macro the horrible mess of nested _Generics comes to front, hidden in type selection macro: the type selection...is just macro applied to the type list, another _Generic macro that has all the types.

3.tuple.h this one is quite interesting: using macro argument lists kept in parens as compile-time objects. The next trick is converting the "tuple" back into argument list:
Its not in tuple.h but counter-intuitevely in varmacro.h

#define wrap(...) __VA_ARGS__
#define detuple(...) wrap __VA_ARGS__
Basically when a "tuple" like (1,2,3) is passed to detuple it strips the parens off it, because wrap assumes the parens are its arguments and returns them back.
4.There are actually car and cdr in there: in the argmacro.h there is curious "rest" macro that strips off the first N arguments from its arguments and frontrest macro which return back first N arguments.
They apparently work by passing the argument list N times so it either cut N front arguments or preserves the N first arguments. Neat.

5.The key of array.h - the foreach macro: i was first curious how it find out the size of array, the trick he used is in mem.h elems() macro that uses size() a dirty macro hack that either returns sizeof or msize(): a call to check heap object length in bytes if its sizeof() equal to size of pointer. Here it is:
#define size1(arg1) ({u8 lensize=sizeof(arg1);\
once;\
if((lensize!=sizeof(vp)))break;\
if(isarray(arg1)|isbasic(arg1)){;break;};\
lensize=msize((vp)(u8)arg1);endonce;\
;lensize;})
void.h isn't that cryptic as it seemed at first glance.

Name: Anonymous 2016-01-28 15:47

>>17
Lisp has a large CPU/Ram overhead thats inherent due its design.
99% of useful things it does is reducing amount of code written: Lisp macros to generate Real code that will run(at runtime) and Lisp code will do the same thing C code does 99% of time.
void.h macros remove most of the "abstraction cruft" which Lisp also remove at cost of performance.
Since the preprocessor is (besides compile-time) a zero-cost abstraction the generated code doesn't suffer any performance penalty for using it.
Lisp generates crappy Lisp code or converts Lisp to crappy C ocde that is inferior to code made with C macros.
Process:
Lisp->code.lisp-(slow)>lisp.c(Lisp-to-C translated)->GCC(optimize)->code.asm
Void.h(zero-cost C macros)->code.c(real C)->GCC(optimize)->code.asm
Some Lisp compilers don't rely on GCC: they produce even worse code. And interpreters..worse than python/ruby.
Lisp compilers would actually be useful if they were generating C code from macros like void.h without any Lisp concepts in result(i.e. text generator that produces C code from macro-blocks). Since C macros already proven to be as versatile as Lisp, the case of using Lisp is quite weak anyway and considering the syntax())( probably useless.

Newer Posts
Don't change these.
Name: Email:
Entire Thread Thread List