Shared publicly  - 
 
Hey, since the last disgusting code hack thing worked out so well on G+, here's a new challenge..

Improve on this new disgusting hack:

#define is_enabled(x) (__stringify(CONFIG_##x)[0]=='1')

which basically is a C language "is the config variable 'x' defined" question (the "__stringify()" thing is the normal two-level macro expansion using the '#' operator, so that it expands the macro argument and then turns it into a string). And gcc does seem to do the proper compile-time optimizations that turn the above into a simple constant.

The intent is to be able to write

if (is_enabled(PROC)) {
...

in C code, without having to make ugly #ifdef sections with all the odd line breaks etc that entails. The kernel config rules are that the CONFIG_XYZ macro exists and has the value '1' for enabled features (you can ignore the module case for now - that's just the same thing, except the preprocessor name is CONFIG_XYZ_MODULE)

Is there a better trick for this? Bonus points if somebody comes up with a single macro that works for both C code and in pre-processor expressions.

--

Edit: so for people who can't be bothered with reading all the comments, +comex . found a solution that works. There's a few tweaking variations of in it there, but +comex . original approach works fine:

#define is_set(macro) is_set_(macro)
#define macrotest_1 ,
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(comma) is_set__(comma 1, 0)
#define is_set___(_, v, ...) v

Thanks.
621
171
Cirrus McMinor's profile photoJames Henstridge's profile photoSamuel Hayashi's profile photoAndrew Milkowski's profile photo
184 comments
 
Oh christ. G+ formatting hasn't improved, and it thinks '#define' is about some kind of hashtag.

Should I complain about the miles of whitespace to the right too? #whitespace.
 
I've been using Java for years and almost forget how to write C code. What kind of nerd i am....
 
I wonder what they will do with my #pragma or #include
 
Yes Linus. And the light gray text on white background. Need the Readability app for Chrome to read anything now.
 
don't be an instagram:) sorry a small joke this is calling for a deep knowledge of C macros, I yield (btw I enjoy my weekly Fedora updates kernel and all)
 
How can you guys not like the new interface design? It certainly is a fresh breeze compared to Facebook (and even the old G+), where way too many distractions are crammed into the top section of the page.

The usage of #whitespace in this new design may not be optimal, but I'd take that any day compared to all the distractions of Facebook.
 
Awesome, programming challenges! I wish I knew enough about cpp...
 
If you know CSS this is easily remedied. I've at least centered it. #feelThePower
 
Hmmm... using C and looking for elegance... I seem to recall that "The C language combines all the power of assembly language with all the ease-of-use of assembly language."
 
it seems to me that simple ifdef or ifndef code would look cleaner, be more immediately obvious, and have the added benefit of optimizing out entire segments of code in the odd if(0) cases, whether or not any "optimization" is specified in the kernel. I think you're looking for a problem to reinvent a solution to.
 
I think # whitespace is a problem of screen resolution. to lower it to a child and not # whitespace.

should make the attempt and put the resolution 1024 * 768, so it will be no changes in netbook, notebooks, tablets ... although it may be something else ... : P
 
Maybe instead of using macros like CONFIG_XYZ, you can use a static hashtable CONFIG that contains values for the option strings, for example if hashget(CONFIG, "XYZ") == 1, then consider CONFIG_XYZ to be enabled.

After that is_enabled can be defined as a function instead of a macro like:

bool is_enabled_func(string x) {
if (hashget(CONFIG, x) == 1) {
return TRUE;
} else
return FALSE;
}
}

If you don't like to type double quotes you can wrap it in a macro (although I don't think that's a good idea):

#define is_enabled(x) (is_enabled_func(__stringify(x)))

then you may say:

if (is_enabled(PROC)) { ... }
 
+Yin Wang: it basically needs to work like the preprocessor "define()" special case: it needs to generate a compile-time constant. No actual code can ever be generated, the compiler has to be able to fold it all into one constant value.

And obviously if the preprocessor symbol isn't defined, it needs to return the constant 0, without any compiler warnings etc.

The "__stringify()" trick works well, but the main problem with it is that you cannot use that trick in the preprocessor itself. We used to have a really disgusting trick that worked for both C code and pre-processor code, but we're going to have to get rid of it because it didn't work reliably enough, and involved tens of thousands of lines of automatically generated crud.

So we may just have to use two different approaches (one for preprocessor, one for C code), but I was hoping somebody had some knowledge of some super-secret gcc __builtin_cpp_defined() hack, or some other clever trick that would "just work".
 
Hmm.. it depends on what the compiler think is "compile time". If the compiler is smart enough, it can evaluate a lot of things including "hashget(CONFIG, "XYZ") == 1" at compile time. But I see this is actually even harder for gcc than __stringify trick, so not good at all.

Maybe you can give an example why __stringify doesn't work well with the preprocessor?
 
+Yin Wang - presumably the requirement is that the macro could be used from a cpp #if directive. The string operations used by the __stringify() version won't work in that context (since they are C constructs).
 
What exactly do you refer to with C code and pre-processor expression? Is it required that runtime access is available or is it sufficient to provide compile time access as your example implies? Would a generated intermediate file be acceptable? My first thought is using _FILE_ and _LINE_ to build a lookup blobby, stored in a flat byte array and preproccessor calculated address offsets for quick access. That would enable your macro to yield direct access to fragmnets of that dataworm. The intention is quick runtime access, of course, and prevent wasting of state by packing data into opaque memory instead of using c-style arrays. Probably not exactly what you're looking for, but maybe enough inspiration to make things fit.
 
So, this works for me:
#include <stdio.h>
#define is_enabled(d) CONFIG_##d
#define CONFIG_FOO 1
#define CONFIG_NOO 0

int main()
{
printf("It's %d!\n", is_enabled(FOO));
if(is_enabled(FOO))
{
puts("And it's true, yo!");
}
if(is_enabled(NOO))
{
puts("Noooo!");
}
return 0;
}

Amidoinitrite?

Output:

It's 1!
And it's true, yo!
 
What's wrong with:
#define is_enabled(x) ((CONFIG_##x-0) == 1)

works here (lightly tested) with the CPP and with C
 
+Linus Torvalds I was just remarking that it is somewhat inspiring that a man who is regarded as somewhat of a god programmer is still grounded and humble enough to put the question out to the masses like this. I mean, that's what open source is all about and a million heads are better than one but it's still a respectable action worth mentioning. Kudos.
 
Related to my last comment, this is what gcc -E says:

int main()
{
printf("It's %d!\n", 1);
if(1)
{
puts("And it's true, yo!");
}
if(0)
{
puts("Noooo!");
}
return 0;
}
 
Also, it works if I do the CONFIG_* defines before the is_enabled definition.
 
+Erik Gregg I think you got it. I don't really understand why he uses __stringify
 
Ummm, guys.. If the config option is not enabled, the define does not exist.

So just using CONFIG_FOO directly doesn't work, because you'll get "CONFIG_FOO not declared" errors if it isn't enabled.

The old hack we used to use was exactly to define every possible symbol, but that results in tons of trouble. And it makes the compiler have to parse all those thousands of unused preprocessor defines..
 
+Nelson Elhage "0" evaluates to 0x30, and therefore to true in C:

if("0")
{
puts("Zero evaluates to 0x30 which is true");
}

Output:
Zero evaluates to 0x30 which is true

Oh wait, never mind! It doesn't evaluate to a string! That's pretty good!
 
+Jan Seiffert The problem is that I think the assumption is that when FOO isn't enabled, CONFIG_FOO is not defined at all. In that case, Linus's original solution works, but yours yields (with gcc): error: ‘CONFIG_FOO’ undeclared (first use in this function)
 
que distro de linux usas?
which Linux distribution you use?
 
+Jan Seiffert: it's not defined to empty. It's undefined.

Try it. Seriously. Just do

int main(int argc, char **argv)
{
if ((UNDEFINED_SYMBOL-0)==1)
return 0;
return 1;
}

and if your compiler compiles it, it's not a C compiler.

So the trick is to detect the difference between a undefined preprocessor symbol and one that is defined.

In the pre-processor, you can use

#if UNDEFINED_SYMBOL

or

#if defined(UNDEFINED_SYMBOL)

but try to make a macro that works both for C expressions and for C pre-processor expressions.

My __stringify() thing works for C, but doesn't work for the pre-processor. It works by just turning an undefined symbol into the string that is the symbol name (and the first character won't be '0'). But string ops are not defined in the C pre-processor (much less ones that dereference them)
 
Crud... I don't get it :(
 
We already have the _enabled_CONFIG* macros which do this... it would be nicer if we could change the __enabled_CONFIG prefix to something that one could actually type, say CONF.
 
I understand it as a tri-state question. My understanding of the problem is:
switch(x) {
case 0: ...;;
case 1: ...;;
default: return "woohoo(equals 0)";;
}
Therefore i think, a lookup w/ fallthrough to 0 is a valid path.
 
+H. Peter Anvin we are getting rid of the whole _enabled_CONFIG_xyzzy mess because it doesn't work. It adds fifteen thousand lines of crap to autoconf.h, and even then it's not enough for some cases. So it's going away. It's pure crap. The above is what will probably replace it unless somebody can come up with something even more clever.
 
I presume the reason is that there are still corner cases where macros don't get defined (which means that any solution which relies on always-defined macros is just going to fail.) Too bad, because it's kind of nice that it caches typos.
 
Your text got upgraded all markdown style!
 
Well, yes, there are things like architecture-specific config variables that other architectures don't even know about and thus wont define. But the whole "make the compiler wade through fifteen thousand lines of pointless crap every time it includes autoconf.h" is a pretty strong argument too...
 
I discussed this post with 1 person in a hangout.
Translate
 
+Theodore Quaid: so that's what __stringify() is: the double macro expansion with '#' on the second one to stringify the argument.

So that's exactly my suggestion. The question is: can it be done better.

For example, that one does not work in

#if is_enabled(SOMETHING)

so we have to have two different ways - one for C code and one for the pre-processor. Our previous (broken) hack allowed the same syntax for both, but at unacceptable cost.

I'm pretty sure it can't be done better with standard C tricks. But I hope I cna be either proven wrong, or somebody knows of some nice gcc extension (we already use and rely on things like __builtin_constant_p() etc).
 
Nerds!!! Just kidding. I'm more of an EET guy otherwise I'd help.
 
After going through the C99 standard's definition of the C Preprocessor it doesn't look like it's possible to evaluate string literals or characters specified by index of a constant string literal. Apparently accessing an index isn't considered a constant expression to the Preprocessor so it cannot be evaluated.
 
Man, this one is a brain buster. Somehow I doubt this is possible to pull off with #if...
 
Stupid hashtags. Can't they at least add `code formatting`?
 
Should this really be done during compile time? Isn't it possible and more logical to handle most of the functionality during configure time using some make magic?
 
seriosly i agree with you chick..........
 
Been trying with different combinations for almost 3 hours now.. I give up..

I put my vote on the original:
#define is_enabled(x) (__stringify(CONFIG_##x)[0]=='1')

I did not make it, but I sure had a fun time trying! :)
 
+Linus Torvalds are you sure that semantic highlighting will work in your editor for the new piece of code? Otherwise you are loosing readability, not gaining.
 
Hmm, now, if there was a way to do user-defined #pragma in gcc ...
 
If I understand you correctly you want to get rid of the ugly
#ifdef CONFIG_BLA
....
#endif
code pieces which makes it harder to read. You function hast to be evaluated in runtime which makes the code a bit slower, and you may get issues with unresolvable symbols as they remain in the code.
The
if (is_enabled(PROC)) {
function_only_with_proc(...)
}
the function_only_with_proc will be in the a.out code and the linker will complain.
Or... I got you wrong. ;-)
comex .
+
10
1
2
1
 
edit: I spent all this time coming up with a joke solution (that relied on a GCC bug! it was awesome), but then I realized there is a much simpler solution:

#define is_set(macro) is_set_(macro)
#define macrotest_1 ,
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(comma) is_set__(comma 1, 0)
#define is_set___(_, v, ...) v
 
Hacking is computing jargon for improving else work. I think you are referring to cracking (unethical break in of some else property/info)
 
+Harish Sunshine " Hacker is a term used by some to mean "a clever programmer" and by others, especially those in popular media, to mean "someone who tries to break into computer systems.""
 
+Harish Sunshine haha, what? I think you misunderstand the purpose; the 'hack' in question is for configuration variables for building in gcc (presumably for use with the linux kernel) NOT an invasive hack for stealing personal details.

Edit: Wow looks like I was a little slow as I was writing that there was nothing, than 3 comments.
 
^^^ Best comment I have read all night!
 
Darn it... Why did yall post just now? Messed up my comment flow! #whitespace
 
+Linus Torvalds Here are just some final thoughts as I give up and go to bed..

1. __stringify works because it uses some operations (for example: #) that can operate on undefined names. This operation must operate on undefined names, and produce a legitimate value (such as an integer), which can then be used to differentiate itself from 1.

2. So the only way seems to be find another such operation that can tell an undefined name from 1. #ifdef does not work because it can't be used inside #define.

3. I'm not familiar enough with cpp to tell if other operators can work in a similar way, but whatever it is, it cannot produce something which cpp can't operate on, for example # doesn't work because produces strings.

Good luck :-)
 
Cant you just do
if ( MAYBEDEFINEDNAME+0)
{...

Should expand to +0 if undefined.
Maybe I'm missing something. Goodnight.
 
+Nathan Bass yeah I thought that I was getting the jump on it too... Hence the "best post of the night"pussy that failed
 
Ha ha ha! Post not pussy.. Damn you Swype!
 
Give the prize to +comex . -- the trick with variadic macros and inserting a comma is pretty darn clever! (though G+ butchered the "_" levels...)
 
+Josh Stone i also think Linus has got his answer with this one.
+Christian Jonassen the issue is that the is_enabled macro expends to C code, which is performance-costly during runtime, and that's why any trick that would come with only compile-time costs would be better.
 
Love these posts ... i always learn something :)
 
Is it really necessary to use one macro for CPP-code (#if,#ifdef) and for actual C-code? Would splitting the task allow sane solutions for each?
 
+comex . You got it! Playing with macro varargs and insertion of a comma did the trick. A version which is not eaten by G+:

#define is_set(macro) EXPAND(macro)
#define COMMA_1 ,
#define EXPAND(value) one_if_comma_else_0(COMMA_##value)
#define one_if_comma_else_0(comma) shift_val(comma 1, 0)
#define shift_val(_, v, ...) v
 
+Erik Gregg I added a comment to your gist to complete it with a test in an "#if" construction. It really works!
 
Basically you are doing a stringification of a expansion of a concatination, so why not:

#define str_exp_pre(x) str_exp(DEFINED_##x)
#define str_exp(x) stringify(x)
#define stringify(x) #x
#define is_enabled(x) (str_exp_pre(x)[0] == '1')

/* TEST */
#define DEFINED_FOO 1
is_enabled(FOO)
is_enabled(BAR)
 
+Andreas Leitgeb So the question is to have cpp remove the compound statement from the output?
 
+jms wams The point is to use cpp to come up with a simple 0 or 1 depending on the existance of a macro. This will in turn be optimised by cc if used in tests, but without requiring gcc to perform complex precomputing for optimization.

The point of this point is that the macro may not be defined, so the expansion may not happen.
 
you see... This is why I am not a programmer... Never was one... Never will be one... I am so sad...

printf ("Hello my sad, sad world");
 
IT is my major but I have just started from scratch. I felt the same way but hey gotta keep up with technology.
 
+Andreas Leitgeb why not? It comes out as (0x31 == '1') which optimizes to true, or (0x0 == '1') which doesn't... No runtime at all, it'll all optimize out, right?
 
This whole thread is exactly why I don't program C. ;-)
 
Maybe
#define is_enabled(x) (sizeof(__stringify(CONFIG_##x)) == sizeof("1") )
 
My vote is to stay with "the ugly ifdef sections". Instead of trying to hide the hacks, work out how to reduce the number you have to use.
 
+Romain Failliot Tried it on Visual C++ Expess 2005: works as expected. Compiler:
Microsoft (R) 32-bit C/C++ Optimizing Compiler Version 14.00.50727.42 for 80x86
 
I'm trying to understand what's so disgusting about the "hack" in the first place. This is exactly what the preprocessor is for.

Sure, the preprocessor is a hack in the first place, and trying to avoid it where unnecessary is a virtuous goal, but it's a tried-and-true hack and this is what it's good at. I say keep it.
 
+Bogdan Manciu array indexing does not imply run time. As long as the expression is constant, the compiler can, and in the case of GCC, does, evaluate it at compile time.
 
+Romain Failliot Maybe visual interprets function macros at definition and the insertion of a comma does not do the trick of shifting the arguments.
 
in MSVC an argument for a macro is an argument no matter it expands to contain commas or ), etc. So the arguments won't shift. The above trick relies on basically a bug on the way gcc parses the macro.
 
A little different spin on it that doesn't have extra spaces or commas (+comex .'s evaluated mid-way to ", 1, 0" or "macrotest_CONFIG_UNDEF 1, 0" whereas this evaluates to "0,1,0" or "macrotest_CONFIG_UNDEF,0"):

#define is_set(macro) is_set_(macro)
#define macrotest_1 0,1
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(oneortwo) is_set__(oneortwo,0)
#define is_set___(_, v, ...) v

Very clever, +comex .!
 
To confirm more concisely than the printing examples others have given:
#define CONFIG_FIRST 1
#define CONFIG_SECOND 0
if(!is_set(CONFIG_FIRST)) assert(0 && 1);
if(is_set(CONFIG_SECOND)) assert(0 && 2);
if(is_set(CONFIG_THIRD)) assert(0 && 3);
#if !is_set(CONFIG_FIRST)
assert(0 && 4);
#endif
#if is_set(CONFIG_SECOND)
assert(0 && 5);
#endif
#if is_set(CONFIG_THIRD)
assert(0 && 6);
#endif

preprocesses down to just:
if(!1) (void)((0 && 1) || (__assert("0 && 1", "defcheck.cc", 53), 0));
if(0) (void)((0 && 2) || (__assert("0 && 2", "defcheck.cc", 54), 0));
if(0) (void)((0 && 3) || (__assert("0 && 3", "defcheck.cc", 55), 0));

Which will be trivially optimized out by the compiler.
 
Linus, please consider making this refactoring crowdsourcing on Google+ an recurring event. It's really great to see people engaging in these discussions.

It's basically like Neil DeGrasse Tyson coming to a school and talking astrophysics and science with kids. This is how you create vocations and create the Linus of the next century. Great stuff.

By the way, I don't understand why Google+ doesn't understand the need for gist-like code blocks in comment threads. This would make the whole experience so much better.
 
One drawback to this approach is that some editors are able to detect which define is not set and show it as commented code.. like Qt Creator you could just import the kernel .config file. So using macros will break this feature.
 
+comex . : Yay. You get the prize. That's exactly what I wanted, and not only does it work within the preprocessor, it doesn't rely on the optimizer being smart, which is really nice.

You get a gold star. We'll be using this in the kernel.
 
This is the very interesting thread. :-)
 
Added a few lines to +comex . and +Keith Moyer 's contributions to make this operate like the original syntax.

#define is_enabled(x) is_enabled_(x)
#define is_enabled_(x) is_set(CONFIG_##x)
#define is_set(macro) is_set_(macro)
#define macrotest_1 0,1
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(comma) is_set__(comma ,0)
#define is_set___(_,v,...) v
 
+Kimani Muhammad The second line isn't necessary.

#define is_enabled(x) is_set(CONFIG_##x)
#define is_set(macro) is_set_(macro)
#define macrotest_1 0,1
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(comma) is_set__(comma ,0)
#define is_set___(_,v,...) v

But yeah, this was brilliant, +comex .
 
+Comex, +Linus Torvalds: A new version using a totally different approach that works for both GCC and MSVC:

#define donothing(...) 0
#define __open (
#define close__ )
/* This macro below is so it works on GCC. In MSVC it would be enough with just doing "#define is_enabled__(x) donothing __open Magic_##x close__" */
#define macro_caller(macro, args) macro args
#define Magic_1 close__ +1+ donothing __open
#define is_enabled_(x) macro_caller(donothing, __open Magic_##x close_)
#define is_enabled_(x) is_enabled__(x)
#define is_enabled(x) is_enabled_(CONFIG_##x)

Here you can see it with syntax coloring and run it: http://codepad.org/T44OUnKt

Feel free to rename Magic_1 to whatever you like, I ran out of naming imagination at that point :P
 
These kind of posts are very interesting, maybe it could be useful to archive it in a more organized fashion!!
 
+Torgeir Natvig both Eclipse and VIM are able to correctly parse the macros and indicate which code is active with +Comex 's solution. VIM has had trouble in the past with the existing code.
 
+Austin Morgan. Interesting. With my approach (http://codepad.org/T44OUnKt) Visual Studio is completely clueless about which code is active... I don't have VIM and Eclipse here. I'm curious about if they would be able to detect it.
 
Yeah, it's a very brilliant solution.

It's a pity that the code is not very well formatted by G+
 
+David Ramos +Linus Torvalds my version just playing with parenthesis

#define dummy_macro(t) 0
#define CONFIG_1 ) + 1 + ( 0

#define is_set(macro) is_set1(macro)
#define is_set1(macro) is_set2(CONFIG_##macro)
#define is_set2(x) (dummy_macro( x ))

#define FOO 1

is_set(FOO)
is_set(BAR)
 
+Jean-Noel Avila the reason my approach (http://codepad.org/T44OUnKt) is more complex than your revision is that it wouldn't work otherwise under MSVC, where dummy_macro(x) will always expand to dummy_macro(t), even when x expands to ) + 1 + ( 0. Hence, in MSVC, your "is_set" will always return 0.

But yeah, as a stripped-down, easier to understand, GCC-only version works very well :)
 
+Andreas Leitgeb Even shorter :
#define dummy_macro(t)
#define CONFIG_1 )(1
#define is_enabled(x) is_set(CONFIG_##x)
#define is_set(macro) is_set1(macro)
#define is_set1(macro) is_set2(CONFIG_##macro)
#define is_set2(x) (dummy_macro( x ) +0)

#define FOO 1

is_set(FOO)
is_set(BAR)

I haven't found any document related to that behavior.
 
+Jean-Noel Avila: your last version will expand to something like dummy_macro()(1)+0
Is not gcc complaining about invoking dummy_macro(t) without arguments? MSVC does (which is the reason I set that macro to be a variadic macro). In any case, following your and +Andreas Leitgeb "optimizations", this is the new GCC and MSVC-compliant version: http://codepad.org/T44OUnKt (warning: broken code ahead because of G+ formatting)

#define donothing(...)
#define __open (
#define close__ )
/* This macro below is so it works on GCC. In MSVC it would be enough with just doing "#define is_enabled_(x) (donothing __open Magic_##x close_) + 0)" */
#define macro_caller(macro, args) macro args
#define Magic_1 close__ __open 1
#define is_enabled_(x) (macro_caller(donothing, __open Magic_##x close_) + 0)
#define is_enabled_(x) is_enabled__(x)
#define is_enabled(x) is_enabled_(CONFIG_##x)

+Jean-Noel Avila: You won't find any documentation specific enough to tell you that, but basically, everytime a macro is expanded in MSVC, the number of arguments is immutable, doesn't matter the arguments have commas or brackets on them after being expanded themselves. The __open, __close macros are there so everything gets expanded in the same level, otherwise it will fail in one of the two compilers. Same with the additional "macro indirection" when joining the tokens. GCC and MSVC expand macros and arguments in a different order and fashion. My solution aims to offer code that works no matter the order in which those are processed, so hopefully will be 100% portable.
Believe me. Just grab a Visual C++ Express edition and try it.
 
Dear Mr. +Linus Torvalds ,

I do not want to annoy you or take a lot of your time but I want to bring to your notice a huge crime about to be committed towards the Computer Science community in Florida. The University of Florida at Gainesville has an excellent Computer Science and Engineering department. However due to some budget cuts the Dean has proposed to remove the heart of the department and reduce it to a joke. I am sure that your support against this move will be vital in our efforts to preserve our department. The relevant links are as follows:

http://saveufcise.wordpress.com/

Please help us!

Sincerely,
A student and a big fan.
 
+David Ramos gcc is not complaining. This is another nasty "feature": it can accept calls without argument if the macro is define with only one.
I believe you for MSVC, it's just that the portability has a big price in term of obfuscation.
 
+Jean-Noel Avila I don't expect that kind of code to be maintained very often, so obfuscation shouldn't be a big problem, while portability is, given the potentially big number of different environments expected to compile it, but of course you raise a valid point.
 
Just wondering: can current linux kernel be compiled with MSVC?
 
I would be VERY surprised if it can :) (but not 100% sure about it). But with the right amount of patches (like this for Intel Compiler: http://www.pyrillion.org/index.html?showframe=linuxkernelpatch.html) it could be ported to different compilers. Which is why I tried to make the solution as portable as I could (also, I work mostly with MSVC and wanted something that worked there too :P)
 
+Alex Riesen Thanks. So, a gcc-only idiom would suffice for the "task at hand". Anyway, finding a portable idiom was still a nice extra challenge for the crowd :-)
comex .
+
1
2
1
 
+Jean-Noel Avila To be fair, the "nasty" feature is standards compliant, and MSVC is not.
 
+comex . Interesting. Do you know whether 'the parenthesis escape by macro extension' trick is standards compliant too?
 
+comex . +Linus Torvalds In the original solution by comex
#define FOO 1 is evaluated as "set" but
#define FOO is evaluated as "not set".
This can be the desired behaviour or perhaps not. If not a single line fix to comex code can be this (see line 2):


#define is_set(macro) is_set_(macro)
#define macrotest_ ,
#define macrotest_1 ,
#define is_set_(value) is_set__(macrotest_##value)
#define is_set_(comma) is_set__(comma 1, 0)
#define is_set___(_, v, ...) v
 
Anyone can post the comparison of the affected codes improved of this solution? How many lines reduced, etc?

For non-programmers like myself, I hope that will give me extra idea on how BIG is this change.
 
For the record, as one of the two guys who wrote the preprocessor GCC currently uses: in the disputed case here, C99 says that GCC's behavior is correct and MSVC's is wrong. (C89 was ambiguous.) (It still irritates me that Microsoft rammed changes into C99 over everyone else's objections and then turned around and refused to actually implement C99 in their compilers.)
 
+Zack Weinberg Well Microsoft is currently in the 'Extinguish' stage of C support. So you shouldn't be at all surprised about that.
史珩
+
2
3
2
 
hi,linus,I am a university student from China ,and i want to translate some of your G+ into chinese to show for my friend(most of they are using linux )。May i do it?(thanks for god,my english is poor but most university student in China is good ,believe me :-D)
 
Your Work Is Inspiring
And I LOVE Linux
 
Sir Linus, I want to know your opinion about Python Programming Language.
 
Sir Linus, I want to know what is your opinion about open source in Portugal ? Thanks
 
I can't think of a single patch in existence that would be a better candidate for backporting, but this will be one I keep up my sleeve indefinitely regardless.
 
Hey, +Linus Torvalds these headscratchers are fun... I didn't have time to even take a stab at this one.. Got some more like this???
 
shit man, i try to understand programing, but it is to hard, i started with python, and im learning about linux mandriva, but for me is hard, how u doing that.
 
Same solution but displaying correctly on g+ :

# define is_set(macro) is_set_1(macro)
# define macrotest_1 ,
# define is_set_1(value) is_set_2(macrotest_##value)
# define is_set_2(comma) is_set_3(comma 1, 0)
# define is_set_3(_, v, ...) v
 
Linus Torvalds Can get your Email I am a big fan of you
 
Was talking to a friend about Unix, Linux and different OS's and we both admitted that Linux is incredibly superior to Windows and even Apple OS. Ubuntu, openSUSE, Mandriva, Fedora, LinuxMint, They're all really pretty, powerful and stable and they run so much faster as well as being safer. Hats off to everyone who contributed to the progress and a massive thank you to +Linus Torvalds.
 
Grattis till millenniumpriset!! Du är en förebild för alla riktiga nördar =)
Translate
 
I see you're trending on G+. It certainly beats Justin Bieber's name trending. Seeing Linus Torvalds trending is definitely awesome. I don't really care for trends most of the time, but I just thought I'd mention it. ;)
 
Does anyone have a comparison between how compilation times are affected by replacing ifdef by if? I have no clear sense of how C macro processing compares to C parsing when it comes to performance, or whether the compiler chews on the contents of the block before throwing it away.
 
Another congrats on being a millennium technology laureate. Good luck!
 
Congrats to the Millennium Price!
 
Linus, congratulations on the deserved award!
 
Congrats on the Millennium Technology Award!
rober x
 
Linus, congratulations on millenium technology award, and thanks for all your great work!!
 
Hey Linus, congrats on the award! Definitely deserving.
 
Hello Mr. Linus.
I had a question about building a Linux kernel.
Where do I start to build a kernel for operating system?
 
Well, strings does not exists in C, not in the standard library at least. You have to define a char array and treat your string char by char. Good luck with that.
 
Hello, Linus. I would like to thank you for your awesome kernel.
Unfortunately, i don't know your email, so i'm posting my question here, hoping you'll see it and answer.

Could you please write some tool to change your kernel to newer, just compiled one, on the fly.

For example, when i do
- make menuconfig
- make bzImage
- make modules
- make modules_install
and then
-make bzImage_loadnow

Noone but you know kernel well to describe if it possible.
Thank you.
 
Thank you, Brendan. I will try. The only thing i'm afraid is licenses. Because it's oracle.
Add a comment...