Fix 1991/dds

This was a fun one! There were up to three segfaults fixed and with
clang the generated file could not be compiled. The latter part was
fixed with (unfortunately) something of a hack. I explain below and in
the README.md how to change that part to use just cc if you have gcc
(macOS gcc is actually clang).

The first segfault which was always triggered was due to the code

     *q>' '&&(*q)--;

This seems odd at first glance but it's pointing to 's' which was
read-only memory as a char *s.  It's now a char s[]. The second and
third segfaults were caused if a file was not specified (or it the one
specified did not exist or couldn't be opened for some reason) and if
the output file could not be opened for writing. The allowing the
generated code to compile with clang is something of a hack
unfortunately. The code return system(q-6); ended up doing return
system("cc a.c"); but depending on the compiler this would trigger
errors due to no function prototype specified and also a case where
main() had a return; without any return value. Because the string s
is complicated and because I did not want to inadvertently mess
something up I changed that code to system("make a"); and then added
the right rule to the Makefile. Thus you now need both make and cc.
If you use gcc you may change the system() call to what was given in
this description to get a more authentic feel. If you do this you must
then run ./a.out not ./a!
This commit is contained in:
Cody Boone Ferguson committed 2023-03-27 12:30:04 -07:00
1 parent 93561d7704
commit 56b31286d1
3 files changed
+34 -10

No files matched your search

+5 -1
View File
@@ -62,7 +62,7 @@ CDEFINE=
# Include files that are needed to compile
#
CINCLUDE=
CINCLUDE= -include stdio.h
# Optimization
#
@@ -80,6 +80,7 @@ LIBS=
#
CC= cc
CSILENCE= -Wno-implicit-function-declaration
# Compiler add-ons or replacements for clang only
#
ifeq ($(CC),clang)
@@ -131,6 +132,9 @@ all: data ${TARGET}
${PROG}: ${PROG}.c
${CC} ${CFLAGS} $< -o $@ ${LIBS}
a: a.c
${CC} ${CFLAGS} -Wno-return-type $< -o $@ ${LIBS}
# alternative executable
#
alt: data ${ALT_TARGET}
+23 -3
View File
@@ -14,7 +14,27 @@
### To run
./dds basic_program
./a.out
./a
[Cody Boone Ferguson](/winners.html#Cody_Boone_Ferguson) fixed some segfaults in
this entry as well as making it so `a` (was `a.out`, see below) can be generated
(as in the program did not work, at least with clang). The first segfault which
was always triggered was due to the code `*q>' '&&(*q)--;`. This seems odd at
first glance but it's pointing to `s` which was read-only memory as a `char *s`.
It's now a `char s[]`. The second and third segfaults were caused if a file was
not specified (or it the one specified did not exist or couldn't be opened for
some reason) and if the output file could not be opened for writing. The
allowing the generated code to compile with clang is something of a hack
unfortunately. The code `return system(q-6);` ended up doing `return system("cc
a.c");` but depending on the compiler this would trigger errors due to no
function prototype specified and also a case where main() had a `return;`
without any return value. Because the string `s` is complicated and because Cody
did not want to inadvertently mess something up he changed that code to
`system("make a");` and then added the right rule to the Makefile. Thus you now
need both `make` and `cc`. If you use gcc you may change the system() call to
what was given in this description to get a more authentic feel. If you do this
you must then run `./a.out` not `./a`! Thank you Cody for your assistance!
## Judges' comments
@@ -24,8 +44,8 @@ Make and run as follows:
For example, the author suggests trying:
dds LANDER.BAS
a.out
./dds LANDER.BAS
./a
Notice that a file a.c has been generated. Can you tell how a.c was
produced? How does a.c relate to LANDER.BAS?
+6 -6
View File
@@ -1,7 +1,7 @@
#include <stdio.h>
#define Q r=R[*p++-'0'];while(
#define B ;break;case
char*s="Qjou!s\\311^-g\\311^-n\\311^-c\\::^-q-ma%mO1JBHm%BQ-aP1J[O1HB%[Q<nbj\
char s[]="Qjou!s\\311^-g\\311^-n\\311^-c\\::^-q-ma%mO1JBHm%BQ-aP1J[O1HB%[Q<nbj\
o)*|gps)<<*txjudi)m*|aQdbtf!::::;sfuvso<aQefgbvmu;aQ<m,,a%CQ<csfbla%bQ<aN2!Q\
\ndbtf!aP2Q;m>aP2Q<a%!D12J!JGJHJOJQJFJSJJJMHS%HD12D12N3!N4\nJUJT%UQm>aP4HC%T\
Qs\\q,,^>m,2<m>aP4HC%SD12N1\nJNQm>s\\..q^aHC%NHb%GN1!D32P3%RN1UP1D12JPQUaP1H\
@@ -10,8 +10,8 @@ R%PN4\nQ<g\\(aP3Q(^>aP2Q,2<n\\(aP3Q(^>aP4Hb%OD12D12N2!N3\nJVP3Q,,<jg)aP3Q=>n\
aP1Q*aHb%FN1\nQm>::::aHC%VP3Q>bupj)hfut)c**aHb%JD12JON1!Qjg)a%LN1UP1D12JIQUa\
P1HL%IQ*m>aN2!N2\nP2Q<fmtf!m,,aHC%MN1!N2>P2Q>aN2\nP2Hbdd!b/d";int k;char R[4][99]
;main(c,v)char**v;{char*p,*r,*q;for(q=s;*q;q++)*q>' '&&(*q)--;{FILE*i=fopen(v
[1],"r"),*o=fopen(q-3,"w");for(p=s;;p++)switch(*p++){B'M':Q(k=fgetc(i))!=EOF
&&k!=*p)*r++=k;if(k==EOF){fputs("}}\n",o);fclose(o);return system(q-6);}*r=0
B'P':while(*p!='`')fputc(*p++,o)B'O':Q*r)fputc(*r++,o);p--B'C':k=0;Q k<*p-'0'
)(*r++=fgetc(i),k++);*r=0 B'I':k= *p;if(**R==k)goto G B'G':k= *p;G:p=s;while(
*p!='$'||p[1]!= k)p++;p++B'N':R[*p-'0'][0]++;}}}
[1],"r"),*o=fopen(q-3,"w");if(!i||!o)return 1;for(p=s;;p++)switch(*p++){B'M':
Q(k=fgetc(i))!=EOF&&k!=*p)*r++=k;if(k==EOF){fputs("}}\n",o);fclose(o);return
system("make a");}*r=0 B'P':while(*p!='`')fputc(*p++,o)B'O':Q*r)fputc(*r++,o);
p--B'C':k=0;Q k<*p-'0')(*r++=fgetc(i),k++);*r=0 B'I':k= *p;if(**R==k)goto G
B'G':k= *p;G:p=s;while(*p!='$'||p[1]!= k)p++;p++B'N':R[*p-'0'][0]++;}}}