2 * NVRAM variable manipulation (Linux user mode half)
4 * Copyright 2004, Broadcom Corporation
7 * THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
8 * KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
9 * SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
10 * FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
21 #include <sys/ioctl.h>
22 #include <sys/types.h>
29 #include <nvram_convert.h>
33 #define PATH_DEV_NVRAM "/dev/nvram"
36 static int nvram_fd
= -1;
37 static char *nvram_buf
= NULL
;
38 int check_action(void);
39 int file_to_buf(char *path
, char *buf
, int len
);
42 nvram_init(void *unused
)
44 if ((nvram_fd
= open(PATH_DEV_NVRAM
, O_RDWR
)) < 0)
47 /* Map kernel string buffer into user space */
48 if ((nvram_buf
= mmap(NULL
, NVRAM_SPACE
, PROT_READ
, MAP_SHARED
, nvram_fd
, 0)) == MAP_FAILED
) {
57 perror(PATH_DEV_NVRAM
);
62 nvram_get(const char *name
)
64 size_t count
= strlen(name
) + 1;
65 char tmp
[100], *value
;
66 unsigned long *off
= (unsigned long *) tmp
;
72 if (count
> sizeof(tmp
)) {
73 if (!(off
= malloc(count
)))
77 /* Get offset into mmap() space */
78 strcpy((char *) off
, name
);
80 count
= read(nvram_fd
, off
, count
);
82 if (count
== sizeof(unsigned long))
83 value
= &nvram_buf
[*off
];
88 perror(PATH_DEV_NVRAM
);
90 if (off
!= (unsigned long *) tmp
)
97 nvram_getall(char *buf
, int count
)
102 if ((ret
= nvram_init(NULL
)))
108 /* Get all variables */
111 ret
= read(nvram_fd
, buf
, count
);
114 perror(PATH_DEV_NVRAM
);
116 return (ret
== count
) ? 0 : ret
;
120 _nvram_set(const char *name
, const char *value
)
122 size_t count
= strlen(name
) + 1;
123 char tmp
[100], *buf
= tmp
;
127 if ((ret
= nvram_init(NULL
)))
130 /* Unset if value is NULL */
132 count
+= strlen(value
) + 1;
134 if (count
> sizeof(tmp
)) {
135 if (!(buf
= malloc(count
)))
140 sprintf(buf
, "%s=%s", name
, value
);
144 ret
= write(nvram_fd
, buf
, count
);
147 perror(PATH_DEV_NVRAM
);
152 return (ret
== count
) ? 0 : ret
;
156 nvram_set(const char *name
, const char *value
)
158 extern struct nvram_convert nvram_converts
[];
159 struct nvram_convert
*v
;
162 ret
= _nvram_set(name
, value
);
164 for(v
= nvram_converts
; v
->name
; v
++) {
165 if(!strcmp(v
->name
, name
)){
166 if(strcmp(v
->wl0_name
,"")) _nvram_set(v
->wl0_name
, value
);
167 if(strcmp(v
->d11g_name
,"")) _nvram_set(v
->d11g_name
, value
);
175 nvram_unset(const char *name
)
177 return _nvram_set(name
, NULL
);
185 cprintf("nvram_commit(): start\n");
187 if((check_action() == ACT_IDLE
) ||
188 (check_action() == ACT_SW_RESTORE
) ||
189 (check_action() == ACT_HW_RESTORE
)){
191 if ((ret
= nvram_init(NULL
)))
194 ret
= ioctl(nvram_fd
, NVRAM_MAGIC
, NULL
);
197 perror(PATH_DEV_NVRAM
);
199 cprintf("nvram_commit(): end\n");
202 cprintf("nvram_commit(): nothing to do...\n");
207 int file2nvram(char *filename
, char *varname
) {
211 char mem
[10000],buf
[30000];
213 if ( !(fp
=fopen(filename
,"rb") ))
216 count
=fread(mem
,1,sizeof(mem
),fp
);
218 for (j
=0;j
<count
;j
++) {
219 if (i
> sizeof(buf
)-3 )
222 if (c
>= 32 && c
<= 126 && c
!= '\\' && c
!= '~') {
223 buf
[i
++]=(unsigned char) c
;
228 sprintf(buf
+i
,"%02X",c
);
234 //fprintf(stderr,"================ > file2nvram %s = [%s] \n",varname,buf);
235 nvram_set(varname
,buf
);
236 //nvram_commit(); //Barry adds for test
239 int nvram2file(char *varname
, char *filename
) {
246 if ( !(fp
=fopen(filename
,"wb") ))
249 buf
=strdup(nvram_safe_get(varname
));
250 //fprintf(stderr,"=================> nvram2file %s = [%s] \n",varname,buf);
251 while ( buf
[i
] && j
< sizeof(mem
)-3 ) {
252 if (buf
[i
] == '\\') {
256 sscanf(buf
+i
,"%02X",&c
);
260 } else if (buf
[i
] == '~') {
269 j
=fwrite(mem
,1,j
,fp
);
280 if(file_to_buf(ACTION_FILE
, buf
, sizeof(buf
))){
281 if(!strcmp(buf
, "ACT_TFTP_UPGRADE")){
282 cprintf("Upgrading from tftp now, quiet exit....\n");
283 return ACT_TFTP_UPGRADE
;
285 else if(!strcmp(buf
, "ACT_WEBS_UPGRADE")){
286 cprintf("Upgrading from web (https) now, quiet exit....\n");
287 return ACT_WEBS_UPGRADE
;
289 else if(!strcmp(buf
, "ACT_WEB_UPGRADE")){
290 cprintf("Upgrading from web (http) now, quiet exit....\n");
291 return ACT_WEB_UPGRADE
;
293 else if(!strcmp(buf
, "ACT_SW_RESTORE")){
294 cprintf("Receive restore command from web, quiet exit....\n");
295 return ACT_SW_RESTORE
;
297 else if(!strcmp(buf
, "ACT_HW_RESTORE")){
298 cprintf("Receive restore commond from resetbutton, quiet exit....\n");
299 return ACT_HW_RESTORE
;
302 //fprintf(stderr, "Waiting for upgrading....\n");
307 file_to_buf(char *path
, char *buf
, int len
)
311 memset(buf
, 0 , len
);
313 if ((fp
= fopen(path
, "r"))) {