home *** CD-ROM | disk | FTP | other *** search
/ Source Code 1992 March / Source_Code_CD-ROM_Walnut_Creek_March_1992.iso / usenet / altsrcs / 1 / 1038 < prev    next >
Internet Message Format  |  1990-12-28  |  55KB

  1. From: chongo@hoptoad.uucp (Landon C. Noll)
  2. Newsgroups: comp.lang.c,comp.unix.wizards,alt.sources,comp.sources.d,misc.misc
  3. Subject: CORRECT 1989 International Obfuscated C Code Contest Winners
  4. Message-ID: <10862@hoptoad.uucp>
  5. Date: 19 Mar 90 17:46:03 GMT
  6.  
  7.  
  8.   *BLUSH*  *BLUSH*  *BLUSH*  *BLUSH*  *BLUSH*  *BLUSH*  *BLUSH*  *BLUSH*
  9.  
  10. The reposting of the 1989 International Obfuscated C Code Contest Winners
  11. was in error.  The reposting was a pre-release version that did not include
  12. a number of important fixes (like some co-winner names on a entry for
  13. example), typos and other stuff.
  14.  
  15. Please nuke the progs from the previous IOCCC posting and replace them
  16. with the ones in this posting.
  17.  
  18. chongo <sorry for the mixup> /\oo/\
  19.  
  20. # This is a shell archive.  Remove anything before this line, then
  21. # unpack it by saving it in a file and typing "sh file".  (Files
  22. # unpacked will be owned by you and have default permissions.)
  23. #
  24. # This archive contains:
  25. # 1989/Makefile 1989/README 1989/fubar.c 1989/fubar.hint 1989/fubar.orig.c
  26. # 1989/fubar.orig.sh 1989/fubar.sh 1989/jar.1.c 1989/jar.1.hint 
  27. # 1989/jar.1.orig.c 1989/jar.1.orig.sh 1989/jar.1.sh 1989/jar.2.c 
  28. # 1989/jar.2.hint 1989/ovdluhe.c 1989/ovdluhe.hint 1989/paul.c 1989/paul.hint 
  29. # 1989/robison.c 1989/robison.hint 1989/rowmer.c 1989/rowmer.hint 1989/rules 
  30. # 1989/tromp.bsd.c 1989/tromp.hint 1989/tromp.s5.c 1989/vanb.c 1989/vanb.hint 
  31. # 1989/westley.c 1989/westley.hint
  32.  
  33. : =-=-=-=-=-=-= first line of shar 1 of 1 =-=-=-=-=-=-=-=-=-
  34. echo mkdir ./1989
  35. mkdir ./1989
  36. echo x - 1989/Makefile
  37. sed -e 's/^X//' > "1989/Makefile" << '//E*O*F 1989/Makefile//'
  38. X# %W% %G% %U%
  39. X#
  40. X# 1989 makefile
  41. X
  42. XSHELL=/bin/sh
  43. XCFLAGS=-O
  44. XCC=cc
  45. X
  46. XWINNERS=ovdluhe jar.1 jar.2 fubar westley paul robison rowmer vanb tromp.bsd
  47. XALTERNATE=jar.1.orig fubar.orig tromp.s5
  48. X
  49. Xall: ${WINNERS}
  50. X
  51. Xovdluhe: ovdluhe.c
  52. X    ${CC} ${CFLAGS} $? -o $@
  53. X
  54. X# NOTE: jar.1.c outputs its string in one section
  55. X#       this program may not print well on some terminals
  56. Xjar.1: jar.1.c jar.1.sh
  57. X    rm -f jar.1
  58. X    cp jar.1.sh jar.1
  59. X    chmod +x jar.1
  60. X# NOTE: The jar.1.orig file is the original entry
  61. Xjar.1.orig: jar.1.orig.c jar.1.orig.sh
  62. X    rm -f jar.1.orig
  63. X    cp jar.1.sh jar.1.orig
  64. X    chmod +x jar.1.orig
  65. X
  66. Xjar.2: jar.2.c
  67. X    ${CC} ${CFLAGS} $? -o $@
  68. X
  69. X# NOTE: fubar.c uses the /bin/sh shell
  70. Xfubar: fubar.c fubar.sh
  71. X    rm -f fubar
  72. X    cp fubar.sh fubar
  73. X    chmod +x fubar
  74. X# NOTE: The fubar.orig.c file is the original entry
  75. Xfubar.orig: fubar.orig.c fubar.orig.sh
  76. X    rm -f fubar.orig
  77. X    cp fubar.orig.sh fubar.orig
  78. X    chmod +x fubar.orig
  79. X
  80. Xwestley: westley.c
  81. X    ${CC} ${CFLAGS} -Dtrgpune=putchar $? -o $@
  82. X
  83. Xpaul: paul.c
  84. X    ${CC} ${CFLAGS} $? -o $@
  85. X
  86. Xrobison: robison.c
  87. X    ${CC} ${CFLAGS} $? -o $@
  88. X
  89. Xrowmer: rowmer.c
  90. X    ${CC} ${CFLAGS} $? -o $@
  91. X
  92. X# NOTE: this version requires BSD style signals and setitimer
  93. X#    this may not work well on low baud rate terminals
  94. X#    the file tromp.bsd.c is the original version
  95. Xtromp: tromp.bsd.c
  96. X    ${CC} ${CFLAGS} $? -o $@
  97. X    touch HI
  98. X    -chmod 0666 HI
  99. X# NOTE: sites without BSD style signals and setitimer (e.g. System V.3)
  100. X#    should use this version
  101. Xtromp.s5: tromp.s5.c
  102. X    ${CC} ${CFLAGS} $? -o $@
  103. X    touch HI
  104. X    -chmod 0666 HI
  105. X
  106. Xvanb: vanb.c
  107. X    ${CC} ${CFLAGS} $? -o $@
  108. X
  109. Xclean:
  110. X    rm -f ovdluhe.o jar.2.o fubar.o westley.o paul.o robison.o
  111. X    rm -f rowmer.o tromp.o vanb.o 
  112. X    rm -f x x1 ouroboros.c ouroboros.o fubar.orig.o tromp.bsd.o tromp.s5.o core
  113. Xclobber: clean
  114. X    rm -f ${WINNERS} 
  115. X    rm -f jar.1.o HI 
  116. X    rm -f ${ALTERNATE}
  117. Xnuke: clobber
  118. X    @true
  119. Xinstall: all
  120. X    cat ${WINNERS} > /dev/null
  121. //E*O*F 1989/Makefile//
  122.  
  123. echo x - 1989/README
  124. sed -e 's/^X//' > "1989/README" << '//E*O*F 1989/README//'
  125. X1989 marked the "The Sixth International Obfuscated C Code Contest"
  126. X
  127. XInstructions for use: Run make to compile entries (it is possible
  128. Xthat on System V or non-unix systems the makefile needs to be
  129. Xchanged). Look at the source and try to figure out what the programs
  130. Xdo, and run them with various inputs. If you want to, look at the
  131. Xhints files for (minor) spoilers.
  132. X
  133. XThis year, the Grand Prize was given to the most useful program.
  134. X
  135. XThe "Strangest abuse of the rules" award was given this year to stress
  136. Xthe fact that starting in 1990, compiling entries must result an
  137. Xexecutable regular file.
  138. X
  139. XIn two other cases, we included System V portable versions of winning
  140. Xprograms.  The makefile always uses the portable version of the "Best
  141. Xself modifying program" because there as no loss of functionality in
  142. Xusing it.  In the case of the "Best game" winner, however, some
  143. Xfunctionality is lost in the portable version and so the makefile uses
  144. Xthe original program.  System V users may need to change the makefile
  145. Xto use the s5 version.  See the hint files or the Makefile for details.
  146. X
  147. XRules and results were posted to comp.lang.c, comp.sources.unix, and
  148. Xalt.sources.  They have been made available on a wide number of Usenet
  149. Xarchive sites such as uunet.  The 1989 winners will be published in the
  150. XMicro/Systems Journal.
  151. //E*O*F 1989/README//
  152.  
  153. echo x - 1989/fubar.c
  154. sed -e 's/^X//' > "1989/fubar.c" << '//E*O*F 1989/fubar.c//'
  155. X
  156. X#include <stdio.h>
  157. X#define QQ      1
  158. X#define TT         1
  159. X#define cc main(c,v) int c; char **v;{char tt[12],qq[7]; int q=0,o=1,l=1,m=1;struct {int c;} f;
  160. X#define ouroboros qq[6]='\0';tt[11]='\0';if(QQ==atoi(v[1])+1){(void)fprintf(stderr,"%s factorial = %d\n",v[1], TT);exit(1);}o=c+f
  161. X#define x ;while(EOF!=(o=getchar())){if(l && q=='Q' && o=='Q'){l=0;(void)getchar();(void)fread(qq,6,1,stdin);(void)printf("Q %6d",atoi(qq)+1);}else
  162. Xif(m && q=='T' && o=='T'){m=0;(void)fread(tt,11,1,stdin);(void)printf("T %9d\n",atoi(tt)*QQ);}else {q=o;(void)putchar(o);}}exit(0);}
  163. Xcc ouroboros.c -o x 
  164. X#define zxc ;{/*
  165. Xcat ouroboros.c | x $1 > x1
  166. Xif [ $? -ne 0 ]; then
  167. Xexit
  168. Xfi
  169. Xmv x1 ouroboros.c
  170. Xchmod +x ouroboros.c
  171. Xexec ouroboros.c $1
  172. Xexit
  173. X*/
  174. //E*O*F 1989/fubar.c//
  175.  
  176. echo x - 1989/fubar.hint
  177. sed -e 's/^X//' > "1989/fubar.hint" << '//E*O*F 1989/fubar.hint//'
  178. XBest self-modifying program: <sequent!fubar> Jay Vosburgh
  179. X
  180. X    Jay Vosburgh
  181. X        Sequent Computer Systems, Inc
  182. X        15450 SW Koll Parkway
  183. X        Beaverton, OR
  184. X        97006
  185. X        USA
  186. X
  187. XJudges notes:
  188. X
  189. X    Run this with a single digit argument (or wait a long time).
  190. X
  191. X    There are 2 versions of this program, the one that was entered,
  192. X    and one that was changed by the judges to be more portable. The
  193. X    makefile runs the latter version by default.
  194. X
  195. X    The blank line at the beginning of the source is mandatory.
  196. X    Do you know why?
  197. X
  198. X    The shell script run by the makefile joins lines that may be
  199. X    cut up by mailers.  The file "fubar.orig.c", for example, needs
  200. X    the 6th and 7th lines joined together (with a space between
  201. X    them) to recreate the original entry.  If you fix the file, you
  202. X    will need to change the last 8 linnes of "fubar.orig.sh" to read:
  203. X
  204. X        cp fubar.orig.c ouroboros.c
  205. X        chmod +x ouroboros.c
  206. X        csh ouroboros.c $1
  207. X        rm -f ouroboros.c x1 x
  208. X
  209. X    The more portable version, "fubar.c", can be fixed by joining the
  210. X    7th and 8th lines in the same way.  As well, if you fix "fubar.c"
  211. X    you will need to also change the last 8 lines to "fubar.sh" to read:
  212. X
  213. X        cp fubar.c ouroboros.c
  214. X        chmod +x ouroboros.c
  215. X        csh ouroboros.c $1
  216. X        rm -f ouroboros.c x1 x
  217. X
  218. XSelected notes from the author:
  219. X
  220. X    In a nutshell, this is probably the slowest and most
  221. X    obnoxious factorial program ever written.  Unfortunately, 
  222. X    the name of the C source must be "ouroboros.c"; the name is 
  223. X    hard-coded into the program.  
  224. X
  225. X    The source is a legal shell script and a legal C program.  
  226. X    The shell script compiles itself, and then executes the
  227. X    resulting binary, giving the source as input.  The program 
  228. X    works by successively modifying #define lines each pass through.
  229. X
  230. X    Both "indent" and "cb" will damage the program, "indent" 
  231. X    much more so.
  232. //E*O*F 1989/fubar.hint//
  233.  
  234. echo x - 1989/fubar.orig.c
  235. sed -e 's/^X//' > "1989/fubar.orig.c" << '//E*O*F 1989/fubar.orig.c//'
  236. X#include <stdio.h>
  237. X#define QQ      1
  238. X#define TT         1
  239. X#define cc main(c,v) int c; char **v;{char tt[12],qq[7]; int q=0,o=1,l=1,m=1;struct {int c;} f;
  240. X#define incest qq[6]='\0';tt[11]='\0';if(QQ==atoi(v[1])+1){(void)fprintf(stderr,"%s factorial = %d\n",v[1], TT);exit(1);}o=c+f
  241. X#define x ;while(EOF!=(o=getchar())){if(l && q=='Q' && o=='Q'){l=0;(void)getchar();(void)fread(qq,6,1,stdin);(void)printf("Q %6d",atoi(qq)+1);}else
  242. Xif(m && q=='T' && o=='T'){m=0;(void)fread(tt,11,1,stdin);(void)printf("T %9d\n",atoi(tt)*QQ);}else {q=o;(void)putchar(o);}}exit(0);}
  243. Xcc incest.c -o x 
  244. X#define zxc ;{/*
  245. Xcat incest.c | x $1 >! x1
  246. Xif ($status != 0) then 
  247. Xexit
  248. Xendif
  249. Xmv x1 incest.c
  250. Xchmod +x incest.c
  251. Xexec incest.c $1
  252. Xexit
  253. X*/
  254. //E*O*F 1989/fubar.orig.c//
  255.  
  256. echo x - 1989/fubar.orig.sh
  257. sed -e 's/^X//' > "1989/fubar.orig.sh" << '//E*O*F 1989/fubar.orig.sh//'
  258. X:
  259. X# to run fubar in the 'proper' way
  260. X
  261. X# parse args
  262. Xif [ $# -ne 1 ]; then
  263. X    echo "usage: $0 number" 1>&2
  264. X    exit 1
  265. Xfi
  266. X
  267. X# run/compile it
  268. Xrm -f incest.c x1 x
  269. Xex - <<EOF
  270. Xr fubar.orig.c
  271. X6,7j
  272. Xw incest.c
  273. XEOF
  274. Xchmod +x incest.c
  275. Xcsh incest.c $1
  276. Xrm -f incest.c x1 x
  277. //E*O*F 1989/fubar.orig.sh//
  278.  
  279. echo x - 1989/fubar.sh
  280. sed -e 's/^X//' > "1989/fubar.sh" << '//E*O*F 1989/fubar.sh//'
  281. X:
  282. X# to run fubar in the 'proper' way
  283. X
  284. X# parse args
  285. Xif [ $# -ne 1 ]; then
  286. X    echo "usage: $0 number" 1>&2
  287. X    exit 1
  288. Xfi
  289. X
  290. X# run/compile it
  291. Xrm -f ouroboros.c x1 x
  292. Xex - <<EOF
  293. Xr fubar.c
  294. X7,8j
  295. Xw ouroboros.c
  296. XEOF
  297. Xchmod +x ouroboros.c
  298. Xouroboros.c $1
  299. Xrm -f ouroboros.c x1 x
  300. //E*O*F 1989/fubar.sh//
  301.  
  302. echo x - 1989/jar.1.c
  303. sed -e 's/^X//' > "1989/jar.1.c" << '//E*O*F 1989/jar.1.c//'
  304. Xchar*_="Hello world.\n";
  305. //E*O*F 1989/jar.1.c//
  306.  
  307. echo x - 1989/jar.1.hint
  308. sed -e 's/^X//' > "1989/jar.1.hint" << '//E*O*F 1989/jar.1.hint//'
  309. XStrangest abuse of the rules: <...!uunet!mcvax!hutcs!jar> Jari Arkko
  310. X
  311. X    Jari Arkko
  312. X    Laboratory of Information Processing Science
  313. X    Helsinki University of Technology
  314. X    Otakaari 1
  315. X    02150 Espoo
  316. X    Finland
  317. X
  318. XJudges notes:
  319. X
  320. X    On many systems the compiler will not allow you to send the
  321. X    object file to /dev/tty.  The author suggested:
  322. X
  323. X        cc -c -o /dev/tty jar.1.c
  324. X
  325. X    On systems that have symbolic links, we suggest:
  326. X
  327. X        ln -s /dev/tty jar.1.o
  328. X        cc -c jar.1.c
  329. X    
  330. X    if your system has symbolic links.  The shell script run
  331. X    by the makefile simply cats the .o file to the terminal
  332. X    which can be used as a last resort.
  333. X
  334. X    Abuse of the rules winners usually result in a change of the
  335. X    rules.  Starting in 1990, compiling entries must result an
  336. X    regular file which can be executed.
  337. X
  338. XSelected notes from the author:
  339. X
  340. X    This program is (supposedly) the smallest C program able to
  341. X    print "Hello world.". The compilation itself produces the
  342. X    desired printout and the program need not be actually run.
  343. //E*O*F 1989/jar.1.hint//
  344.  
  345. echo x - 1989/jar.1.orig.c
  346. sed -e 's/^X//' > "1989/jar.1.orig.c" << '//E*O*F 1989/jar.1.orig.c//'
  347. Xchar*He="llo world.\n";
  348. //E*O*F 1989/jar.1.orig.c//
  349.  
  350. echo x - 1989/jar.1.orig.sh
  351. sed -e 's/^X//' > "1989/jar.1.orig.sh" << '//E*O*F 1989/jar.1.orig.sh//'
  352. X:
  353. X# 'run' jar.1.orig
  354. X
  355. X# run/compile it
  356. Xrm -f jar.1.orig.o
  357. Xcc jar.1.orig.c -c
  358. Xcat jar.1.orig.o
  359. Xrm -f jar.1.orig.o
  360. //E*O*F 1989/jar.1.orig.sh//
  361.  
  362. echo x - 1989/jar.1.sh
  363. sed -e 's/^X//' > "1989/jar.1.sh" << '//E*O*F 1989/jar.1.sh//'
  364. X:
  365. X# 'run' jar.1
  366. X
  367. X# run/compile it
  368. Xrm -f jar.1.o
  369. Xcc jar.1.c -c
  370. Xcat jar.1.o
  371. Xrm -f jar.1.o
  372. //E*O*F 1989/jar.1.sh//
  373.  
  374. echo x - 1989/jar.2.c
  375. sed -e 's/^X//' > "1989/jar.2.c" << '//E*O*F 1989/jar.2.c//'
  376. X#define d define
  377. X#d a include
  378. X#a <stdio.h>
  379. X#a <string.h>
  380. X#a <ctype.h>
  381. X#d p char*
  382. X#d P ,(p)
  383. X#d T(E) !strcmp(E,"()")
  384. X#d U return
  385. X#d W while
  386. X#d X sbrk(199)
  387. X#d z atof
  388. X#d e isspace
  389. X#d D A(_)
  390. X#d E S(C(_))
  391. X#d B(y) p y(_)p _;{
  392. X#d G(y,V) B(y)p i;U sprintf(i=X,"%lf",z(E)V z(S(C(D)))),i;}
  393. X
  394. X        p sbrk(),*S(),*j(),*O,*H;K,Y,M=14;double
  395. X      z();Q(_)p _;{int V=0;W(e(*_))_++;H=_;W(V|!(e
  396. X    (*H)|*H==')'||(*H=='('&&H-_)))V+=(*H=='(')-(*H==
  397. X      ')'),H++;U H-_;}B(C)U _++,Y=Q(_),_=strncpy(X,_,Y),_[
  398. X    Y]=0,_;}B(A)_++,_+=Q(_);W(e(*_))_++;U O=X,*O='(',strcpy(
  399. X  O+1,_),O;}B(Z)U _;}B(c)U C(E);}B(q)U A(E);}B(t)p i=E;U H=S(C
  400. X(D)),sprintf(O=X,T(H                 )?"(%s)":"(%s %s",i,H+1)
  401. X
  402. X         ,O;}B(F)U S(C(A(T(E)?D:_)));}L(i,s)p
  403. X
  404. Xi,*s;{U isdigit(*i)        ?         z(i)!=z(s):strcmp(i,s);}
  405. X  B(b)U L(E,S(C(D)))?"()":"t";}B(R)U E;}B(o)U z(E)<z(S(C(D)))?
  406. X    "t":"()";}G(f,+)G(g,-)G(h,*)p r[4][2]={"function"   P R,
  407. X      "quote"P C,"lambda"P Z,"defun"P j};B(j)U r[M][1]=D,*
  408. X    r[M++]=C(_);}p not[99][2]={"if"P F,"equal"P b,"<"
  409. X      P o,"+"P f,"-"P g,"*"P h,"car"P c,"cdr"P q,
  410. X        "cons"P t,"t","t"};B(S)int Li,s;p u;if(
  411. X          isdigit(*_)|T(_))U _;for(Y=M;Y--;)
  412. X        if(!strcmp(_,*r[Y]))U r[Y][1]
  413. X          ;u=E,_=D;if(*u-'(')U(*((p(*)())u)
  414. X        )(_);s=Li=M;W(!T(_))r[M][1]=E,*r[M++]
  415. X    ="",_=D;O=C(u);W(!T(O))*r[Li++]=C(O),O=A(O);U O=S
  416. X    (C(A(u))),M=s,O;}main(){H=O=X,Y=0;W(Y|!e(K=getchar()))K==
  417. X    EOF?exit(0):0,Y+=(K=='(')-(K==')'),*H++=K;*H=0,puts(S(O))
  418. X                ,
  419. X         main();{printf("XLISP 4.0\n");}}
  420. //E*O*F 1989/jar.2.c//
  421.  
  422. echo x - 1989/jar.2.hint
  423. sed -e 's/^X//' > "1989/jar.2.hint" << '//E*O*F 1989/jar.2.hint//'
  424. XBest of show: <...!uunet!mcvax!hutcs!jar> Jari Arkko, Ora Lassila, Esko Nuutila
  425. X
  426. X    Jari Arkko, Ora Lassila, Esko Nuutila
  427. X    Laboratory of Information Processing Science
  428. X    Helsinki University of Technology
  429. X    Otakaari 1
  430. X    02150 Espoo
  431. X    Finland
  432. X
  433. XJudges notes:
  434. X
  435. X    This is the most useful program entered this year. It is a
  436. X    rather large subset of lisp.  It has no error recovery, and
  437. X    performs rather poorly in a number of cases.  Even so, placing
  438. X    all this functionality in such a small, densely packed program,
  439. X    is impressive enough to win the Best of show award.
  440. X
  441. XSelected notes from the author:
  442. X
  443. X    This program implements a Lisp interpreter in 1465 bytes of source.
  444. X    Some sophisticated features supported, eg. functionals and recursion.  
  445. X    The special-forms/functions/variables implemented are:
  446. X    
  447. X        +    -    *    <    ()    
  448. X        car    cdr    cons    defun    equal
  449. X        function if    lambda    quote    t
  450. X    
  451. X    Below are sample lisp expressions you might choose to try as input.
  452. X    The program implements a conventional lisp listener, i.e. you type in
  453. X    lisp expressions (followed by CR), the program evaluates them and
  454. X    prints out the return values. End execution by typing an end-of-file
  455. X    character.
  456. X    
  457. X    (+ 2.5 3.1)
  458. X    (defun fib (n)
  459. X       (if (< n 2)
  460. X           1
  461. X           (+ (fib (- n 2)) (fib (- n 1)))))
  462. X    (fib 10)
  463. X    (defun ! (x) (if (equal x 0) 1 (* x (! (- x 1)))))
  464. X    (! 7)
  465. X    (defun fn1 (fn) (+ (fn 1 2) (fn 3 4)))
  466. X    (defun fn2 (a b) (+ a b))
  467. X    (fn1 (function +))
  468. X    (fn1 (function fn2))
  469. X    (fn1 (function (lambda (z1 z2) (+ z1 z2))))
  470. X    (quote a)
  471. X    (cons (quote (a b)) (quote (c d e)))
  472. X    (cons (quote (f)) ())
  473. X    (car (quote (a b c)))
  474. X    (cdr (cdr (quote (g h i))))
  475. X    
  476. X    Please do not leave any whitespace before the first parenthesis when
  477. X    you type your input, or any other unnecessary whitespace. Please try to
  478. X    avoid any undefined variables or functions, wrong number of arguments
  479. X    etc. All these errors are likely to dump core (i.e. there are no error
  480. X    checks in the program).
  481. X    
  482. X    Traditional Lisp implementations use cons cells as the main data
  483. X    structure. Lists are organized of pointer chains of these cells.
  484. X    In this program, an alternate representation was chosen: char*'s.
  485. X    All list operations, including the ones in the interpreter, are
  486. X    made using string representations of the lists. These operations
  487. X    must count parentheses and skip whitespace. This leads to extremely
  488. X    poor performance!
  489. //E*O*F 1989/jar.2.hint//
  490.  
  491. echo x - 1989/ovdluhe.c
  492. sed -e 's/^X//' > "1989/ovdluhe.c" << '//E*O*F 1989/ovdluhe.c//'
  493. X#include <string.h>
  494. Xtypedef char ape
  495. X#define D define
  496. X#D EA register
  497. X#D EP unsigned
  498. X#D A 1
  499. X#D AP (A<<A)
  500. X#D P (A<<AP)
  501. X#D AE ((P<<P)<<A)
  502. X#D PE (((A<<P)<<P)<<P)
  503. X#D E ((EP)A>>A)
  504. X#D APE {EA EP ape ea=AE;while(ea--) e[ea]=E;}
  505. X;ape a[PE+A],ap,*ae,p[P+A],e[AE];
  506. Xmain(){ape pe,*ep=a;srand((EP)time((long)E));
  507. Xwhile(((*(ep++)=getchar())!=-A)&&((ep-a)<PE));
  508. X*(ae= --ep)=E;for(ap=E;ap<=P;){APE;if(pe=PA())
  509. X{putchar(pe);if(ap<P){p[ap]=pe;ap++;}else{
  510. Xep=p+A;while(*ep) *(ep-A)= *(ep++); *(ep-A)=pe;}}else break;}}
  511. XPA(){EA ape pe,*ep=a,pa,Ap=E;for(ep=a;ep<ae-P;ep++)
  512. Xif(!strncmp(ep,p,ap)){e[*(ep+ap)]++;Ap++;}if(!Ap)return(Ap);
  513. Xpa=rand()%Ap+A;pe=~E,Ap=!Ap;while((Ap+=e[++pe])<pa);return(pe);}
  514. //E*O*F 1989/ovdluhe.c//
  515.  
  516. echo x - 1989/ovdluhe.hint
  517. sed -e 's/^X//' > "1989/ovdluhe.hint" << '//E*O*F 1989/ovdluhe.hint//'
  518. XMost humorous output: <...!unido!cernvax!ethz!ovdluhe> Oskar von der Luehe
  519. X
  520. X    Oskar von der Luehe
  521. X    Institut fuer Astronomie
  522. X    ETH - Zentrum
  523. X    8092 Zuerich
  524. X    Switzerland
  525. X
  526. XJudges notes:
  527. X
  528. X    Run this program using your favorite text file as input.  Files
  529. X    such as mailboxes, man pages and usenet articles are especially
  530. X    recommended.  You will get different output each time you run it.
  531. X
  532. X    Run the program this way:
  533. X
  534. X        ovdluhe < textfile
  535. X
  536. X    The program stops when it reaches the end of the template buffer 
  537. X    by chance or is killed.
  538. X
  539. XSelected notes from the author:
  540. X
  541. X    This program implements an "Eddington ape" - it generates
  542. X    random text from a supplied template.  The template text file
  543. X    is read through stdin.  The larger the template, the better the
  544. X    result.  A maximum of 2**12 chars are used. From the template,
  545. X    the program calculates the statistics of chars that immediately
  546. X    follow a given string (correlator string) of a certain length
  547. X    (currently 4 - can be varied by changing the definition for P
  548. X    accordingly).  A character is randomly chosen, weighted by its
  549. X    probability to occur after the correlator string.  That
  550. X    character is printed to stdout and placed at the end of the
  551. X    correlator string, whose first character is discarded.
  552. X    Meaningful words are therefore usually preserved, the effect on
  553. X    sentences can be dramatically random.
  554. X
  555. X    You might want to vary the definition of P between 2 and 10 and
  556. X    observe the result.
  557. //E*O*F 1989/ovdluhe.hint//
  558.  
  559. echo x - 1989/paul.c
  560. sed -e 's/^X//' > "1989/paul.c" << '//E*O*F 1989/paul.c//'
  561. X#include <stdio.h>
  562. X#define f int
  563. X#define v (void)printf(
  564. X#define x ),exit(1);
  565. X#define y ){if(n)c=z(n,u),u=n,n=c;o[i]=n?'0'+(1&*n):'0';}
  566. X#define z(a,b) (f*)(~1&*a^(f)b)
  567. X#define k(l) if(!(l=(f*)malloc(sizeof(l))))v 23+m x if(1&(f)l)v 39+m x*l=
  568. Xr(p,q,d)f*p,*q;{char o[81];f*n=p,i=39,*c,*u=d?q:z(p,q);o[40]='0'+(1&*p);
  569. Xfor(;i>=0;i--y u=d?z(p,q):q;n=p;for(i=41;i<79;i++y o[i++]='\r';o[i++]=0;
  570. Xv o);(void)fflush(stdout);sleep(1);}
  571. Xmain(a,c)char**c;{char*u,*malloc(),*m=
  572. X"Usage: black [string]\n\0No more memory\n\0Unusable memory alignment\n\0jt,s@m@ (beleY%XX&Yz {z&z}i|R(|)*((.)i)hiniFiGJ%FG.JJgJ: ;;&;z {z&z}-RS/ROiOV OP+PsaPh+ijainnjmamfmfAlnnnnphppopv%vvgv.aABiB1/BVP11/1.%..&.OhrR-WV V1#1VP1CcC0R\
  573. X\n\n'CVP0\n!\n\n'\nEaEEnEamat!akckk'kwaww'wz,zzozEit +",
  574. X*n=m;f*q,*p=0,*g,b=3,d;
  575. Xif(a>2)v m x n=a>1?c[1]:n;
  576. X/*v"\t\t\t\t\tV\n");*/
  577. Xk(q)0;u=n;a=~1&'j';
  578. Xwhile(a!='x'){
  579. X    /*r(q,p,b);*/
  580. X    for(;;u+=3){
  581. X        u= *u?u:n;
  582. X        if((~1&*u)==a&&(1&*q)<<1==(2&u[2]))break;
  583. X    }
  584. X    a=~1&u[1];
  585. X    d=(8&u[2])>>3;
  586. X    if(16&u[2])putchar(u[3]);
  587. X    if(4&u[2])*q|=1;else*q&=~1;
  588. X    if(b==d)g=p;else{
  589. X        g=z(q,p);
  590. X        if(!g){k(g)(f)q;*q^=(f)g;}
  591. X    }
  592. X    p=q;q=g;b=1-d;
  593. X}
  594. X/*r(q,p,b);v"\n");*/exit(0);
  595. X}
  596. //E*O*F 1989/paul.c//
  597.  
  598. echo x - 1989/paul.hint
  599. sed -e 's/^X//' > "1989/paul.hint" << '//E*O*F 1989/paul.hint//'
  600. XMost complex algorithm: <...!oliveb!cirrusl!paul> Paul E. Black
  601. X
  602. X    Paul E. Black
  603. X    CIRRUS LOGIC, Inc.
  604. X    1463 Centre Pointe Dr.
  605. X    Milpitas, CA 
  606. X    95035 
  607. X    USA
  608. X
  609. XJudges notes:
  610. X
  611. X    The original source contained a long line which caused many
  612. X    mailers to barf.  The original file may be re-constructed by
  613. X    removeing the trailing "\" on line 12 and joining lines 12 and
  614. X    13 together without a space.
  615. X
  616. X    WHAT FOLLOWS IS A DETAILED PROGRAM EXPLINATION AND SPOILER.
  617. X    IF YOU WANT A REAL CHALLENGE, DON'T READ ANY FURTHER AND TRY
  618. X    TO UNDERSTAND THE PROGRAM VIA THE SOURCE.
  619. X
  620. X
  621. XSelected notes from the author:
  622. X
  623. X    This programs computes and prints Fibonacci numbers by
  624. X    simulating a Turing machine with the proper program.
  625. X    Understanding the C program, i.e., a Turing machine simulator,
  626. X    is only the first and simplest step.  The Turing machine
  627. X    program must be understood, too!  (it is trivial, perhaps even
  628. X    natural to write incredibly obscure Turing programs.)
  629. X
  630. X    If the program is invoked with an operand, the operand is used
  631. X    as the Turing program.  It includes a "trace" facility,
  632. X    subroutine r (commented out for obscurity), to help write and
  633. X    debug Turing programs.  Just the thing for some fun in a Theory
  634. X    of Computation class.
  635. X
  636. X    The Turing machine tape is represented as a doubly linked list
  637. X    of pointers.  The forward and backward links are XOR'd together
  638. X    and stored in one pointer.  If we always keep one of the links
  639. X    on hand, we can recover the other link at any time.  The
  640. X    variable q is the scan head (and a pointer at some tape cell),
  641. X    and p is a "previous" link.  The state of the tape is stored in
  642. X    the low order bit of the pointer.  Since we always allocate an
  643. X    even number of bytes, the low order bit carries no information
  644. X    (see portability below.) Memory representing a tape cell is
  645. X    allocated when the cell is first scanned.  Thus the simulation
  646. X    begins with a tape effectively the size of virtual memory set
  647. X    to all zeros.  Since a header can be added to any Turing
  648. X    program to write initial data and position the scan head, this
  649. X    is little loss of generality.
  650. X
  651. X    The simulated Turing machine has a single tape with either an 1
  652. X    or a 0 in each cell.  The Turing machine language format is a
  653. X    string of three bytes.  The first byte is the current state.
  654. X    The second byte is the next state.  (The last bit of states is
  655. X    ignored, e.g., B and C are the same state, in an attempt to be
  656. X    able to have interesting words in the program.)  The third byte
  657. X    is composed of bits.  Bit 1 (2&byte) is the symbol scanned,
  658. X    i.e. an instruction is selected for state and for a match with
  659. X    the symbol under the scan head.  Bit 2 (4&byte) is the new
  660. X    symbol to be written to the cell.  Bit 3 (8&byte) is the
  661. X    direction to move the scan head: 0 for left and 1 for right.
  662. X    If bit 4 (16&byte) is true, the next character is sent to
  663. X    stdout.  (I added this feature so programs could print
  664. X    results.)
  665. X
  666. X    The Turing machine has next state 'j' when it begins.  The
  667. X    cycle is 1) exit if the state is 'x', 2) find the next
  668. X    instruction (given the state and the character under the scan
  669. X    head).  [The program string is searched forward for the next
  670. X    matching instruction.  If the end of the string is reached, the
  671. X    search begins again at the first of the string.  Thus states
  672. X    can be used as local labels in different places.]  3) change to
  673. X    the next state, 4) print a character if indicated, 5) write the
  674. X    tape symbol, and 6) move the scan head.  The cycle then repeats
  675. X    with step 1.  A call to the trace routine is just before step
  676. X    2, but is commented out.
  677. X
  678. X    The following ROT13'ed text is a quick outline of the actual
  679. X    Turing program:
  680. X
  681. X        Urer vf n dhvpx bhgyvar bs gur Ghevat cebtenz: gur
  682. X        cerivbhf naq pheerag Svobanppv ahzoref ner xrcg va onfr
  683. X        1 sbez jvgu gur pheerag ba gur evtug.  Gur svefg guerr
  684. X        fgrcf frg hc gur svefg gjb ahzoref, 1 naq 1.  Gura
  685. X        [ortvaavat jvgu "@ ("] n znexre bs VVV vf perngrq naq
  686. X        gur pheerag ahzore vf pbcvrq gb gur evtug bs gur
  687. X        znexre.  Gura [ortvaavat jvgu "BI "] gur ahzore vf
  688. X        pbairegrq gb ovanel ol ercrngrq qvivqvat ol 2 yrnivat V
  689. X        sbe erznvaqre 1, naq VV sbe erznvaqre 0.  Arkg
  690. X        [ortvaavat jvgu "JI "] gur ovanel ercerfragngvba vf
  691. X        cevagrq naq vgf flzobyf naq gur znexre ner renfrq.
  692. X        Svanyyl [ortvaavat jvgu "RRa"] gur gjb ahzoref ner
  693. X        nqqrq naq gur pheerag ahzore pbcvrq gb gur yrsg gb
  694. X        orpbzr gur cerivbhf.  Gura gur plpyr ercrngf.
  695. X
  696. X    The program requires that the lowest bit of a pointer to be 0.
  697. X
  698. X    I could have squeezed the program under 1024 bytes without the
  699. X    trace subroutine, but I felt it was important for understanding
  700. X    the program.  Besides it is fun to watch the tape zooming back
  701. X    and forth as the program runs.  A much better debugger or trace
  702. X    could easily be added.
  703. //E*O*F 1989/paul.hint//
  704.  
  705. echo x - 1989/robison.c
  706. sed -e 's/^X//' > "1989/robison.c" << '//E*O*F 1989/robison.c//'
  707. X typedef struct A*B,*(*C)();struct A{C(*d)();B e;}*v(),*b;C n[256];
  708. X# include <stdio.h>
  709. X#define a (d->e)
  710. X#define o (B)printf
  711. X#define X(_){return _;}
  712. X#define Y(_,A)B _(d,e)B d,e;X(A)
  713. X#define Z(P)C P(f,g,h,i)C f,g,h,i;X(P)
  714. X#define c(_)(b=(B)malloc(sizeof(*b)),b->d=_,b->e=d,b)
  715. X#define _(D,E,F,G,H)B D();Y(D/**/f,E)Y(D/**/g,F)Y(D/**/h,G)Y(D/**/i,H)Y(D,(*(*d->d)(D/**/f,D/**/g,D/**/h,D/**/i))(d,e))
  716. XZ(f)
  717. XZ(g)
  718. XZ(h)
  719. XZ(i)
  720. X_(j,d,d,j a,j a)
  721. X_(k,d,c(h),c(h),c(h))
  722. X_(l,c(i),d,c(i),c(i))
  723. X_(m,c(g),c(f),l(m a),k(m a))
  724. X_(p,d,l(m(d)),k(p a),l(m a))
  725. X_(q,l(p(d)),m(d),l a,k(q a))
  726. X_(r,m(d),k(mf a),l(r a),k a)
  727. X_(s,d,e,o("0",s a),o("1",s a))
  728. X_(t,d,p(e),k(t(a,e)),v(k(t(a,e)),e))
  729. X_(u,k(e),l(r(e)),k(v(a,e)),l(v(a,e)))
  730. X_(v,e,r(e),u(e,a),u(q(e),a))
  731. X_(w,o("0"),d,s(d),s(d))
  732. X_(x,(*n[getchar()])(d),o("-1"),w(p(d,o("-"))),xh(d))
  733. X_(y,xf(mg()),v(d,p(yf())),v(d,yf()),t(d,yf()))
  734. X_(z,xf(yf()),(*(*j(d)->d)(w,x))(d),xf(k(d)),xf(l(d)))
  735. Xmain(){
  736. Xn['(']=zf;n['x']=yi;n['-']=yg;
  737. Xn['+']=yh;n['0']=zh;n['1']=zi;
  738. Xn[' ']=xf;n[')']=n['\n']=kf;
  739. Xo("\n",zg(yf()));}
  740. //E*O*F 1989/robison.c//
  741.  
  742. echo x - 1989/robison.hint
  743. sed -e 's/^X//' > "1989/robison.hint" << '//E*O*F 1989/robison.hint//'
  744. XBest minimal use of C: <robison@a.cs.uiuc.edu> Arch D. Robison
  745. X
  746. X    Arch D. Robison
  747. X    University of Illinois
  748. X    1304 W. Springfield Ave.
  749. X    Urbana, IL 
  750. X    61801
  751. X    USA
  752. X
  753. XJudges notes:
  754. X
  755. X    Sites with punch card facilities will be happy to note that
  756. X    the source deck can be re-collated with an ASCII sort.
  757. X
  758. X    Note that this program uses only a small subset of the
  759. X    constructs that the C language supports.
  760. X
  761. XSelected notes from the author:
  762. X
  763. X    This program is a handy picoAPL interpreter written in C--.  It
  764. X    outputs the evaluation of an APL expression from standard
  765. X    input.  Functions are limited to dyadic +,-,x, and unary -;
  766. X    numerals must be binary.  Parentheses may be used for
  767. X    grouping.  For example:
  768. X
  769. X        101x111-100
  770. X
  771. X    prints:
  772. X
  773. X        1111
  774. X
  775. X    That is 5x(7-4) is 15.  (APL groups from right to left.)
  776. X    Extending it to the full APL language should be trivial.
  777. X
  778. X    The C-- language improves the C language by removing superfluous
  779. X    and confusing features: arithmetic, logical operations, shifts,
  780. X    relationals, address-of, and flow control.  In fact, the only 
  781. X    expressions retained are function calls, indirection, array 
  782. X    assignments, the ',' operator, and sizeof.  Despite these
  783. X    restrictions, the C-- program does arithmetic on arbitrarily 
  784. X    large binary numbers.
  785. X
  786. X    To obtain a C-- reference, simply rip out the irrelevant pages 
  787. X    from your K&R C manual.  To obtain a C-- compiler, simply rip
  788. X    out the irrelevant bytes from your cc compiler.
  789. //E*O*F 1989/robison.hint//
  790.  
  791. echo x - 1989/rowmer.c
  792. sed -e 's/^X//' > "1989/rowmer.c" << '//E*O*F 1989/rowmer.c//'
  793. X
  794. X
  795. X                                    char
  796. X                                _3141592654[3141
  797. X      ],__3141[3141];_314159[31415],_3141[31415];main(){register char*
  798. X      _3_141,*_3_1415, *_3__1415; register int _314,_31415,__31415,*_31,
  799. X    _3_14159,__3_1415;*_3141592654=__31415=2,_3141592654[0][_3141592654
  800. X   -1]=1[__3141]=5;__3_1415=1;do{_3_14159=_314=0,__31415++;for( _31415
  801. X  =0;_31415<(3,14-4)*__31415;_31415++)_31415[_3141]=_314159[_31415]= -
  802. X1;_3141[*_314159=_3_14159]=_314;_3_141=_3141592654+__3_1415;_3_1415=
  803. X__3_1415    +__3141;for            (_31415 = 3141-
  804. X       __3_1415  ;            _31415;_31415--
  805. X       ,_3_141 ++,            _3_1415++){_314
  806. X       +=_314<<2 ;            _314<<=1;_314+=
  807. X      *_3_1415;_31             =_314159+_314;
  808. X      if(!(*_31+1)             )* _31 =_314 /
  809. X      __31415,_314             [_3141]=_314 %
  810. X      __31415 ;* (             _3__1415=_3_141
  811. X     )+= *_3_1415              = *_31;while(*
  812. X     _3__1415 >=              31415/3141 ) *
  813. X     _3__1415+= -              10,(*--_3__1415
  814. X    )++;_314=_314              [_3141]; if ( !
  815. X    _3_14159 && *              _3_1415)_3_14159
  816. X    =1,__3_1415 =              3141-_31415;}if(
  817. X    _314+(__31415               >>1)>=__31415 )
  818. X    while ( ++ *               _3_141==3141/314
  819. X       )*_3_141--=0               ;}while(_3_14159
  820. X       ) ; { char *               __3_14= "3.1415";
  821. X       write((3,1),               (--*__3_14,__3_14
  822. X       ),(_3_14159                ++,++_3_14159))+
  823. X      3.1415926; }                for ( _31415 = 1;
  824. X     _31415<3141-                1;_31415++)write(
  825. X    31415% 314-(                3,14),_3141592654[
  826. X  _31415    ] +                   "0123456789","314"
  827. X  [ 3]+1)-_314;                   puts((*_3141592654=0
  828. X,_3141592654))                    ;_314= *"3.141592";}
  829. //E*O*F 1989/rowmer.c//
  830.  
  831. echo x - 1989/rowmer.hint
  832. sed -e 's/^X//' > "1989/rowmer.hint" << '//E*O*F 1989/rowmer.hint//'
  833. XBest layout: <roemer@cs.vu.nl> Roemer B. Lievaart
  834. X
  835. X    Lievaart, Roemer B.
  836. X    VU-Informatica, Amsterdam
  837. X    Marcusstraat 29/2, 
  838. X    NL 1091 TJ Amsterdam
  839. X    Netherlands
  840. X
  841. XJudges notes:
  842. X
  843. X    Do you know what this program does?  If you do, look again,
  844. X    there is more here than meets the PI.
  845. X
  846. XSelected notes from the author:
  847. X
  848. X    Passes lint, but not with the strictest options, for it
  849. X    contains some "null-statements", as well two identifiers
  850. X    which are, if compilers only take 6 characters, the same.  It
  851. X    also uses write(2), so not totally system independent.
  852. X
  853. X    You are very much invited to pass this program through a
  854. X    C-beautifier. (First strip newlines and tabs, if your cb can't
  855. X    do that.)
  856. //E*O*F 1989/rowmer.hint//
  857.  
  858. echo x - 1989/rules
  859. sed -e 's/^X//' > "1989/rules" << '//E*O*F 1989/rules//'
  860. XSubject: 6th International Obfuscated C Code Contest Rules
  861. XNewsgroups: comp.lang.c,comp.unix.wizards
  862. XKeywords: rules,1989,obfuscate,contest,IOCCC
  863. X
  864. X    Obfuscate:  tr.v.  -cated, -cating, -cates.  1. a.  To render obscure.
  865. X        b.  To darken.  2. To confuse:  his emotions obfuscated his
  866. X        judgement.  [LLat. obfuscare, to darken : ob(intensive) +
  867. X        Lat. fuscare, to darken < fuscus, dark.] -obfuscation n.
  868. X        obfuscatory adj.
  869. X
  870. XGOALS OF THE CONTEST:
  871. X
  872. X    * To write the most Obscure/Obfuscated C program under the rules below.
  873. X    * To show what should NOT be done in C programs.
  874. X    * To provide a safe forum for poor C code.  :-)
  875. X
  876. XRULES:
  877. X
  878. X    To help us handle the vast volume of entries, we ask that you
  879. X    follow the rules below.  Sorry for the length, but we need all
  880. X    the help we can get!
  881. X
  882. X    1) Your source MUST be 1536 bytes or less, and it must be a complete
  883. X       program, not just a subroutine.
  884. X
  885. X    2) To help us process your entries, we ask that you submit entries
  886. X       in the following format.  Please be sure to include the --- lines,
  887. X       otherwise our extraction program may skip your entry!
  888. X
  889. X---header items---
  890. Xname:        Your name, of course!
  891. Xorg:        School/Company/Organization
  892. Xemail address:    Email address from a well known site, or in a registered domain
  893. Xpostal address:    Postal address
  894. X        include your country as well
  895. Xenvironment:    Indicate the Hardware 
  896. X        and OS under which your program was tested
  897. Xentry:        5    <number of entries sent so far including this one>
  898. Xremarks:        <see below>
  899. X---how to compile---
  900. XX Give the command(s) needed to compile your program.
  901. XX Follow the same rules as given for the program below except that the
  902. XX command size must be 160 characters or less.
  903. X---program---
  904. XX Place obfuscated source of 1536 characters or less in this section.
  905. XX Add a leading X to each line to avoid problems with mailers.
  906. XX Some mailers don't like files with very long lines.  If your entry contains E
  907. XC    lines longer 80 chars we ask you to form continuation line sets.  To form E
  908. XC    a continuation line set, place an 'E' character at the point of a split E
  909. XC    and place a C (instead of an X) at the beginning of the next line. E
  910. XC    Finally, end the continuation line set as normal.
  911. XX The E\nC's and leading X's will be removed prior to extraction and thus E
  912. XC    they don't contribute toward the source character count.  All other E
  913. XC    characters are considered to be source.  Whitespace after 'X' or 'C' E
  914. XC    and before the 'E' is significant, we added it here for readability.
  915. XX Newlines and tabs each count as 1 character.  Assume 8 character tab stops.
  916. XX If your entry does not end in a newline, leave a final 'E' on the end. E
  917. X---end---
  918. X
  919. X    3) Regarding the header items:
  920. X
  921. X        * Any text outside of the above format will be kept confidential.
  922. X
  923. X        * All header lines are required, but you may use 'anonymous'
  924. X          for any header line other than 'remarks' or 'entry'.
  925. X
  926. X        * In the 'remarks' please include:
  927. X        - what this program does
  928. X        - why you think the program is obfuscated
  929. X        - any other remarks you wish to make
  930. X
  931. X    4) Your entry should be written in common C. (K&R + common extensions)
  932. X       Due to the lack of ANSI C compilers, it is suggested, but not
  933. X       required, that you avoid use of constructs unique to ANSI C.
  934. X
  935. X    5) The program must be of original work.  All programs must be
  936. X       in the public domain.  All copyrighted programs will be rejected.
  937. X
  938. X    6) Entries must be received between 26-Mar-89 0:00 GMT and 
  939. X       26-May-89 0:00 GMT.  Email your entries to:
  940. X       
  941. X        ...!{sun,pacbell,uunet,pyramid,amdahl}!hoptoad!obfuscate
  942. X
  943. X       We will attempt to Email a confirmation of receipt of contest
  944. X       entries, however since Email is not reliable you may not receive it.
  945. X       We regret that we can no longer accept entries via postal mail.
  946. X
  947. X    7) Each person may submit up to 8 entries.  Multiple entries must
  948. X       be sent in separate Email letters.
  949. X    
  950. X    8) Entries that can not be built automatically in a portable makefile 
  951. X       are not allowed.  (e.g., don't use #include "/dev/tty")
  952. X
  953. X
  954. XANNOUNCEMENT OF WINNERS:
  955. X
  956. X    * First announcement will be at the Summer 89 Usenix BOF.
  957. X
  958. X    * Winning entries will be posted in mid June 1989 to 
  959. X      comp.sources.unix as well as news groups where these rules 
  960. X      were posted.  (depending on the judges work load)
  961. X    
  962. X    * Winning entries will be deposited into the uunet archives.
  963. X
  964. X    * An article containing the winning entries will be published
  965. X      in a future issue of the "Micro/Systems Journal".
  966. X
  967. X    * Winners receive international fame and flames!  :-)
  968. X
  969. X
  970. XJUDGING:
  971. X
  972. X    Awards will be given to the best entry in a number of categories.
  973. X    The actual category list will vary depending on the types of entries
  974. X    we receive.  As a guide, consider using the following:
  975. X
  976. X        * The best small one line program
  977. X        * The most obscure algorithm
  978. X        * The strangest source layout
  979. X        * The most useful obfuscated program
  980. X        * The most creatively obfuscated program
  981. X        * Best obfuscated entry smaller than 256 bytes
  982. X        * Best obfuscated entry smaller than 1024 bytes
  983. X        * <anything else so strange that it deserves an award>
  984. X
  985. XPOINTS TO PONDER:
  986. X
  987. X    People are encouraged to examine winners of the previous
  988. X    contests.  A copy of these entries was posted to
  989. X    comp.sources.unix.  Contact the comp.sources.unix moderator, or
  990. X    some archive site (such as uunet).  Keep in mind that rules
  991. X    change from year to year, so some winning entries may not be
  992. X    valid entries this year.  What was unique and novel one year
  993. X    might be 'old' the next year.  In short, use your best judgement.
  994. X
  995. X    We examine each entry on several levels of confusion.  For example
  996. X    each entry is judged when we:
  997. X
  998. X        * look at the original source
  999. X        * run it through:  sed -e ',^#[     ]*define,d' | /lib/cpp
  1000. X        * run it through a C beautifier
  1001. X        * examine the algorithm
  1002. X        * compile and lint it
  1003. X        * execute it
  1004. X    
  1005. X    One line programs are best when they are short, obscure and concise.
  1006. X
  1007. X    We tend to dislike programs that:
  1008. X
  1009. X        * are very hardware specific
  1010. X        * are very OS or Un*x version specific
  1011. X             (index/strchr differences are ok, but 
  1012. X              socket/streams specific code is likely not to be)
  1013. X        * dump core or have compiler warnings
  1014. X             (it is ok only if you warn us in the 'remark' header item)
  1015. X        * won't compile under both BSD or SYS V Un*x
  1016. X        * use an excessively long compile line to get around the
  1017. X             size limit
  1018. X        * are longer than they need to be
  1019. X        * are similar to previous winners
  1020. X        * are similar to previous losers  :-)
  1021. X
  1022. X    Simply abusing #defines or -Dfoo=bar won't go as far as a program
  1023. X    that is more well rounded in confusion.
  1024. X
  1025. X    Unless you are cramped for space, or unless you are entering the 
  1026. X    'best one liner' category, we suggest that you format your program 
  1027. X    in a more creative way than simply forming excessively long lines.
  1028. X
  1029. X    We like programs that:
  1030. X
  1031. X        * are as concise and small as they need to be
  1032. X        * do something quasi-interesting
  1033. X        * pass lint without complaint
  1034. X        * are portable
  1035. X        * are unique or novel in their obfuscation style
  1036. X        * use a number of different types of obfuscation
  1037. X        * make us laugh and/or throw up  :-)
  1038. X
  1039. X    Some types of programs can't excel in some areas.  We try to account
  1040. X    for this by giving awards to programs in a number of areas.  Of course,
  1041. X    your program doesn't have to excel in all areas, but doing well in
  1042. X    several helps.
  1043. X
  1044. X    Be creative!
  1045. X
  1046. X    The Judging will be done by Landon Noll and Larry Bassel.  If you have
  1047. X    any QUESTIONS or COMMENTS, please feel free to send them to:
  1048. X
  1049. X        ...!{sun,pacbell,uunet,pyramid,amdahl}!hoptoad!judges
  1050. X        judges@toad.com
  1051. X
  1052. X    however contest entries should be sent to: 
  1053. X    
  1054. X        ...!{sun,pacbell,uunet,pyramid,amdahl}!hoptoad!obfuscate
  1055. X        obfuscate@toad.com
  1056. X
  1057. X
  1058. Xchongo <Landon Curt Noll> /\cc/\      hoptoad!chongo
  1059. XLarry Bassel                  {amdahl,ucbvax,cbosgd}|sun!lab
  1060. X
  1061. Xp.s. The 1989 contest is being dedicated to the                 |\_.^
  1062. X     brain that was removed from Bill the Cat.                 (@ o)
  1063. X                               *Ackpt!*   {:} 
  1064. X                                       U
  1065. //E*O*F 1989/rules//
  1066.  
  1067. echo x - 1989/tromp.bsd.c
  1068. sed -e 's/^X//' > "1989/tromp.bsd.c" << '//E*O*F 1989/tromp.bsd.c//'
  1069. Xlong h[4];t(){h[3]-=h[3]/3000;setitimer(0,h,0);}c,d,l,v[]={(int)t,0,2},w,s,I,K
  1070. X=0,i=276,j,k,q[276],Q[276],*n=q,*m,x=17,f[]={7,-13,-12,1,8,-11,-12,-1,9,-1,1,
  1071. X12,3,-13,-12,-1,12,-1,11,1,15,-1,13,1,18,-1,1,2,0,-12,-1,11,1,-12,1,13,10,-12,
  1072. X1,12,11,-12,-1,1,2,-12,-1,12,13,-12,12,13,14,-11,-1,1,4,-13,-12,12,16,-11,-12,
  1073. X12,17,-13,1,-1,5,-12,12,11,6,-12,12,24};u(){for(i=11;++i<264;)if((k=q[i])-Q[i]
  1074. X){Q[i]=k;if(i-++I||i%12<1)printf("\033[%d;%dH",(I=i)/12,i%12*2+28);printf(
  1075. X"\033[%dm  "+(K-k?0:5),k);K=k;}Q[263]=c=getchar();}G(b){for(i=4;i--;)if(q[i?b+
  1076. Xn[i]:b])return 0;return 1;}g(b){for(i=4;i--;q[i?x+n[i]:x]=b);}main(C,V,a)char*
  1077. X*V,*a;{h[3]=1000000/(l=C>1?atoi(V[1]):2);for(a=C>2?V[2]:"jkl pq";i;i--)*n++=i<
  1078. X25||i%12<2?7:0;srand(getpid());system("stty cbreak -echo stop u");sigvec(14,v,
  1079. X0);t();puts("\033[H\033[J");for(n=f+rand()%7*4;;g(7),u(),g(0)){if(c<0){if(G(x+
  1080. X12))x+=12;else{g(7);++w;for(j=0;j<252;j=12*(j/12+1))for(;q[++j];)if(j%12==10){
  1081. Xfor(;j%12;q[j--]=0);u();for(;--j;q[j+12]=q[j]);u();}n=f+rand()%7*4;G(x=17)||(c
  1082. X=a[5]);}}if(c==*a)G(--x)||++x;if(c==a[1])n=f+4**(m=n),G(x)||(n=m);if(c==a[2])G
  1083. X(++x)||--x;if(c==a[3])for(;G(x+12);++w)x+=12;if(c==a[4]||c==a[5]){s=sigblock(
  1084. X8192);printf("\033[H\033[J\033[0m%d\n",w);if(c==a[5])break;for(j=264;j--;Q[j]=
  1085. X0);while(getchar()-a[4]);puts("\033[H\033[J\033[7m");sigsetmask(s);}}d=popen(
  1086. X"stty -cbreak echo stop \023;cat - HI|sort -rn|head -20>/tmp/$$;mv /tmp/$$ HI\
  1087. X;cat HI","w");fprintf(d,"%4d on level %1d by %s\n",w,l,getlogin());pclose(d);}
  1088. //E*O*F 1989/tromp.bsd.c//
  1089.  
  1090. echo x - 1989/tromp.hint
  1091. sed -e 's/^X//' > "1989/tromp.hint" << '//E*O*F 1989/tromp.hint//'
  1092. XBest game: <tromp@piring.cwi.nl> John Tromp
  1093. X
  1094. X    John Tromp
  1095. X    Centre for Mathematics and Computer Science (CWI)
  1096. X    Oetgensstraat 7
  1097. X    1701CK Heerhugowaard
  1098. X    Netherlands
  1099. X
  1100. XJudges notes:
  1101. X
  1102. X    This is a character terminal version of the TETRIS program. 
  1103. X    It runs on a VT100 compatible terminal or emulator.  It is 
  1104. X    best used at 4800 baud or more.
  1105. X    
  1106. X    Usage:
  1107. X
  1108. X        tromp [drops_per_sec  [cmd_string]]
  1109. X        tromp.s5 [1  [cmd_string]]
  1110. X    
  1111. X    By default, "drops_per_sec", the number of times an object
  1112. X    will drop in a second, is 2.  The default "cmd_string" is
  1113. X    "jkl pq".  The first 6 characters of "cmd_string" relate
  1114. X    to the following 6 game commands:
  1115. X
  1116. X        j - left
  1117. X        k - rotate
  1118. X        l - right
  1119. X      <space> - drop
  1120. X        p - pause
  1121. X        q - quit
  1122. X    
  1123. X    Specifying "cmd_string" allows one to re-define the commands.
  1124. X    The pause command pauses the game, clears the screen and
  1125. X    prints the current score.  To un-pause, type the pause
  1126. X    character again, which by default is "p".
  1127. X
  1128. X    This original program requires a BSD-style interval timer and
  1129. X    and new BSD signal interface.  If you are using System V.3
  1130. X    or earlier, for example, you will need to make "tromp.s5" 
  1131. X    instead of "tromp".  You can change the default make rule 
  1132. X    by changing "tromp" to "tromp.s5" in the "WINNERS=..." line
  1133. X    of the Makefile.
  1134. X
  1135. X    The "tromp.s5" version is not as functional as "tromp".  
  1136. X    The "drops_per_sec" is ignored and defaults to 1.  The level 
  1137. X    is always reported as 0.
  1138. X
  1139. X    As was stated last year, we are likely to be more strict about
  1140. X    portability in the future.  [ We mean it this time :-) ]
  1141. X
  1142. XSelected notes from the author:
  1143. X
  1144. X    This program plays the familiar game of `TETRIS' with the
  1145. X    following features:
  1146. X
  1147. X        * outputs vt100-like escape-sequences for cursor 
  1148. X          positioning and normal/reverse video in curses 
  1149. X          like fashion (minimal output for screen updates)
  1150. X
  1151. X        * continuously increasing speed (except in pause)
  1152. X
  1153. X        * start speed selectable by giving n as first argument, 
  1154. X          where n is the number of drops per second (default=2).
  1155. X
  1156. X        * controls also selectable by giving as the second argument 
  1157. X          a string of 6 characters.  By default they are "jkl pq".
  1158. X
  1159. X        * screen is blanked during the pause and the score is shown
  1160. X
  1161. X        * maintains a high-score table
  1162. X
  1163. X    Giving a full path name for the table will result in a
  1164. X    system-wide hiscore allowing a competition between users.
  1165. X
  1166. XThe author provided us with the following notes and new version of
  1167. Xthe program:
  1168. X
  1169. X    Here is a somewhat improved version of my tetris entry.  All the 
  1170. X    changes are in the popen() at the end.  Formerly a move was done 
  1171. X    to the HI score file which is not permitted for other users. Now 
  1172. X    other users can change the HI score file.  The extra option -m is 
  1173. X    passed to sort, so that it knows that its input files are already 
  1174. X    sorted.  The -o output option of sort is used instead of a 
  1175. X    temporary file.
  1176. X
  1177. X    You may also want to consider giving just the raw option to stty
  1178. X    at the start and -raw at the end. This further reduces the size of
  1179. X    the program, but has the possible disadvantage that the program
  1180. X    can only by stopped by 'q' or by the `kill -9' command.
  1181. X
  1182. Xlong h[4];t(){h[3]-=h[3]/3000;setitimer(0,h,0);}c,d,l,v[]={(int)t,0,2},w,s,I,K
  1183. X=0,i=276,j,k,q[276],Q[276],*n=q,*m,x=17,f[]={7,-13,-12,1,8,-11,-12,-1,9,-1,1,
  1184. X12,3,-13,-12,-1,12,-1,11,1,15,-1,13,1,18,-1,1,2,0,-12,-1,11,1,-12,1,13,10,-12,
  1185. X1,12,11,-12,-1,1,2,-12,-1,12,13,-12,12,13,14,-11,-1,1,4,-13,-12,12,16,-11,-12,
  1186. X12,17,-13,1,-1,5,-12,12,11,6,-12,12,24};u(){for(i=11;++i<264;)if((k=q[i])-Q[i]
  1187. X){Q[i]=k;if(i-++I||i%12<1)printf("\033[%d;%dH",(I=i)/12,i%12*2+28);printf(
  1188. X"\033[%dm  "+(K-k?0:5),k);K=k;}Q[263]=c=getchar();}G(b){for(i=4;i--;)if(q[i?b+
  1189. Xn[i]:b])return 0;return 1;}g(b){for(i=4;i--;q[i?x+n[i]:x]=b);}main(C,V,a)char*
  1190. X*V,*a;{h[3]=1000000/(l=C>1?atoi(V[1]):2);for(a=C>2?V[2]:"jkl pq";i;i--)*n++=i<
  1191. X25||i%12<2?7:0;srand(getpid());system("stty cbreak -echo stop u");sigvec(14,v,
  1192. X0);t();puts("\033[H\033[J");for(n=f+rand()%7*4;;g(7),u(),g(0)){if(c<0){if(G(x+
  1193. X12))x+=12;else{g(7);++w;for(j=0;j<252;j=12*(j/12+1))for(;q[++j];)if(j%12==10){
  1194. Xfor(;j%12;q[j--]=0);u();for(;--j;q[j+12]=q[j]);u();}n=f+rand()%7*4;G(x=17)||(c
  1195. X=a[5]);}}if(c==*a)G(--x)||++x;if(c==a[1])n=f+4**(m=n),G(x)||(n=m);if(c==a[2])G
  1196. X(++x)||--x;if(c==a[3])for(;G(x+12);++w)x+=12;if(c==a[4]||c==a[5]){s=sigblock(
  1197. X8192);printf("\033[H\033[J\033[0m%d\n",w);if(c==a[5])break;for(j=264;j--;Q[j]=
  1198. X0);while(getchar()-a[4]);puts("\033[H\033[J\033[7m");sigsetmask(s);}}d=popen(
  1199. X"stty -cbreak echo stop \023;sort -mnr -o HI - HI;cat HI","w");fprintf(d,
  1200. X"%4d from level %1d by %s\n",w,l,getlogin());pclose(d);}
  1201. //E*O*F 1989/tromp.hint//
  1202.  
  1203. echo x - 1989/tromp.s5.c
  1204. sed -e 's/^X//' > "1989/tromp.s5.c" << '//E*O*F 1989/tromp.s5.c//'
  1205. Xlong h[4];E[80],S;t(){signal(14,t);if(S)longjmp(E,1);}c,d,l,v[]={(int)t,0,2},
  1206. Xw,s,I,K=0,i=276,j,k,q[276],Q[276],*n=q,*m,x=17,f[]={7,-13,-12,1,8,-11,-12,-1,9
  1207. X,-1,1,12,3,-13,-12,-1,12,-1,11,1,15,-1,13,1,18,-1,1,2,0,-12,-1,11,1,-12,1,13,
  1208. X10,-12,1,12,11,-12,-1,1,2,-12,-1,12,13,-12,12,13,14,-11,-1,1,4,-13,-12,12,16,-
  1209. X11,-12,12,17,-13,1,-1,5,-12,12,11,6,-12,12,24};u(){for(i=11;++i<264;)if((k=q[i
  1210. X])-Q[i]){Q[i]=k;if(i-++I||i%12<1)printf("\033[%d;%dH",(I=i)/12,i%12*2+28);
  1211. Xprintf("\033[%dm  "+(K-k?0:5),k);K=k;}alarm(1);Q[263]=c=((S=1)&&!setjmp(E))?
  1212. Xgetchar():-1;alarm(0);}G(b){for(i=4;i--;)if(q[i?b+n[i]:b])return 0;return 1;}g
  1213. X(b){for(i=4;i--;q[i?x+n[i]:x]=b);}main(C,V,a)char**V,*a;{for(a=C>2?V[2]:
  1214. X"jkl pq";i;i--)*n++=i<25||i%12<2?7:0;srand(getpid());system("stty raw -echo");
  1215. Xsignal(14,t);t();puts("\033[H\033[J");for(n=f+rand()%7*4;;g(7),u(),g(0)){if(c<
  1216. X0){if(G(x+12))x+=12;else{g(7);++w;for(j=0;j<252;j=12*(j/12+1))for(;q[++j];)if(
  1217. Xj%12==10){for(;j%12;q[j--]=0);u();for(;--j;q[j+12]=q[j]);u();}n=f+rand()%7*4;G
  1218. X(x=17)||(c=a[5]);}}if(c==*a)G(--x)||++x;if(c==a[1])n=f+4**(m=n),G(x)||(n=m);if
  1219. X(c==a[2])G(++x)||--x;if(c==a[3])for(;G(x+12);++w)x+=12;if(c==a[4]||c==a[5]){
  1220. Xprintf("\033[H\033[J\033[0m%d\n",w);if(c==a[5])break;for(j=264;j--;Q[j]=0);
  1221. Xwhile(getchar()-a[4]);puts("\033[H\033[J\033[7m");}}system("stty cooked echo")
  1222. X;d=popen("cat - HI|sort -rn|sed -n 1,20p>/tmp/$$;mv /tmp/$$ HI;cat HI","w");
  1223. Xfprintf(d,"%4d on level %1d by %s\n",w,l,getlogin());pclose(d);}
  1224. //E*O*F 1989/tromp.s5.c//
  1225.  
  1226. echo x - 1989/vanb.c
  1227. sed -e 's/^X//' > "1989/vanb.c" << '//E*O*F 1989/vanb.c//'
  1228. Xmain(Q,O)char**O;{if(--Q){main(Q,O);O[Q][0]^=0X80;for(O[0][0]=0;O[++O[0][0]]!=0;)if(O[O[0][0]][0]>0)puts(O[O[0][0]]);puts("----------");main(Q,O);}}
  1229. //E*O*F 1989/vanb.c//
  1230.  
  1231. echo x - 1989/vanb.hint
  1232. sed -e 's/^X//' > "1989/vanb.hint" << '//E*O*F 1989/vanb.hint//'
  1233. XBest one liner: <...!{decvax|akgua}!ucf-cs!vanb> David Van Brackle
  1234. X
  1235. X    David Van Brackle
  1236. X    Department of Computer Science
  1237. X    University of Central Florida
  1238. X    Orlando, Florida 
  1239. X    32816
  1240. X    USA 
  1241. X
  1242. XJudges notes:
  1243. X
  1244. X    This program computes all proper subsets of the set of
  1245. X    arguments passed to it.  Each subset is printed with one 
  1246. X    element on each line, followed by a line of ten dashes.
  1247. X
  1248. X    Try:
  1249. X
  1250. X        vanb the rug gary lent    
  1251. X        vanb unix is better than os/2
  1252. X
  1253. XSelected notes from the author:
  1254. X
  1255. X    The program has the following charming and possibly 
  1256. X    non-portable features:
  1257. X
  1258. X        * It has no local or global variables, 
  1259. X          only the command-line parameters.
  1260. X
  1261. X        * It calls main recursively.
  1262. X
  1263. X            * It alters the command-line parameters.
  1264. X
  1265. X            * It uses the fact that if the high bit is set in a character
  1266. X              variable, the value is negative.
  1267. //E*O*F 1989/vanb.hint//
  1268.  
  1269. echo x - 1989/westley.c
  1270. sed -e 's/^X//' > "1989/westley.c" << '//E*O*F 1989/westley.c//'
  1271. X
  1272. X/**//*/};)/**/main(/*//**/tang       ,gnat/**//*/,ABBA~,0-0(avnz;)0-0,tang,raeN
  1273. X,ABBA(niam&&)))2-]--tang-[kri      - =raeN(&&0<)/*clerk*/,noon,raeN){(!tang&&
  1274. Xnoon!=-1&&(gnat&2)&&((raeN&&(    getchar(noon+0)))||(1-raeN&&(trgpune(noon
  1275. X)))))||tang&&znva(/*//**/tang   ,tang,tang/**|**//*/((||)))0(enupgrt=raeN
  1276. X(&&tang!(||)))0(rahcteg=raeN(  &&1==tang((&&1-^)gnat=raeN(;;;)tang,gnat
  1277. X,ABBA,0(avnz;)gnat:46+]552&)191+gnat([kri?0>]652%)191+gnat([kri=gnat
  1278. X(&&)1-^gnat(&&)1& ABBA(!;)raeN,tang,gnat,ABBA(avnz&&0>ABBA{)raeN
  1279. X,/**/);}znva(/*//**/tang,gnat,ABBA/**//*/(niam;}1-,78-,611-,321
  1280. X-,321-,001-,64-,43-,801-,001-,301-,321-,511-,53-,54,44,34,24
  1281. X,14,04,93,83,73,63,53,43,33,85,75,65,55,45,35,25,15,05,94,84
  1282. X,74,64,0,0,0,0,0,0,/**/){ABBA='N'==65;(ABBA&&(gnat=trgpune
  1283. X(0)))||(!ABBA&&(gnat=getchar(0-0)));(--tang&1)&&(gnat='n'<=
  1284. Xgnat&&gnat<='z'||'a'<=gnat&&gnat<='m'||'N'<=gnat&&gnat<='Z'
  1285. X||'A'<=gnat&&gnat<='M'?(((gnat&/*//**/31/**//*/,21,11,01,9,8
  1286. X,7,6,5,4,3,2,1,62,52,42,/**/)+12)%26)+(gnat&/*//**/32/**//*/,
  1287. X22,12,02,91,81,71,61,51,41{=]652[kri};)/*pry*/)+65:gnat);main
  1288. X(/*//**\**/tang^tang/**//*/,/*       */,~/*//*-*/tang,gnat,ABBA-
  1289. X0/**//*/(niam&&ABBA||))))tang(       rahcteg&&1-1=<enrA(||))tang(
  1290. Xenupgrt&&1==enrA((&&)2&gnat(&&         )1-^tang(&&ABBA!(;)85- =tang
  1291. X(&&)'a\'=gnat(&&)1-==gnat(&&)4          ==ABBA(&&tang!;))))0(enupgrt=
  1292. X gnat(&&)tang!((||)))0(rahcteg        =gnat(&&tang((&&ABBA;;)1-'A'=!
  1293. X'Z'=tang(&&ABBA{)enrA/***/);gnat    ^-1&&znva(tang+1,gnat,1+gnat); 
  1294. X main(ABBA&2/*//*\\**/,tang,gnat    ,ABBA/**//*/(avnz/**/);}/*//**/
  1295. //E*O*F 1989/westley.c//
  1296.  
  1297. echo x - 1989/westley.hint
  1298. sed -e 's/^X//' > "1989/westley.hint" << '//E*O*F 1989/westley.hint//'
  1299. XMost algorithms in one program: <westley@starfire> Merlyn LeRoy (Brian Westley)
  1300. X
  1301. X    Merlyn LeRoy (Brian Westley)
  1302. X    Starfire Consulting
  1303. X    1026 Blair Ave.
  1304. X    St. Paul, MN  
  1305. X    55104  
  1306. X    USA
  1307. X
  1308. XJudges notes:
  1309. X
  1310. X    There is a secret way to get ONE of the versions to print out
  1311. X    "Hello, world!\n".  Can you find how to do it?
  1312. X
  1313. X    Try the following commands:
  1314. X
  1315. X        westley < westley.c > ver0.c
  1316. X        westley 1 < westley.c > ver1.c
  1317. X        westley 1 2 < westley.c > ver2.c
  1318. X        westley 1 2 3 < westley.c > ver3.c
  1319. X    
  1320. X    Try compiling and running the 4 resulting programs.
  1321. X
  1322. XSelected notes from the author:
  1323. X
  1324. X    This is a filter.  If it is run with no arguments, it copies
  1325. X    stdin to stdout.  With one argument, it ROT13's stdin to
  1326. X    stdout.  With two arguments, it reverses stdin to stdout.  With
  1327. X    three arguments, it does both.  It requires the ASCII character
  1328. X    set, with all characters being in 0..255, and EOF must be -1.
  1329. X    Also requires two's complement (I think).
  1330. X
  1331. X    The source code will run if ROT13'ed and/or reversed, using a
  1332. X    different algorithm for each version (hereafter referred to as
  1333. X    ver0 (original), ver1 (ROT13), ver2 (reversed), and ver3 
  1334. X    (ROT13 and reversed)).
  1335. X
  1336. X    When compiling these versions, one needs to define 'trgpune'
  1337. X    in the compile line.  Example:
  1338. X
  1339. X        cc -Dtrgpune=putchar ver3.c -o ver3
  1340. X
  1341. X    "trgpune" is the ROT13 of getchar(), so getchar() and putchar()
  1342. X    are exchanged in the ROT13 counterpart.  It is easy to see that
  1343. X    this is unavoidable.  I must have a #define for a library
  1344. X    function; otherwise I would have an unidentifed extern for the
  1345. X    ROT13 version.  If I then define this function, it won't link
  1346. X    in the library version for the ORIGINAL code, since my
  1347. X    definition will supercede the library function.  Hence, the
  1348. X    compiler option gives me putchar(), and allows me to use
  1349. X    getchar().  I pass a dummy argument to getchar() to eliminate
  1350. X    "variable number of args" from lint (unless it checks against
  1351. X    the library).  Otherwise, all versions lint reasonably (main
  1352. X    returns random value & constant in conditional context [when I
  1353. X    check for ROT13 version] is all it complains about).
  1354. X
  1355. X    ver0 and ver1 use a range check and a calculation to do ROT13,
  1356. X    while ver2 and ver3 use table lookup.  All versions contain
  1357. X    main() and it's ROT13 fn, znva().  ver0/ver1 [ver2/ver3] are
  1358. X    (of course) syntactically identical, since the syntax is in the
  1359. X    non-alphabetic characters.  However, since one program starts
  1360. X    at main() while it's ROT13 counterpart starts at znva(), znva()
  1361. X    calls main (znva() is also used for output).
  1362. X
  1363. X    All versions use recursion to work.  If the program is NOT
  1364. X    reversing it's output, it prints out the (possibly ROT13'd)
  1365. X    character before recursing, otherwise it prints it out
  1366. X    afterward (or doesn't recurse at all when EOF is reached).
  1367. X    Since most of this code is identical, it is put into znva() and
  1368. X    called with a first parameter of 0 as a flag (as "main()", it's
  1369. X    first argument (argc) must be at least one).
  1370. X
  1371. X    I can't use any flow control.  If I used if(), I would have a
  1372. X    function vs() to define in the ROT13 version.  But a function
  1373. X    called vs() turns into a function called if() in the original,
  1374. X    so it can't be done.  Therefore, I do:
  1375. X
  1376. X        expr1 && expr2 && (expr3=etc);
  1377. X
  1378. X    which is the same as:
  1379. X
  1380. X         if (expr1 && expr2) expr3=etc;
  1381. X
  1382. X    A/UX on the Macintosh doesn't get this right; it evaluates ALL
  1383. X    expressions if they aren't in an assignment or conditional
  1384. X    statement.  This might warrant a warning, since other compilers
  1385. X    may do this.  I found MANY compilers botched:
  1386. X
  1387. X        expr1 && (expr2,expr3);
  1388. X
  1389. X    expr2 was OFTEN evaluated even if expr1 was false.  I removed
  1390. X    such statements to make it more portable.
  1391. X
  1392. X    The variable names are worth noting:
  1393. X
  1394. X         'irk' and  'vex' are ROT13 pairs and are synonyms.
  1395. X        'Near' and 'Arne' are ROT13 pairs and are anagrams.
  1396. X        'NOON' and 'ABBA' are ROT13 pairs and are palindromes.
  1397. X        'tang' and 'gnat' are both ROT13 and palindrome pairs!
  1398. X
  1399. X    Normally (!), a reversible C program is done thus:
  1400. X
  1401. X        /**/ forward code /*/ edoc drawkcab /**/
  1402. X
  1403. X    If your compiler nests comments, it will get this wrong.
  1404. X    However, I have made some bits of the code palindromic,
  1405. X    (or different, but reversible) so it is more like:
  1406. X
  1407. X        /**/forward/*//**/ palindromic /**//*/drawkcab/**/
  1408. X
  1409. X    The code can therefore be interlaced.  There are eight
  1410. X    such palindromic bits.  You can find them within the
  1411. X    /*//**/   /**//*/ pairs.
  1412. X
  1413. X    The body of the code of ver0 and ver1 is a large lumpy 'K' (for
  1414. X    Kernighan); the code of ver2 and ver3 is a flat-topped and
  1415. X    lumpier 'R' (for Ritchie).  Judicious use of spaces and tabs
  1416. X    helped here.  It barely fits on an 80x24 screen.  Squint.  Note
  1417. X    that the code must start with a blank line, or the reversed version
  1418. X    will lack a terminating newline.
  1419. //E*O*F 1989/westley.hint//
  1420.  
  1421. echo Possible errors detected by \'wc\' [hopefully none]:
  1422. temp=/tmp/shar$$
  1423. trap "rm -f $temp; exit" 0 1 2 3 15
  1424. cat > $temp <<\!!!
  1425.      83    283   1841 Makefile
  1426.      26    224   1317 README
  1427.      19     77    729 fubar.c
  1428.      54    293   1808 fubar.hint
  1429.      18     75    716 fubar.orig.c
  1430.      19     55    258 fubar.orig.sh
  1431.      19     54    264 fubar.sh
  1432.       1      2     25 jar.1.c
  1433.      34    154    973 jar.1.hint
  1434.       1      2     24 jar.1.orig.c
  1435.       8     18    113 jar.1.orig.sh
  1436.       8     18     88 jar.1.sh
  1437.      44    120   1465 jar.2.c
  1438.      65    379   2328 jar.2.hint
  1439.      21     57    678 ovdluhe.c
  1440.      39    224   1426 ovdluhe.hint
  1441.      35     74   1149 paul.c
  1442.     103    828   4708 paul.hint
  1443.      33     69   1023 robison.c
  1444.      45    217   1418 robison.hint
  1445.      36    110   1454 rowmer.c
  1446.      23    104    673 rowmer.hint
  1447.     205   1284   7848 rules
  1448.      19     44   1494 tromp.bsd.c
  1449.     109    548   4553 tromp.hint
  1450.      19     41   1466 tromp.s5.c
  1451.       1      1    149 vanb.c
  1452.      34    125    846 vanb.hint
  1453.      24     38   1517 westley.c
  1454.     120    764   4671 westley.hint
  1455.    1265   6282  47022 total
  1456. !!!
  1457. wc 1989/Makefile 1989/README 1989/fubar.c 1989/fubar.hint 1989/fubar.orig.c \
  1458. 1989/fubar.orig.sh 1989/fubar.sh 1989/jar.1.c 1989/jar.1.hint \
  1459. 1989/jar.1.orig.c 1989/jar.1.orig.sh 1989/jar.1.sh 1989/jar.2.c \
  1460. 1989/jar.2.hint 1989/ovdluhe.c 1989/ovdluhe.hint 1989/paul.c 1989/paul.hint \
  1461. 1989/robison.c 1989/robison.hint 1989/rowmer.c 1989/rowmer.hint 1989/rules \
  1462. 1989/tromp.bsd.c 1989/tromp.hint 1989/tromp.s5.c 1989/vanb.c 1989/vanb.hint \
  1463. 1989/westley.c 1989/westley.hint | sed 's=[^ ]*/==' | diff -b $temp -
  1464. exit 0
  1465.