Bug 231

Summary: sysctl -p [file] doesn't work
Product: Busybox Reporter: Denys Fedoryshchenko <denys>
Component: OtherAssignee: unassigned
Status: RESOLVED FIXED    
Severity: major CC: busybox-cvs
Priority: P5    
Version: 1.14.x   
Target Milestone: ---   
Hardware: PC   
OS: Linux   
Host: i386 Target: i386
Build: 1.13.3
Attachments: Fix sysctl -p
Fix sysctl -p more

Description Denys Fedoryshchenko 2009-03-28 21:22:08 UTC
After upgrading from last 1.12 release i notice that modules.dep generated by included script depmod.pl will not work. For example latest kernel with garp compiled in (modprobe 8021q), or ppp. It will show unresolved symbols, and will load module on next attempt.
Default modules.dep generated by kernel tools is fine on new version, so it is just matter of documentation.

More big problem is sysctl
/etc/sysctl.conf content is:
net.ipv4.ip_forward=1
kernel.panic_on_oops=1
kernel.panic=5
vm.min_free_kbytes=16384
net.ipv4.tcp_max_syn_backlog=10240
net.ipv4.conf.all.arp_filter=1
vm.panic_on_oom=2
net.core.netdev_max_backlog=4000
net.ipv4.conf.default.send_redirects=0
net.ipv4.conf.all.send_redirects=0
net.ipv4.conf.eth0.send_redirects=0
net.ipv4.conf.eth1.send_redirects=0
net.ipv4.conf.eth2.send_redirects=0
net.ipv4.conf.eth3.send_redirects=0

after executing sysctl -p i will get:

sysctl: error: malformed setting '=1'
sysctl: error: malformed setting '=1'
sysctl: error: malformed setting '=5'
sysctl: error: malformed setting '=16384'
sysctl: error: malformed setting '=10240'
sysctl: error: malformed setting '=1'
sysctl: error: malformed setting '=2'


After some short debugging i notice:
               printf("%s|%s\n",token[1],token[0]);
                sprintf(parser->line, "%s=%s", token[0], token[1]); // must have room by definition
                printf("%s|%s\n",token[1],token[0]);

I will get:
1|net.ipv4.conf.default.rp_filter
1|=1
sysctl: error: malformed setting '=1'
Comment 1 Denys Vlasenko 2009-03-29 02:11:53 UTC
Created attachment 195 [details]
Fix sysctl -p

Please try attached patch, it should fix sysctl -p
Comment 2 Denys Vlasenko 2009-03-29 02:23:33 UTC
Committed as rev. 25872.
Comment 3 Denys Fedoryshchenko 2009-05-09 02:09:57 UTC
Sorry for long time, i just worked a bit on bug to find out whats wrong.
I added few debug lines

               /* parser->line is big enough for sprintf */
                printf("Len of line is %d, current value is %s, token[0] data %s len %d and token[1] data %s len %d\n",strlen(parser->line),parser->line,token[0],strlen(token[0]),token[1],strlen(token[1
                sprintf(parser->line, "%s=%s", token[0], token[1]);
                printf("!!! %s=%s / %s \n",token[0],token[1],parser->line);


Len of line is 19, current value is net/ipv4/ip_forward, token[0] data net/ipv4/ip_forward len 19 and token[1] data 1 len 1
!!! =1=1 / =1

If i disable compiler optimizations (CONFIG_DEBUG_PESSIMIZE) - everything becoming fine.
It seems compiler optimizing something and on sprintf he is screwing idea of reusing parser->line.

I test on multiple computers to make sure, that it is not my gcc fault.

Also i modify source a bit:
                /* parser->line is big enough for sprintf */
                printf("token[0]:'%s' parser->line:'%s'\n",token[0],parser->line);
                sprintf(parser->line,"testtest");
                printf("token[0]:'%s' parser->line:'%s'\n",token[0],parser->line);
                sprintf(parser->line, "%s=%s", token[0], token[1]);

and got:
token[0]:'net/ipv4/ip_forward' parser->line:'net/ipv4/ip_forward'
token[0]:'testtest' parser->line:'testtest'


and seems that token[0] have same address as parser->line?

Let me know if i should close this bug, but i think people who use gcc 4.3.3 will hit same bug.



Comment 4 Denys Vlasenko 2009-05-10 21:43:54 UTC
Created attachment 311 [details]
Fix sysctl -p more

Does this patch help?
Comment 5 Denys Fedoryshchenko 2009-05-10 22:02:32 UTC
Yes it does, i did something similar as workaround (with malloc), but seems this code much more beautuful. 
But still old code looks fine and should work, strange, why gcc does such strange things...
Comment 6 Denys Vlasenko 2009-05-10 23:35:09 UTC
sprintf(buf, "%s....", buf, ...) is not portable, I imagine. It makes sense to just avoid that.