Tested on Debian 12 on TS-7970. The contents of /etc/fw_env.config are:
root@tsimx6:~# strace fw_setenv testenvvar testval
execve("/usr/bin/fw_setenv", ["fw_setenv", "testenvvar", "testval"], 0xbe8ecda8 /* 15 vars */) = 0
brk(NULL) = 0x1eca000
mmap2(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6f9c000
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=13162, ...}) = 0
mmap2(NULL, 13162, PROT_READ, MAP_PRIVATE, 3, 0) = 0xb6f98000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libubootenv.so.0", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\230\f\0\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=13776, ...}) = 0
mmap2(NULL, 143568, PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6f74000
mmap2(0xb6f80000, 78032, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0) = 0xb6f80000
munmap(0xb6f74000, 49152) = 0
munmap(0xb6f94000, 12496) = 0
mprotect(0xb6f83000, 61440, PROT_NONE) = 0
mmap2(0xb6f92000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x2000) = 0xb6f92000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libc.so.6", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\3\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\251\344\1\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0755, stx_size=1102644, ...}) = 0
mmap2(NULL, 1139660, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0xb6e69000
mmap2(0xb6f73000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x109000) = 0xb6f73000
mmap2(0xb6f76000, 37836, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0xb6f76000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libz.so.1", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\0\0\0\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=132760, ...}) = 0
mmap2(NULL, 262392, PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6e28000
mmap2(0xb6e30000, 196856, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0) = 0xb6e30000
munmap(0xb6e28000, 32768) = 0
munmap(0xb6e61000, 28920) = 0
mprotect(0xb6e41000, 122880, PROT_NONE) = 0
mmap2(0xb6e5f000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1f000) = 0xb6e5f000
close(3) = 0
mmap2(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6f96000
set_tls(0xb6f96520) = 0
set_tid_address(0xb6f96088) = 510
set_robust_list(0xb6f9608c, 12) = 0
rseq(0xb6f96500, 0x20, 0, 0xe7f5def3) = 0
mprotect(0xb6f73000, 8192, PROT_READ) = 0
mprotect(0xb6e5f000, 4096, PROT_READ) = 0
mprotect(0xb6f92000, 4096, PROT_READ) = 0
mprotect(0x431000, 4096, PROT_READ) = 0
mprotect(0xb6fbb000, 4096, PROT_READ) = 0
ugetrlimit(RLIMIT_STACK, {rlim_cur=8192*1024, rlim_max=RLIM_INFINITY}) = 0
munmap(0xb6f98000, 13162) = 0
getrandom("\x3f\x6b\xc6\x39", 4, GRND_NONBLOCK) = 4
brk(NULL) = 0x1eca000
brk(0x1eeb000) = 0x1eeb000
openat(AT_FDCWD, "/etc/fw_env.config", O_RDONLY) = 3
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=202, ...}) = 0
read(3, "# SPI flash on the TS-7970/TS-79"..., 4096) = 202
readlink("/dev", 0xbeb76748, 1023) = -1 EINVAL (Invalid argument)
readlink("/dev/mtdblock0", 0xbeb76748, 1023) = -1 EINVAL (Invalid argument)
statx(AT_FDCWD, "/dev/mtdblock0", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFBLK|0660, stx_size=0, ...}) = 0
openat(AT_FDCWD, "/dev/mtdblock0", O_RDONLY) = 4
close(4) = 0
readlink("/dev", 0xbeb76748, 1023) = -1 EINVAL (Invalid argument)
readlink("/dev/mtdblock0", 0xbeb76748, 1023) = -1 EINVAL (Invalid argument)
statx(AT_FDCWD, "/dev/mtdblock0", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFBLK|0660, stx_size=0, ...}) = 0
openat(AT_FDCWD, "/dev/mtdblock0", O_RDONLY) = 4
close(4) = 0
close(3) = 0
openat(AT_FDCWD, "/var/lock/fw_printenv.lock", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3
flock(3, LOCK_EX) = 0
openat(AT_FDCWD, "/dev/mtdblock0", O_RDONLY) = 4
_llseek(4, 1048576, [1048576], SEEK_SET) = 0
read(4, "\312\f.f\0autoload=no\0baudrate=115200"..., 8192) = 8192
close(4) = 0
openat(AT_FDCWD, "/dev/mtdblock0", O_RDONLY) = 4
_llseek(4, 1572864, [1572864], SEEK_SET) = 0
read(4, "Z*%|\1autoload=no\0baudrate=115200"..., 8192) = 8192
close(4) = 0
openat(AT_FDCWD, "/dev/mtdblock0", O_RDWR) = 4
close(4) = 0
flock(3, LOCK_UN) = 0
close(3) = 0
exit_group(0) = ?
+++ exited with 0 +++
root@tsimx6:~# fw_printenv |grep testenv
root@tsimx6:~#
root@tsimx6:~# strace fw_setenv testenvvar testval
execve("/usr/bin/fw_setenv", ["fw_setenv", "testenvvar", "testval"], 0xbeea3da8 /* 15 vars */) = 0
brk(NULL) = 0x1e4e000
mmap2(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6efe000
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=13162, ...}) = 0
mmap2(NULL, 13162, PROT_READ, MAP_PRIVATE, 3, 0) = 0xb6efa000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libubootenv.so.0", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\230\f\0\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=13776, ...}) = 0
mmap2(NULL, 143568, PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6ed6000
mmap2(0xb6ee0000, 78032, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0) = 0xb6ee0000
munmap(0xb6ed6000, 40960) = 0
munmap(0xb6ef4000, 20688) = 0
mprotect(0xb6ee3000, 61440, PROT_NONE) = 0
mmap2(0xb6ef2000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x2000) = 0xb6ef2000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libc.so.6", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\3\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\251\344\1\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0755, stx_size=1102644, ...}) = 0
mmap2(NULL, 1139660, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0xb6dc9000
mmap2(0xb6ed3000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x109000) = 0xb6ed3000
mmap2(0xb6ed6000, 37836, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0xb6ed6000
close(3) = 0
openat(AT_FDCWD, "/lib/arm-linux-gnueabihf/libz.so.1", O_RDONLY|O_LARGEFILE|O_CLOEXEC) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\0\0\0\0004\0\0\0"..., 512) = 512
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=132760, ...}) = 0
mmap2(NULL, 262392, PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6d88000
mmap2(0xb6d90000, 196856, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0) = 0xb6d90000
munmap(0xb6d88000, 32768) = 0
munmap(0xb6dc1000, 28920) = 0
mprotect(0xb6da1000, 122880, PROT_NONE) = 0
mmap2(0xb6dbf000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1f000) = 0xb6dbf000
close(3) = 0
mmap2(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb6ef8000
set_tls(0xb6ef8520) = 0
set_tid_address(0xb6ef8088) = 519
set_robust_list(0xb6ef808c, 12) = 0
rseq(0xb6ef8500, 0x20, 0, 0xe7f5def3) = 0
mprotect(0xb6ed3000, 8192, PROT_READ) = 0
mprotect(0xb6dbf000, 4096, PROT_READ) = 0
mprotect(0xb6ef2000, 4096, PROT_READ) = 0
mprotect(0x451000, 4096, PROT_READ) = 0
mprotect(0xb6f1d000, 4096, PROT_READ) = 0
ugetrlimit(RLIMIT_STACK, {rlim_cur=8192*1024, rlim_max=RLIM_INFINITY}) = 0
munmap(0xb6efa000, 13162) = 0
getrandom("\xd5\xab\xb5\x18", 4, GRND_NONBLOCK) = 4
brk(NULL) = 0x1e4e000
brk(0x1e6f000) = 0x1e6f000
openat(AT_FDCWD, "/etc/fw_env.config", O_RDONLY) = 3
statx(3, "", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT|AT_EMPTY_PATH, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFREG|0644, stx_size=192, ...}) = 0
read(3, "# SPI flash on the TS-7970/TS-79"..., 4096) = 192
readlink("/dev", 0xbeb31748, 1023) = -1 EINVAL (Invalid argument)
readlink("/dev/mtd0", 0xbeb31748, 1023) = -1 EINVAL (Invalid argument)
statx(AT_FDCWD, "/dev/mtd0", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFCHR|0600, stx_size=0, ...}) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDONLY) = 4
ioctl(4, MIXER_READ(1) or MEMGETINFO, {type=MTD_NORFLASH, flags=MTD_WRITEABLE|MTD_BIT_WRITEABLE, size=0x800000, erasesize=0x1000, writesize=0x1, oobsize=0, padding=0}) = 0
close(4) = 0
readlink("/dev", 0xbeb31748, 1023) = -1 EINVAL (Invalid argument)
readlink("/dev/mtd0", 0xbeb31748, 1023) = -1 EINVAL (Invalid argument)
statx(AT_FDCWD, "/dev/mtd0", AT_STATX_SYNC_AS_STAT|AT_NO_AUTOMOUNT, STATX_BASIC_STATS, {stx_mask=STATX_BASIC_STATS|STATX_MNT_ID, stx_attributes=0, stx_mode=S_IFCHR|0600, stx_size=0, ...}) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDONLY) = 4
ioctl(4, MIXER_READ(1) or MEMGETINFO, {type=MTD_NORFLASH, flags=MTD_WRITEABLE|MTD_BIT_WRITEABLE, size=0x800000, erasesize=0x1000, writesize=0x1, oobsize=0, padding=0}) = 0
close(4) = 0
close(3) = 0
openat(AT_FDCWD, "/var/lock/fw_printenv.lock", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3
flock(3, LOCK_EX) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDONLY) = 4
_llseek(4, 1048576, [1048576], SEEK_SET) = 0
read(4, "\312\f.f\0autoload=no\0baudrate=115200"..., 8192) = 8192
close(4) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDONLY) = 4
_llseek(4, 1572864, [1572864], SEEK_SET) = 0
read(4, "Z*%|\1autoload=no\0baudrate=115200"..., 8192) = 8192
close(4) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDWR) = 4
ioctl(4, MIXER_WRITE(6) or MEMUNLOCK, {start=0x100000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
ioctl(4, MIXER_WRITE(2) or MEMERASE, {start=0x100000, length=0x1000}) = 0
_llseek(4, 1048576, [1048576], SEEK_SET) = 0
write(4, "\371\17\241Y\1autoload=no\0baudrate=115200"..., 4096) = 4096
ioctl(4, MIXER_WRITE(5) or MEMLOCK, {start=0x100000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
ioctl(4, MIXER_WRITE(6) or MEMUNLOCK, {start=0x101000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
ioctl(4, MIXER_WRITE(2) or MEMERASE, {start=0x101000, length=0x1000}) = 0
_llseek(4, 1052672, [1052672], SEEK_SET) = 0
write(4, "\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"..., 4096) = 4096
ioctl(4, MIXER_WRITE(5) or MEMLOCK, {start=0x101000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
close(4) = 0
openat(AT_FDCWD, "/dev/mtd0", O_RDWR) = 4
_llseek(4, 1572868, [1572868], SEEK_SET) = 0
ioctl(4, MIXER_WRITE(6) or MEMUNLOCK, {start=0x180000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
write(4, "\0", 1) = 1
ioctl(4, MIXER_WRITE(5) or MEMLOCK, {start=0x180000, length=0x1000}) = -1 EOPNOTSUPP (Operation not supported)
close(4) = 0
flock(3, LOCK_UN) = 0
close(3) = 0
exit_group(0) = ?
+++ exited with 0 +++
root@tsimx6:~# fw_printenv |grep testenv
testenvvar=testval
Tested on Debian 12 on TS-7970. The contents of
/etc/fw_env.configare:When trying to set a var:
Notice no call to
write()on the filedes of/dev/mtdblock0is called.However, if
fw_env.configuses/dev/mtd0instead of/dev/mtdblock0: