TE
TechEcho
Home24h TopNewestBestAskShowJobs
GitHubTwitter
Home

TechEcho

A tech news platform built with Next.js, providing global tech news and discussions.

GitHubTwitter

Home

HomeNewestBestAskShowJobs

Resources

HackerNews APIOriginal HackerNewsNext.js

© 2025 TechEcho. All rights reserved.

The joy of max()

316 pointsby thefoxabout 7 years ago

12 comments

tbodtabout 7 years ago
The most insane macro in that is this monstrosity:<p><pre><code> #define __is_constant(x) \ (sizeof(int) == sizeof(*(1 ? ((void*)((long)(x) * 0l)) : (int*)1))) </code></pre> If x is a compile-time constant, (void* )((long)(x) * 0l) is equivalent to NULL, otherwise it&#x27;s just a regular void* . And if both sides of a ternary are pointers, the rule is:<p>If one side is NULL, the type of the ternary should be the type of the other side (int* in this case).<p>Otherwise, if one side is a void* , the type of the ternary should be void* .<p>So if x is constant, the type of the ternary is int* , and if it&#x27;s not constant the type is void* . The sizeof(* ()) around it turns that into sizeof(int) or sizeof(void), and in the GNU dialect sizeof(void) is 1, which is different from sizeof(int). Whew.<p>What I want to know is what&#x27;s wrong with __builtin_constant_p.
评论 #16720286 未加载
评论 #16721655 未加载
评论 #16720770 未加载
netheril96about 7 years ago
I often find it amusing how C advocates complain about the complexity of C++, and then proceed to implement the same complex functionality in even more brittle ways. Language features I have seen C developers emulate poorly in C: constepxr (here), virtual functions (with function pointers), templates (with macros), exceptions (with setjmp&#x2F;longjmp).
评论 #16722418 未加载
评论 #16725216 未加载
rwmjabout 7 years ago
The lesson here is that if you&#x27;re designing an operating system, you should also be designing&#x2F;evolving the programming language to go alongside it. The original authors of Unix did this (developing C in parallel), and so have many more obscure OSes. This could have been written simply as &#x27;max()&#x27; with appropriate modifications to the compiler to make it do the right thing.
评论 #16722499 未加载
评论 #16724291 未加载
RcouF1uZ4gsCabout 7 years ago
This is why C++ is so nice. Constexpr fits the bill perfectly instead of using these non-portable hacks.
评论 #16720467 未加载
评论 #16720481 未加载
评论 #16720455 未加载
gshrikantabout 7 years ago
What exactly is the typecheck macro doing here? I get that it compares the sizes of two pointer values but I don&#x27;t know why and I feel like there is some C standard nuance involved here that I don&#x27;t understand. Also, is the `sizeof` used to force evaluation at compile time?
评论 #16721791 未加载
评论 #16721846 未加载
nothrabannosirabout 7 years ago
I’m surprised this is necessary at all. Wouldn’t a compiler at any reasonable optimisation level optimise __cmp_once into __cmp automatically (and then into the resulting max constant) if used with constants? Seems like very basic constant propagation.
评论 #16720118 未加载
评论 #16720066 未加载
wruzaabout 7 years ago
I would like to use a language that doesn’t involve sizeof(typeof...) and template(Tmagic...) both.<p><pre><code> #include “meta.h” @tr max(@ta a, @tb b) if (is_comparable(ta, tb)) tr = common_base(ta, tb, optionshere...) produce_code {...} else compile_error “incompatible types in $(__func__)” </code></pre> I can’t figure out for decades why can’t we just get all ideas from lisp and code in happiness.
评论 #16723664 未加载
评论 #16724357 未加载
AnssiHabout 7 years ago
For an explanation of __is_constant(), see the thread where it was suggested: <a href="https:&#x2F;&#x2F;lkml.org&#x2F;lkml&#x2F;2018&#x2F;3&#x2F;20&#x2F;845" rel="nofollow">https:&#x2F;&#x2F;lkml.org&#x2F;lkml&#x2F;2018&#x2F;3&#x2F;20&#x2F;845</a> (this was also indirectly linked to in the article)<p>tl;dr: If one of the expressions in a ternary operator is a null pointer constant, the result type is that of the other expression.
andrepdabout 7 years ago
This in cpp:<p><pre><code> template&lt;class T&gt; constexpr const T&amp; max(const T&amp; a, const T&amp; b) { return a&gt;b ? a : b; }</code></pre>
评论 #16721077 未加载
评论 #16721511 未加载
kralljaabout 7 years ago
I’m not up to date on GCC macros, so I’m not familiar with this syntax:<p><pre><code> #define __cmp_once(x, y, op) ({ \ typeof(x) __x = (x); \ typeof(y) __y = (y); \ __cmp(__x, __y, op); }) </code></pre> Is that a block-expression, or what?
评论 #16721250 未加载
jstanleyabout 7 years ago
What&#x27;s the advantage of ever using cmp over just always using cmp_once?
评论 #16720341 未加载
评论 #16720275 未加载
评论 #16720255 未加载
drngddsabout 7 years ago
I&#x27;m really confused by the 1s in this macro. What are they, syntactically? The second one looks like it could be being cast to the type &quot;pointer to y&quot; but the first one has the sizeof expression in front of it.<p><pre><code> #define __typecheck(x, y) \ (!!(sizeof((typeof(x)*)1 == (typeof(y)*)1)))</code></pre>
评论 #16724045 未加载