* CONFIG_PRINTK doesn't makes size smaller
@ 2005-09-20 6:14 colin
2005-09-20 6:38 ` Andrey Panin
2005-09-20 8:30 ` Denis Vlasenko
0 siblings, 2 replies; 8+ messages in thread
From: colin @ 2005-09-20 6:14 UTC (permalink / raw)
To: linux-kernel
Hi there,
I tried to make kernel with CONFIG_PRINTK off. I considered it should become
smaller, but it didn't because it actually isn't an empty function, and
there are many copies of it in vmlinux, not just one. Here is its
definition:
static inline int printk(const char *s, ...) { return 0; }
I change the definition to this and it can greatly reduce the size by about
5%:
#define printk(...) do {} while (0)
However, this definition would lead to error in some situations. For
example:
1. (printk)
2. ret = printk
I hope someone could suggest a better definition of printk that can both
make printk smaller and eliminate errors.
Regards,
Colin
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 6:14 CONFIG_PRINTK doesn't makes size smaller colin @ 2005-09-20 6:38 ` Andrey Panin 2005-09-20 7:48 ` Vadim Lobanov 2005-09-20 8:30 ` Denis Vlasenko 1 sibling, 1 reply; 8+ messages in thread From: Andrey Panin @ 2005-09-20 6:38 UTC (permalink / raw) To: colin; +Cc: linux-kernel On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > Hi there, > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > smaller, but it didn't because it actually isn't an empty function, and > there are many copies of it in vmlinux, not just one. Here is its > definition: > static inline int printk(const char *s, ...) { return 0; } > > I change the definition to this and it can greatly reduce the size by about > 5%: > #define printk(...) do {} while (0) > However, this definition would lead to error in some situations. For > example: > 1. (printk) > 2. ret = printk > > I hope someone could suggest a better definition of printk that can both > make printk smaller and eliminate errors. What about the macro below ? #define printk(...) ({ do { } while(0); 0; }) -- Andrey Panin | Linux and UNIX system administrator pazke@donpac.ru | PGP key: wwwkeys.pgp.net ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 6:38 ` Andrey Panin @ 2005-09-20 7:48 ` Vadim Lobanov 2005-09-20 8:03 ` Andrew Morton 2005-09-20 9:02 ` Andrey Panin 0 siblings, 2 replies; 8+ messages in thread From: Vadim Lobanov @ 2005-09-20 7:48 UTC (permalink / raw) To: Andrey Panin; +Cc: colin, linux-kernel On Tue, 20 Sep 2005, Andrey Panin wrote: > On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > > > Hi there, > > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > > smaller, but it didn't because it actually isn't an empty function, and > > there are many copies of it in vmlinux, not just one. Here is its > > definition: > > static inline int printk(const char *s, ...) { return 0; } > > > > I change the definition to this and it can greatly reduce the size by about > > 5%: > > #define printk(...) do {} while (0) > > However, this definition would lead to error in some situations. For > > example: > > 1. (printk) > > 2. ret = printk > > > > I hope someone could suggest a better definition of printk that can both > > make printk smaller and eliminate errors. > > What about the macro below ? > > #define printk(...) ({ do { } while(0); 0; }) So what does the do-while loop give us in the above case? In other words, why not just do the following...? #define printk(...) ({ 0; }) -VadimL ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 7:48 ` Vadim Lobanov @ 2005-09-20 8:03 ` Andrew Morton 2005-09-20 9:11 ` colin 2005-09-20 9:02 ` Andrey Panin 1 sibling, 1 reply; 8+ messages in thread From: Andrew Morton @ 2005-09-20 8:03 UTC (permalink / raw) To: Vadim Lobanov; +Cc: pazke, colin, linux-kernel Vadim Lobanov <vlobanov@speakeasy.net> wrote: > > On Tue, 20 Sep 2005, Andrey Panin wrote: > > > On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > > > > > Hi there, > > > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > > > smaller, but it didn't because it actually isn't an empty function, and > > > there are many copies of it in vmlinux, not just one. Here is its > > > definition: > > > static inline int printk(const char *s, ...) { return 0; } > > > > > > I change the definition to this and it can greatly reduce the size by about > > > 5%: > > > #define printk(...) do {} while (0) > > > However, this definition would lead to error in some situations. For > > > example: > > > 1. (printk) > > > 2. ret = printk > > > > > > I hope someone could suggest a better definition of printk that can both > > > make printk smaller and eliminate errors. > > > > What about the macro below ? > > > > #define printk(...) ({ do { } while(0); 0; }) > > So what does the do-while loop give us in the above case? In other > words, why not just do the following...? > > #define printk(...) ({ 0; }) > You may find that when printk() is a static inline there are still copies of the control string in the generated kernel image: printk("foo %d\n", bar()); must still evaluate bar() and may cause "foo %d\n" to turn up in vmlinux. IIRC later versions of gcc do remove the unreferenced string. If printk is a macro, it all of course disappears. ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 8:03 ` Andrew Morton @ 2005-09-20 9:11 ` colin 0 siblings, 0 replies; 8+ messages in thread From: colin @ 2005-09-20 9:11 UTC (permalink / raw) To: Andrew Morton, Vadim Lobanov; +Cc: pazke, linux-kernel Hi all, Andrey's suggestion can solve the compiling problem. I also tested the problem that Vadim had just said. I found that the marco version of printk indeed will have the problem in this kind of situation: printk("foo %d\n", bar()); bar() in marco version of printk won't be called. Because someone may put meaningful instructions in it, it may cause error. Is there any better solution of definition of printk that can greatly reduce size? BTW, I see many function definitions in kernel using "do {} while(0);". Do they have this kind of potential problem, too? Regards, Colin ----- Original Message ----- From: "Andrew Morton" <akpm@osdl.org> To: "Vadim Lobanov" <vlobanov@speakeasy.net> Cc: <pazke@donpac.ru>; <colin@realtek.com.tw>; <linux-kernel@vger.kernel.org> Sent: Tuesday, September 20, 2005 4:03 PM Subject: Re: CONFIG_PRINTK doesn't makes size smaller > Vadim Lobanov <vlobanov@speakeasy.net> wrote: > > > > On Tue, 20 Sep 2005, Andrey Panin wrote: > > > > > On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > > > > > > > Hi there, > > > > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > > > > smaller, but it didn't because it actually isn't an empty function, and > > > > there are many copies of it in vmlinux, not just one. Here is its > > > > definition: > > > > static inline int printk(const char *s, ...) { return 0; } > > > > > > > > I change the definition to this and it can greatly reduce the size by about > > > > 5%: > > > > #define printk(...) do {} while (0) > > > > However, this definition would lead to error in some situations. For > > > > example: > > > > 1. (printk) > > > > 2. ret = printk > > > > > > > > I hope someone could suggest a better definition of printk that can both > > > > make printk smaller and eliminate errors. > > > > > > What about the macro below ? > > > > > > #define printk(...) ({ do { } while(0); 0; }) > > > > So what does the do-while loop give us in the above case? In other > > words, why not just do the following...? > > > > #define printk(...) ({ 0; }) > > > > You may find that when printk() is a static inline there are still copies > of the control string in the generated kernel image: > > printk("foo %d\n", bar()); > > must still evaluate bar() and may cause "foo %d\n" to turn up in vmlinux. > IIRC later versions of gcc do remove the unreferenced string. > > If printk is a macro, it all of course disappears. ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 7:48 ` Vadim Lobanov 2005-09-20 8:03 ` Andrew Morton @ 2005-09-20 9:02 ` Andrey Panin 2005-09-20 15:41 ` Vadim Lobanov 1 sibling, 1 reply; 8+ messages in thread From: Andrey Panin @ 2005-09-20 9:02 UTC (permalink / raw) To: Vadim Lobanov; +Cc: colin, linux-kernel On 263, 09 20, 2005 at 12:48:59AM -0700, Vadim Lobanov wrote: > On Tue, 20 Sep 2005, Andrey Panin wrote: > > > On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > > > > > Hi there, > > > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > > > smaller, but it didn't because it actually isn't an empty function, and > > > there are many copies of it in vmlinux, not just one. Here is its > > > definition: > > > static inline int printk(const char *s, ...) { return 0; } > > > > > > I change the definition to this and it can greatly reduce the size by about > > > 5%: > > > #define printk(...) do {} while (0) > > > However, this definition would lead to error in some situations. For > > > example: > > > 1. (printk) > > > 2. ret = printk > > > > > > I hope someone could suggest a better definition of printk that can both > > > make printk smaller and eliminate errors. > > > > What about the macro below ? > > > > #define printk(...) ({ do { } while(0); 0; }) > > So what does the do-while loop give us in the above case? In other > words, why not just do the following...? do-while loop eliminates "statement with no effect" warnings from gcc4. > #define printk(...) ({ 0; }) > -- Andrey Panin | Linux and UNIX system administrator pazke@donpac.ru | PGP key: wwwkeys.pgp.net ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 9:02 ` Andrey Panin @ 2005-09-20 15:41 ` Vadim Lobanov 0 siblings, 0 replies; 8+ messages in thread From: Vadim Lobanov @ 2005-09-20 15:41 UTC (permalink / raw) To: Andrey Panin; +Cc: colin, linux-kernel On Tue, 20 Sep 2005, Andrey Panin wrote: > On 263, 09 20, 2005 at 12:48:59AM -0700, Vadim Lobanov wrote: > > On Tue, 20 Sep 2005, Andrey Panin wrote: > > > > > On 263, 09 20, 2005 at 02:14:55PM +0800, colin wrote: > > > > > > > > Hi there, > > > > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > > > > smaller, but it didn't because it actually isn't an empty function, and > > > > there are many copies of it in vmlinux, not just one. Here is its > > > > definition: > > > > static inline int printk(const char *s, ...) { return 0; } > > > > > > > > I change the definition to this and it can greatly reduce the size by about > > > > 5%: > > > > #define printk(...) do {} while (0) > > > > However, this definition would lead to error in some situations. For > > > > example: > > > > 1. (printk) > > > > 2. ret = printk > > > > > > > > I hope someone could suggest a better definition of printk that can both > > > > make printk smaller and eliminate errors. > > > > > > What about the macro below ? > > > > > > #define printk(...) ({ do { } while(0); 0; }) > > > > So what does the do-while loop give us in the above case? In other > > words, why not just do the following...? > > do-while loop eliminates "statement with no effect" warnings from gcc4. > > > #define printk(...) ({ 0; }) > > Funky: gcc3.3.4 seems to like it just fine. I am rather curious why gcc4 has different semantics in this case. But that is probably off-topic for this list... In either case, as Andrew Morton pointed out, function invokations as arguments don't get expanded out in the case of it being a macro, so no dice. > -- > Andrey Panin | Linux and UNIX system administrator > pazke@donpac.ru | PGP key: wwwkeys.pgp.net > -VadimL ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: CONFIG_PRINTK doesn't makes size smaller 2005-09-20 6:14 CONFIG_PRINTK doesn't makes size smaller colin 2005-09-20 6:38 ` Andrey Panin @ 2005-09-20 8:30 ` Denis Vlasenko 1 sibling, 0 replies; 8+ messages in thread From: Denis Vlasenko @ 2005-09-20 8:30 UTC (permalink / raw) To: colin; +Cc: linux-kernel On Tuesday 20 September 2005 09:14, colin wrote: > > Hi there, > I tried to make kernel with CONFIG_PRINTK off. I considered it should become > smaller, but it didn't because it actually isn't an empty function, and > there are many copies of it in vmlinux, not just one. Here is its > definition: > static inline int printk(const char *s, ...) { return 0; } > > I change the definition to this and it can greatly reduce the size by about > 5%: > #define printk(...) do {} while (0) > However, this definition would lead to error in some situations. For > example: > 1. (printk) > 2. ret = printk > > I hope someone could suggest a better definition of printk that can both > make printk smaller and eliminate errors. I think isolated testcase (a preprocessed .c file) would be interesting. Use make dir/dir/file.i, reduce result to small .c file which shows the problem, and show it on lkml. -- vda ^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2005-09-20 15:41 UTC | newest] Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2005-09-20 6:14 CONFIG_PRINTK doesn't makes size smaller colin 2005-09-20 6:38 ` Andrey Panin 2005-09-20 7:48 ` Vadim Lobanov 2005-09-20 8:03 ` Andrew Morton 2005-09-20 9:11 ` colin 2005-09-20 9:02 ` Andrey Panin 2005-09-20 15:41 ` Vadim Lobanov 2005-09-20 8:30 ` Denis Vlasenko
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®