0

It was explained e.g. here:

Get separate used memory info from free -m command

how to cut the output of free command. But I want to do this every few seconds and log it to a file. So I tried:

free -g -s2 | sed -n 's/^Mem:\s\+[0-9]\+\s\+\([0-9]\+\)\s.\+/\1/p' >> memory2.log

but the file stays empty. Why is that and how to fix it?

2 Answers2

1

I would use awk to form a much simpler command. Awk also uses output buffering, but the mawk that's on my Ubuntu desktop supports an option to use line buffering:

free -g -s2 | awk -W interactive '/^Mem:/ {print $2}'

(Note: on my computer, awk is linked to mawk via the Debian alternatives subsystem)

If you're going to run a shell loop to invoke free | awk then it becomes a very simple command:

while true; do
  free -g | awk '/^Mem:/ {print $2}' >> /path/to/memory2.log
  sleep 2
done
Sotto Voce
  • 3,664
  • 1
  • 8
  • 21
1

This happens because as far as I know sed buffers the input first, that means the command doesn't end so it won't get to the part where it gets appended (>>). To fix this simply use the -u / --unbuffered flag for sed:

free -g -s2 | sed -u -n 's/^Mem:\s\+[0-9]\+\s\+\([0-9]\+\)\s.\+/\1/p' >> memory2.log

Other solution would be to use a while loop:

while true; do free -g | sed -n 's/^Mem:\s\+[0-9]\+\s\+\([0-9]\+\)\s.\+/\1/p'; sleep 1; done >> memory2.log

Hope that helps :)

Pixelbog
  • 540
  • 2
  • 17
  • Another solution (that could work on any command and doesn't depend on a specific flag like `-u` for `sed`) is using [`stdbuf`](https://linux.die.net/man/1/stdbuf), for instance: `stdbuf -oL sed -n '...'`. But that's just for general knowledge, if the command supports unbuffering via a flag, it's better to use the command's native capabilities. – aviro Aug 17 '23 at 11:26