Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.c > #101235 > unrolled thread
| Started by | BartC <bc@freeuk.com> |
|---|---|
| First post | 2017-01-07 18:35 +0000 |
| Last post | 2017-01-10 11:28 +0000 |
| Articles | 20 on this page of 66 — 14 participants |
Back to article view | Back to comp.lang.c
Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 18:35 +0000
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-01-07 11:23 -0800
Re: Macro Expansion Ben Bacarisse <ben.usenet@bsb.me.uk> - 2017-01-07 21:28 +0000
Re: Macro Expansion Siri Cruise <chine.bleu@yahoo.com> - 2017-01-07 11:45 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 20:16 +0000
Re: Macro Expansion Siri Cruise <chine.bleu@yahoo.com> - 2017-01-07 12:23 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 20:31 +0000
Re: Macro Expansion Siri Cruise <chine.bleu@yahoo.com> - 2017-01-07 12:42 -0800
Re: Macro Expansion Ian Collins <ian-news@hotmail.com> - 2017-01-08 14:42 +1300
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 13:18 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 20:15 +0000
Re: Macro Expansion Ben Bacarisse <ben.usenet@bsb.me.uk> - 2017-01-07 20:42 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 22:50 +0000
Re: Macro Expansion Ian Collins <ian-news@hotmail.com> - 2017-01-08 11:59 +1300
Re: Macro Expansion Malcolm McLean <malcolm.mclean5@btinternet.com> - 2017-01-07 15:10 -0800
Re: Macro Expansion supercat@casperkitty.com - 2017-01-07 17:24 -0800
Re: Macro Expansion Tim Rentsch <txr@alumni.caltech.edu> - 2017-01-15 21:55 -0800
Re: Macro Expansion supercat@casperkitty.com - 2017-01-16 09:06 -0800
Re: Macro Expansion Tim Rentsch <txr@alumni.caltech.edu> - 2017-01-31 08:51 -0800
Re: Macro Expansion supercat@casperkitty.com - 2017-01-31 13:06 -0800
Re: Macro Expansion Tim Rentsch <txr@alumni.caltech.edu> - 2017-02-03 07:49 -0800
Re: Macro Expansion supercat@casperkitty.com - 2017-02-03 12:03 -0800
Re: Macro Expansion Tim Rentsch <txr@alumni.caltech.edu> - 2017-02-09 09:00 -0800
Re: Macro Expansion Ben Bacarisse <ben.usenet@bsb.me.uk> - 2017-01-08 01:37 +0000
Re: Macro Expansion Jean-Marc Bourguet <jm@bourguet.org> - 2017-01-08 10:22 +0100
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-01-07 12:18 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 20:28 +0000
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-01-07 12:36 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-07 22:59 +0000
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-01-08 00:20 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 13:30 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-10 14:00 +0000
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-01-10 07:43 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-10 17:47 +0000
Re: Macro Expansion Ben Bacarisse <ben.usenet@bsb.me.uk> - 2017-01-10 22:49 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-10 23:28 +0000
Re: Macro Expansion "James R. Kuyper" <jameskuyper@verizon.net> - 2017-01-10 18:51 -0500
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-11 00:06 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-10 20:30 +0000
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-04-26 10:04 -0700
Re: Macro Expansion Keith Thompson <kst-u@mib.org> - 2017-04-26 12:00 -0700
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-04-26 12:24 -0700
Re: Macro Expansion bartc <bc@freeuk.com> - 2017-04-26 20:12 +0100
Re: Macro Expansion Thiago Adams <thiago.adams@gmail.com> - 2017-04-26 12:34 -0700
Re: Macro Expansion jameskuyper@verizon.net - 2017-04-26 13:46 -0700
Re: Macro Expansion Jean-Marc Bourguet <jm@bourguet.org> - 2017-01-08 10:13 +0100
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 13:10 +0000
Re: Macro Expansion Jean-Marc Bourguet <jm@bourguet.org> - 2017-01-08 15:51 +0100
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 17:17 +0000
Re: Macro Expansion supercat@casperkitty.com - 2017-01-08 11:04 -0800
Re: Macro Expansion Malcolm McLean <malcolm.mclean5@btinternet.com> - 2017-01-08 11:10 -0800
Re: Macro Expansion supercat@casperkitty.com - 2017-01-08 14:08 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 19:49 +0000
Re: Macro Expansion supercat@casperkitty.com - 2017-01-08 14:17 -0800
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 19:19 +0000
Re: Macro Expansion Jean-Marc Bourguet <jm@bourguet.org> - 2017-01-08 21:43 +0100
Re: Macro Expansion supercat@casperkitty.com - 2017-01-08 10:43 -0800
Re: Macro Expansion Keith Thompson <kst-u@mib.org> - 2017-01-08 12:39 -0800
Re: Macro Expansion antispam@math.uni.wroc.pl - 2017-01-08 22:54 +0000
Re: Macro Expansion "James R. Kuyper" <jameskuyper@verizon.net> - 2017-01-08 18:36 -0500
Re: Macro Expansion antispam@math.uni.wroc.pl - 2017-01-09 01:15 +0000
Re: Macro Expansion "James R. Kuyper" <jameskuyper@verizon.net> - 2017-01-08 20:49 -0500
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-08 23:53 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-09 01:11 +0000
Re: Macro Expansion antispam@math.uni.wroc.pl - 2017-01-09 01:31 +0000
Re: Macro Expansion BartC <bc@freeuk.com> - 2017-01-10 11:28 +0000
Page 2 of 4 — ← Prev page 1 [2] 3 4 Next page →
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2017-02-03 07:49 -0800 |
| Message-ID | <kfn37fvb7gq.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #102868 |
supercat@casperkitty.com writes: > On Tuesday, January 31, 2017 at 10:51:53 AM UTC-6, Tim Rentsch wrote: >> supercat writes: >> >>> On Sunday, January 15, 2017 at 11:56:05 PM UTC-6, Tim Rentsch wrote: >>>> supercat writes: >>>>> The language was in wide use prior to the Standard, and the >>>>> Committee decided that it should try to come up with a single set >>>>> of rules which was consistent with as many implementations as >>>>> possible, [...] >>>> >>>> Your view of the history is mistaken. See the Rationale >>>> document. >>> >>> You mean this part? >>> >>> | The X3J11 charter clearly mandates the Committee to codify >>> | common existing practice. The Committee has held fast to >>> | precedent wherever this was clear and unambiguous. The vast >>> | majority of the language defined by the Standard is precisely >>> | the same as is defined in Appendix A of The C Programming >>> | Language by Brian Kernighan and Dennis Ritchie, and as is >>> | implemented in almost all C translators. (This document >>> | is hereinafter referred to as K&R.) >> >> No I meant this part: >> >> | Existing code is important, existing implementations are not. > > As I intended the term "consistent", if X always yields 1, while Y may > arbitrarily yield 1 or 2, the behavior of X is consistent with that of > Y, but not vice versa. Perhaps some other term would have been better? The key word here is not "consistent" but "implementations". What the committee paid attention to was not what behaviors /implementations/ chose but what behaviors /code/ made use of. That is a significant difference.
[toc] | [prev] | [next] | [standalone]
| From | supercat@casperkitty.com |
|---|---|
| Date | 2017-02-03 12:03 -0800 |
| Message-ID | <652e0dd9-136d-427d-b677-de92ebf5ca63@googlegroups.com> |
| In reply to | #103039 |
On Friday, February 3, 2017 at 9:49:16 AM UTC-6, Tim Rentsch wrote: > The key word here is not "consistent" but "implementations". > What the committee paid attention to was not what behaviors > /implementations/ chose but what behaviors /code/ made use of. > That is a significant difference. The authors of the Standard cannot influence existing code, since by definition it has already been created. They only way they can affect whether existing code will be usable on new implementations is by influencing the new implementations. I will grant that if a new implementation were to change a behavior upon which code relied, but happened to do so in a fashion that still met the code's requirements, such a change should not be regarded as damaging the old code even if the behavior was inconsistent with the old implementation. A more important point of contention is whether the Standard should recognize the existence of the substantial corpus of code that relies upon features or guarantees which can be practically supported on nearly all newer platforms but not on older ones. In 1980s, hardware designs were becoming more and more consistent; many people could thus reasonably have expected that the only implementations where certain guarantees would ever impose a major cost would be those for obsolescent hardware platforms. Consequently, use of such guarantees was expected to limit compatibility with older platforms, but not expected to affect compatibility with newer ones. What I don't think the authors of the Standard anticipated is that the guarantees which 1980s-1990s hardware and compilers could and did support at near-zero cost would become more expensive. If there would never be any reason that compilers for new platforms wouldn't support some guarantee, a recommendation that they do so would have been a waste of ink. If code which relies upon what used to be commonplace guarantees is regarded as having value, the Standard should recognize its existence. If default support would be expensive, the Standard could introduce ways by which code could demand the guarantee in places where it is needed, and deprecate the use of the guarantee without proper notice to the compiler.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2017-02-09 09:00 -0800 |
| Message-ID | <kfnvasj47va.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #103071 |
supercat@casperkitty.com writes: > On Friday, February 3, 2017 at 9:49:16 AM UTC-6, Tim Rentsch wrote: >> The key word here is not "consistent" but "implementations". >> What the committee paid attention to was not what behaviors >> /implementations/ chose but what behaviors /code/ made use of. >> That is a significant difference. > > The authors of the Standard cannot influence existing code, since by > definition it has already been created. They only way they can affect > whether existing code will be usable on new implementations is by > influencing the new implementations. I will grant that if a new > implementation were to change a behavior upon which code relied, but > happened to do so in a fashion that still met the code's requirements, > such a change should not be regarded as damaging the old code even if > the behavior was inconsistent with the old implementation. > > A more important point of contention is whether the Standard should > recognize the existence of the substantial corpus of code that relies > upon features or guarantees which can be practically supported on > nearly all newer platforms but not on older ones. In 1980s, hardware > designs were becoming more and more consistent; many people could thus > reasonably have expected that the only implementations where certain > guarantees would ever impose a major cost would be those for obsolescent > hardware platforms. Consequently, use of such guarantees was expected > to limit compatibility with older platforms, but not expected to affect > compatibility with newer ones. > > What I don't think the authors of the Standard anticipated is that the > guarantees which 1980s-1990s hardware and compilers could and did support > at near-zero cost would become more expensive. If there would never be > any reason that compilers for new platforms wouldn't support some guarantee, > a recommendation that they do so would have been a waste of ink. If > code which relies upon what used to be commonplace guarantees is regarded > as having value, the Standard should recognize its existence. If default > support would be expensive, the Standard could introduce ways by which > code could demand the guarantee in places where it is needed, and deprecate > the use of the guarantee without proper notice to the compiler. I see you are up to your old tricks of oversnipping so you can change the subject.
[toc] | [prev] | [next] | [standalone]
| From | Ben Bacarisse <ben.usenet@bsb.me.uk> |
|---|---|
| Date | 2017-01-08 01:37 +0000 |
| Message-ID | <8737gunxgz.fsf@bsb.me.uk> |
| In reply to | #101261 |
BartC <bc@freeuk.com> writes:
> On 07/01/2017 20:42, Ben Bacarisse wrote:
>> BartC <bc@freeuk.com> writes:
>
>>> I wish they would just state all this stuff instead of leaving people
>>> to either deduce it or eventually discover it for themselves.
>>
>> "They" (presumably the C committee) have an obligation to be precise
>> rather than explanatory. It's the various books and tutorials about C
>> that should explain this in simpler terms. If no such thing exists -- a
>> lot of C tutorials are either overly simplistic or wrong -- then it's
>> not the fault of the C committee.
>
> Who was responsible for standardising such a complicated macro
> language? I can't believe most C programmers are aware of all arcane
> details.
That's a rhetorical question, I assume.
Macro languages are notoriously hard to understand unless they are
hopelessly under-powered. Some may even be very simple to specify (TRAC
for example) but the consequences of the definition can be
extraordinarily complex.
<snip>
>> ... A test:
>>
>> #define X Y
>> #define Y T
>> #define T X Y
>>
>> <T> => <X><Y>
>> <X> => <Y>
>> <Y> => <T>
>> <Y> => <T>
>
> This introduces new problems. Just take this:
>
> #define X T
> #define T X
> T
>
> How does it manage to not keep expanding indefinitely? The simplest
> case is taken care of:
>
> #define T T
>
> by being explicitly mentioned (somewhere or other). For the T=>X, X=>T
> example, I can remember a 'topmost' macro name, and avoid expanding
> that even deep inside an unrelated macro expansion. But with this
> tweak of your example:
>
> #define X Y
> #define Y X
> #define T X Y
BTW, simpler and easier to see what happens would be
#define X (Y)
#define Y [X]
#define T {X}
T
> Now it's X=>Y, Y=>X that threatens to go on forever. I can't add these
> names to the list of names that have been expanded, as that is local
> to each level of macro. I might need to propagate a whole sequence of
> 'topmost' macro names to each level.
Expansions are nested rather than iterated, so you just need to be able
to find what expansion you are in and what expansion that expansion is
in, and so on up. Passing some sort of parent pointer down into each
sub-expansion will automatically give you a chain of "active" macros.
<snip>
> Yikes. I guess whoever devised this scheme didn't think too much about
> efficiency in implementing it.
I'm not sure you can say that unless you are sure you've got the right
interpretation of the rules and a good design for implementing them.
Again, you may be right and it's hell to implement, but I would not be
confident in saying that.
<snip>
--
Ben.
[toc] | [prev] | [next] | [standalone]
| From | Jean-Marc Bourguet <jm@bourguet.org> |
|---|---|
| Date | 2017-01-08 10:22 +0100 |
| Message-ID | <87wpe5x5wy.fsf@news.bourguet.org> |
| In reply to | #101273 |
Ben Bacarisse <ben.usenet@bsb.me.uk> writes: > Expansions are nested rather than iterated, so you just need to be able > to find what expansion you are in and what expansion that expansion is > in, and so on up. Passing some sort of parent pointer down into each > sub-expansion will automatically give you a chain of "active" macros. You also need to mark identifiers so that they are no more considered later on. Yours, -- Jean-Marc
[toc] | [prev] | [next] | [standalone]
| From | Thiago Adams <thiago.adams@gmail.com> |
|---|---|
| Date | 2017-01-07 12:18 -0800 |
| Message-ID | <8b14d650-30b5-4faf-b0dc-4c52a353ec98@googlegroups.com> |
| In reply to | #101235 |
On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: [...] > It works with many of the examples I've tried, but I have little > confidence that whatever I end up with will always work, as I'm guessing > at the algorithms needed. Do you have a unit test or a list of samples to share?
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-07 20:28 +0000 |
| Message-ID | <o4rivj$s08$1@dont-email.me> |
| In reply to | #101243 |
On 07/01/2017 20:18, Thiago Adams wrote: > On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: > [...] >> It works with many of the examples I've tried, but I have little >> confidence that whatever I end up with will always work, as I'm guessing >> at the algorithms needed. > > Do you have a unit test or a list of samples to share? Not yet. Just the examples from the Standard and from the GNU docs, or silly ones like in my OP. The only macros I'm likely to use myself are going to be straightforward ones that anyone can understand, and can be trivially expanded. -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | Thiago Adams <thiago.adams@gmail.com> |
|---|---|
| Date | 2017-01-07 12:36 -0800 |
| Message-ID | <58ad3b29-e9cb-4b82-84f0-f8ed0c77d2d7@googlegroups.com> |
| In reply to | #101246 |
On Saturday, January 7, 2017 at 6:29:11 PM UTC-2, Bart wrote: > On 07/01/2017 20:18, Thiago Adams wrote: > > On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: > > [...] > >> It works with many of the examples I've tried, but I have little > >> confidence that whatever I end up with will always work, as I'm guessing > >> at the algorithms needed. > > > > Do you have a unit test or a list of samples to share? > > Not yet. Just the examples from the Standard and from the GNU docs, or > silly ones like in my OP. > > The only macros I'm likely to use myself are going to be straightforward > ones that anyone can understand, and can be trivially expanded. I am thinking in restart this macro expansion using an script language as well. There are more details, for instance the "defined" operator works only in #if. I have an extra parameter to tell when "defined" can be used.
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-07 22:59 +0000 |
| Message-ID | <o4rrqe$ren$1@dont-email.me> |
| In reply to | #101248 |
On 07/01/2017 20:36, Thiago Adams wrote:
> On Saturday, January 7, 2017 at 6:29:11 PM UTC-2, Bart wrote:
>> On 07/01/2017 20:18, Thiago Adams wrote:
>>> On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote:
>>> [...]
>>>> It works with many of the examples I've tried, but I have little
>>>> confidence that whatever I end up with will always work, as I'm guessing
>>>> at the algorithms needed.
>>>
>>> Do you have a unit test or a list of samples to share?
>>
>> Not yet. Just the examples from the Standard and from the GNU docs, or
>> silly ones like in my OP.
>>
>> The only macros I'm likely to use myself are going to be straightforward
>> ones that anyone can understand, and can be trivially expanded.
>
>
> I am thinking in restart this macro expansion using an
> script language as well.
The script language was just a quick way of experimenting with different
algorithms until I got something that worked. It doesn't include any
tokenising; it just works with lists of strings, where each string
represents a token. So ("a","+","b") for 'a+b'.
Currently the code is incredibly clunky (and it doesn't work yet), but I
will later have to implement it as very tight, compiled code.
> There are more details, for instance the "defined" operator
> works only in #if.
>
> I have an extra parameter to tell when "defined" can be used.
I forgot about #if; another nightmare! That also means there are two
contexts where preprocessed tokens are delivered: to the parser in a
different part of the compiler; and to the handler for #if/#elsif, which
is still inside the preprocessor. Another complication in the data flow.
--
Bartc
[toc] | [prev] | [next] | [standalone]
| From | Thiago Adams <thiago.adams@gmail.com> |
|---|---|
| Date | 2017-01-08 00:20 -0800 |
| Message-ID | <3281b492-8ca3-44b8-a84e-9dc1d490684b@googlegroups.com> |
| In reply to | #101235 |
On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: [...] > The descriptions I've seen of the process seem to me ambiguous and > difficult to understand (maybe they're striving to be as cryptic as the > language they are describing!). Bart, I found some references: Dave Prosser's C preprocessing algorithm annotated by Diomidis D. Spinellis http://www.spinellis.gr/blog/20060626/index.html This project and many others uses this algorithm https://github.com/rui314/8cc-old/blob/master/cpp.c The source is well documented. Also this one: https://github.com/alexfru/SmallerC/blob/93d3bb6ffc97eea3477c2ffe6717b3cd2c9c5dfe/v0100/ucpp/macro.c
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-08 13:30 +0000 |
| Message-ID | <o4teqp$5ke$1@dont-email.me> |
| In reply to | #101280 |
On 08/01/2017 08:20, Thiago Adams wrote: > On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: > [...] >> The descriptions I've seen of the process seem to me ambiguous and >> difficult to understand (maybe they're striving to be as cryptic as the >> language they are describing!). > > Bart, I found some references: > > Dave Prosser's C preprocessing algorithm annotated by Diomidis D. Spinellis > http://www.spinellis.gr/blog/20060626/index.html Thanks. Although it might need a touch more annotation before I can fully understand it! (Like, what the fat dots mean, and what a superscript signifies.) (I like the note about spending 5 years trying to do it. That is, create a fully conforming one. But I think a mostly conforming one will be good enough for my purposes.) > > https://github.com/alexfru/SmallerC/blob/93d3bb6ffc97eea3477c2ffe6717b3cd2c9c5dfe/v0100/ucpp/macro.c I think I've seen the ucpp code. The trouble with existing /C/ implementations is that most of the code is preoccupied with the details of that implementation, which might be very different from what I have in mind. -- bartc
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-10 14:00 +0000 |
| Message-ID | <o52pbd$5mp$1@dont-email.me> |
| In reply to | #101293 |
On 08/01/2017 13:30, BartC wrote: > On 08/01/2017 08:20, Thiago Adams wrote: >> On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: >> [...] >>> The descriptions I've seen of the process seem to me ambiguous and >>> difficult to understand (maybe they're striving to be as cryptic as the >>> language they are describing!). >> >> Bart, I found some references: >> >> Dave Prosser's C preprocessing algorithm annotated by Diomidis D. >> Spinellis >> http://www.spinellis.gr/blog/20060626/index.html > > Thanks. Although it might need a touch more annotation before I can > fully understand it! (Like, what the fat dots mean, and what a > superscript signifies.) It turns out I was looking at the non-annotated algorithm! But the annotated one is still too abstract and too complicated to readily turn into code (actual code or more conventional pseudo-code). The version I'm working on at the moment (my third attempt) is far simpler. But I don't know yet how well it will work. (If it does work I'll try and write it up.) -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | Thiago Adams <thiago.adams@gmail.com> |
|---|---|
| Date | 2017-01-10 07:43 -0800 |
| Message-ID | <35bf4dd4-b642-4a98-9d7e-f577a1667a58@googlegroups.com> |
| In reply to | #101381 |
On Tuesday, January 10, 2017 at 12:00:52 PM UTC-2, Bart wrote: > On 08/01/2017 13:30, BartC wrote: > > On 08/01/2017 08:20, Thiago Adams wrote: > >> On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: > >> [...] > >>> The descriptions I've seen of the process seem to me ambiguous and > >>> difficult to understand (maybe they're striving to be as cryptic as the > >>> language they are describing!). > >> > >> Bart, I found some references: > >> > >> Dave Prosser's C preprocessing algorithm annotated by Diomidis D. > >> Spinellis > >> http://www.spinellis.gr/blog/20060626/index.html > > > > Thanks. Although it might need a touch more annotation before I can > > fully understand it! (Like, what the fat dots mean, and what a > > superscript signifies.) > > It turns out I was looking at the non-annotated algorithm! But the > annotated one is still too abstract and too complicated to readily turn > into code (actual code or more conventional pseudo-code). > > The version I'm working on at the moment (my third attempt) is far > simpler. But I don't know yet how well it will work. > > (If it does work I'll try and write it up.) > I started to implement the algorithm yesterday in a simple way, just to show how it works using typescript. I will post here as soon it produces values.
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-10 17:47 +0000 |
| Message-ID | <o536kt$poa$1@dont-email.me> |
| In reply to | #101389 |
On 10/01/2017 15:43, Thiago Adams wrote: > On Tuesday, January 10, 2017 at 12:00:52 PM UTC-2, Bart wrote: >> On 08/01/2017 13:30, BartC wrote: >>> On 08/01/2017 08:20, Thiago Adams wrote: >>>> On Saturday, January 7, 2017 at 4:36:08 PM UTC-2, Bart wrote: >>>> [...] >>>>> The descriptions I've seen of the process seem to me ambiguous and >>>>> difficult to understand (maybe they're striving to be as cryptic as the >>>>> language they are describing!). >>>> >>>> Bart, I found some references: >>>> >>>> Dave Prosser's C preprocessing algorithm annotated by Diomidis D. >>>> Spinellis >>>> http://www.spinellis.gr/blog/20060626/index.html >>> >>> Thanks. Although it might need a touch more annotation before I can >>> fully understand it! (Like, what the fat dots mean, and what a >>> superscript signifies.) >> >> It turns out I was looking at the non-annotated algorithm! But the >> annotated one is still too abstract and too complicated to readily turn >> into code (actual code or more conventional pseudo-code). >> >> The version I'm working on at the moment (my third attempt) is far >> simpler. But I don't know yet how well it will work. >> >> (If it does work I'll try and write it up.) >> > I started to implement the algorithm yesterday in a simple way, just to show how it works using typescript. > I will post here as soon it produces values. In the meantime perhaps someone can explain this behaviour. First start with this example: #define f a*f f(2)(9) First expansion gives this (using / to separate expanded parts and rest of the source): 2 * f / (9) f cannot be expanded again, so stays at f. Output is 2*f(9). Now take this one: #define f a*g #define g f(a) f(2)(9) First expansion (using / to separate already processed tokens, this expansion, and rest of the source): / 2 * g / (9) g is now expanded (using the (9) as the arg as it can step across that / boundary) to result in: 2 * / f(9) / But this time, f *is* expanded again! To result in 2 * 9 * g. (The last g is not expanded as no argument follows). The exact rules as to when a macro name can be expanded and when it can't are driving me crazy. With this example: #define f a g #define g f f The first expansion is /a g/. The next is a / f /, but it stops here, as a f, because f can't be expanded here. But above, the f(9) was expanded (although half that, the '(9)', was outside the expansion). Why is the second occurrence of f expandable in one instance, and not in another? -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | Ben Bacarisse <ben.usenet@bsb.me.uk> |
|---|---|
| Date | 2017-01-10 22:49 +0000 |
| Message-ID | <87shoqttsu.fsf@bsb.me.uk> |
| In reply to | #101391 |
BartC <bc@freeuk.com> writes: <snip> > In the meantime perhaps someone can explain this behaviour. <snip> > ... take this one: > > #define f a*g > #define g f(a) > f(2)(9) > > First expansion (using / to separate already processed tokens, this > expansion, and rest of the source): > > / 2 * g / (9) > > g is now expanded (using the (9) as the arg as it can step across that > / boundary) to result in: > > 2 * / f(9) / > > But this time, f *is* expanded again! To result in 2 * 9 * g. (The > last g is not expanded as no argument follows). I think you've got something wrong here. You probably had (at some time) a parameter in the definition of f or g (or both). <snip> -- Ben.
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-10 23:28 +0000 |
| Message-ID | <o53qjj$6kg$1@dont-email.me> |
| In reply to | #101404 |
On 10/01/2017 22:49, Ben Bacarisse wrote: > BartC <bc@freeuk.com> writes: > <snip> >> In the meantime perhaps someone can explain this behaviour. > <snip> >> ... take this one: >> >> #define f a*g >> #define g f(a) >> f(2)(9) >> >> First expansion (using / to separate already processed tokens, this >> expansion, and rest of the source): >> >> / 2 * g / (9) >> >> g is now expanded (using the (9) as the arg as it can step across that >> / boundary) to result in: >> >> 2 * / f(9) / >> >> But this time, f *is* expanded again! To result in 2 * 9 * g. (The >> last g is not expanded as no argument follows). > > I think you've got something wrong here. You probably had (at some > time) a parameter in the definition of f or g (or both). Yes, sorry. My first example should be: #define f(a) a*f f(2)(9) => 2*f(9) And the second one (equivalent to example #11 in the list I posted in this thread c. 3 hours ago): #define f(a) a*g #define g(a) f(a) f(2)(9) => 2*9*g The first has one expansion of f(), the second has two. The rule about when f should be expanded a subsequent time or not is obscure. -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | "James R. Kuyper" <jameskuyper@verizon.net> |
|---|---|
| Date | 2017-01-10 18:51 -0500 |
| Message-ID | <4e7e4f70-e4d8-a827-cb47-a6024dab6180@verizon.net> |
| In reply to | #101404 |
On 01/10/2017 05:49 PM, Ben Bacarisse wrote:
> BartC <bc@freeuk.com> writes:
> <snip>
>> In the meantime perhaps someone can explain this behaviour.
> <snip>
>> ... take this one:
>>
>> #define f a*g
>> #define g f(a)
>> f(2)(9)
>>
>> First expansion (using / to separate already processed tokens, this
>> expansion, and rest of the source):
>>
>> / 2 * g / (9)
>>
>> g is now expanded (using the (9) as the arg as it can step across that
>> / boundary) to result in:
>>
>> 2 * / f(9) /
>>
>> But this time, f *is* expanded again! To result in 2 * 9 * g. (The
>> last g is not expanded as no argument follows).
>
> I think you've got something wrong here. You probably had (at some
> time) a parameter in the definition of f or g (or both).
This looks suspiciously similar to the example from 6.10.3.4p4, and all
of BartC's comments above make sense if this is what he's talking about:
#define f(a) a*g
#define g(a) f(a)
instead of what he actually wrote. The point of that example is that
during preprocessing of f(2)(9) you get the following sequence of
replacements:
f(2)(9)
2*g(9)
2*f(9)
The "g" comes from the token list that replaced f(2), and recognition of
"f" as a macro is supposed to be suppressed for "2*g". However, you have
to add "(9)" to make a complete invocation of g macro, and that "(9)"
was not part that list of tokens derived from an expansion of f. Should
the expansion of a macro-invocation that is only partially derived from
a previous expansion of f() be re-scanned for occurrences of f()? In
other words, does it count as a "nested replacement" in the sense of
6.10.3.4p2? Arguments could be given for either interpretation of
"nested", and the standard doesn't define the term. The example in
6.10.3.4p4 is provided for the explicit purpose of pointing out that it
is implicitly unspecified.
They could have define "nested replacement" explicitly, to either allow
or disallow such cases - but they decided to leave it unspecified
instead. That strikes me as an odd choice - but clearly a deliberate one.
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-11 00:06 +0000 |
| Message-ID | <o53srn$dbq$1@dont-email.me> |
| In reply to | #101408 |
On 10/01/2017 23:51, James R. Kuyper wrote: > On 01/10/2017 05:49 PM, Ben Bacarisse wrote: >> BartC <bc@freeuk.com> writes: >> <snip> >>> In the meantime perhaps someone can explain this behaviour. >> <snip> >>> ... take this one: >>> >>> #define f a*g >>> #define g f(a) >>> f(2)(9) >>> >>> First expansion (using / to separate already processed tokens, this >>> expansion, and rest of the source): >>> >>> / 2 * g / (9) >>> >>> g is now expanded (using the (9) as the arg as it can step across that >>> / boundary) to result in: >>> >>> 2 * / f(9) / >>> >>> But this time, f *is* expanded again! To result in 2 * 9 * g. (The >>> last g is not expanded as no argument follows). >> >> I think you've got something wrong here. You probably had (at some >> time) a parameter in the definition of f or g (or both). > > This looks suspiciously similar to the example from 6.10.3.4p4, and all > of BartC's comments above make sense if this is what he's talking about: > > #define f(a) a*g > #define g(a) f(a) I think someone posted the example in the thread. My copy of the standard (2009 draft) doesn't have that. But a 2011 draft I've just looked at, does. And it gives two possible expansions, both apparently valid. So that's something I don't need to worry about (other than that the majority of compilers - including gcc - seem to support the version that my CPP test program doesn't output; they expand f() again). > instead of what he actually wrote. The point of that example is that > during preprocessing of f(2)(9) you get the following sequence of > replacements: > > f(2)(9) > 2*g(9) > 2*f(9) > > The "g" comes from the token list that replaced f(2), and recognition of > "f" as a macro is supposed to be suppressed for "2*g". However, you have > to add "(9)" to make a complete invocation of g macro, and that "(9)" > was not part that list of tokens derived from an expansion of f. Should > the expansion of a macro-invocation that is only partially derived from > a previous expansion of f() be re-scanned for occurrences of f()? In > other words, does it count as a "nested replacement" in the sense of > 6.10.3.4p2? Arguments could be given for either interpretation of > "nested", and the standard doesn't define the term. The example in > 6.10.3.4p4 is provided for the explicit purpose of pointing out that it > is implicitly unspecified. I guess then that this example (my own): #define A(x,y) if(x==y) #define B A( B 10,20); is also unspecified. Yet some compilers manage it, generating 'if(10==20);'. But others go badly wrong. -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | BartC <bc@freeuk.com> |
|---|---|
| Date | 2017-01-10 20:30 +0000 |
| Message-ID | <o53g5e$v6u$1@dont-email.me> |
| In reply to | #101389 |
On 10/01/2017 15:43, Thiago Adams wrote: > On Tuesday, January 10, 2017 at 12:00:52 PM UTC-2, Bart wrote: >> It turns out I was looking at the non-annotated algorithm! But the >> annotated one is still too abstract and too complicated to readily turn >> into code (actual code or more conventional pseudo-code). >> >> The version I'm working on at the moment (my third attempt) is far >> simpler. But I don't know yet how well it will work. >> >> (If it does work I'll try and write it up.) >> > I started to implement the algorithm yesterday in a simple way, just to show how it works using typescript. > I will post here as soon it produces values. I've got this set of tests at the minute that I'm working with. Most are antispam's examples, and I've added labels so that it is easier to compare the output across compilers. Run a compiler's -E equivalent on this C code (note that it won't compile because the examples aren't in a meaningful context): //---------------------------------------------- #define a(x) mac_a(x) #define b #define d(x) (x) #define e(x, y, z) x y ## z #define f a d d (x) #define g a b (c) #define h(x, y) x y #define hash # #define i j j #define j i 1: a b (c) 2: a d (c) 3: d(a b (c)) 4: d(a d (c)) 5: f 6: e(a,,a) 7: e(a, c d, e) 8: h(hash, zz) 9: i 10: d(i) #define k(a) a*m #define m(a) k(a) 11: k(2)(9) #define A(x,y) if(x==y) #define B A( 12: B 10,20); //---------------------------------------------- I'm using gcc for the 'definitive' interpretation, and that gives these results: 1: a (c) 2: a (c) 3: (mac_a(c)) 4: (mac_a(c)) 5: a d (x) 6: a a 7: a c de 8: # zz 9: i i 10: (i i) 11: 2*9*m 12: if(10==20); I tried a number of other compilers, most had some problems with the examples listed: Pelles C: #11 lccwin-32: #3 #4 #6 #11 DMC: #12 (crashes) Tiny C: #12 (out of memory) MSVC 2008: #5 #12 My test program currently has problems with #10, #11 and #12. (But when I fix those, what usually happens is that it will introduce problems elsewhere!) Your preprocessor project is OK with #1 to #4, but appears to have problems with example #5 onwards (#9 and #10 causes it to hang, while #12 generates a debug message). Conclusion: everyone saying that the Standard's description of macro expansion is perfectly clear and unambiguous, obviously doesn't know what they're talking about! Otherwise all those compilers would work perfectly. -- Bartc
[toc] | [prev] | [next] | [standalone]
| From | Thiago Adams <thiago.adams@gmail.com> |
|---|---|
| Date | 2017-04-26 10:04 -0700 |
| Message-ID | <02e4ec4b-b840-4ce3-b45d-3aeb82d00ef3@googlegroups.com> |
| In reply to | #101398 |
On Tuesday, January 10, 2017 at 6:30:12 PM UTC-2, Bart wrote:
> On 10/01/2017 15:43, Thiago Adams wrote:
> > On Tuesday, January 10, 2017 at 12:00:52 PM UTC-2, Bart wrote:
>
> >> It turns out I was looking at the non-annotated algorithm! But the
> >> annotated one is still too abstract and too complicated to readily turn
> >> into code (actual code or more conventional pseudo-code).
> >>
> >> The version I'm working on at the moment (my third attempt) is far
> >> simpler. But I don't know yet how well it will work.
> >>
> >> (If it does work I'll try and write it up.)
> >>
> > I started to implement the algorithm yesterday in a simple way, just to show how it works using typescript.
> > I will post here as soon it produces values.
>
> I've got this set of tests at the minute that I'm working with. Most are
> antispam's examples, and I've added labels so that it is easier to
> compare the output across compilers.
>
> Run a compiler's -E equivalent on this C code (note that it won't
> compile because the examples aren't in a meaningful context):
>
> //----------------------------------------------
> #define a(x) mac_a(x)
> #define b
> #define d(x) (x)
> #define e(x, y, z) x y ## z
> #define f a d d (x)
> #define g a b (c)
> #define h(x, y) x y
> #define hash #
> #define i j j
> #define j i
>
> 1: a b (c)
> 2: a d (c)
> 3: d(a b (c))
> 4: d(a d (c))
> 5: f
> 6: e(a,,a)
> 7: e(a, c d, e)
> 8: h(hash, zz)
> 9: i
> 10: d(i)
>
> #define k(a) a*m
> #define m(a) k(a)
> 11: k(2)(9)
>
> #define A(x,y) if(x==y)
> #define B A(
> 12: B 10,20);
> //----------------------------------------------
>
> I'm using gcc for the 'definitive' interpretation, and that gives these
> results:
>
> 1: a (c)
> 2: a (c)
> 3: (mac_a(c))
> 4: (mac_a(c))
> 5: a d (x)
> 6: a a
> 7: a c de
> 8: # zz
> 9: i i
> 10: (i i)
> 11: 2*9*m
> 12: if(10==20);
>
> I tried a number of other compilers, most had some problems with the
> examples listed:
>
> Pelles C: #11
> lccwin-32: #3 #4 #6 #11
> DMC: #12 (crashes)
> Tiny C: #12 (out of memory)
> MSVC 2008: #5 #12
>
> My test program currently has problems with #10, #11 and #12. (But when
> I fix those, what usually happens is that it will introduce problems
> elsewhere!)
>
> Your preprocessor project is OK with #1 to #4, but appears to have
> problems with example #5 onwards (#9 and #10 causes it to hang, while
> #12 generates a debug message).
>
> Conclusion: everyone saying that the Standard's description of macro
> expansion is perfectly clear and unambiguous, obviously doesn't know
> what they're talking about! Otherwise all those compilers would work
> perfectly.
>
One more test case, I saw this on windows headers.
#define _VARIANT_BOOL /##/
struct {
_VARIANT_BOOL bool;
}
This will expand to :
struct {
}
[toc] | [prev] | [next] | [standalone]
Page 2 of 4 — ← Prev page 1 [2] 3 4 Next page →
Back to top | Article view | comp.lang.c
csiph-web