Я пытаюсь написать оболочку bash script, которая потребляет большое количество ОЗУ на встроенном устройстве за определенное пользователем время. Как мне это сделать без использования массивов?
Напишите оболочку bash script, которая потребляет постоянное количество ОЗУ за определенное пользователем время
Ответ 1
Даже если традиционные Bash массивы не поддерживаются, все же возможно создать массивные переменные с помощью команды eval
встроенный в конкретную оболочку.
Следующий пример script основан на некоторых сценариях, которые я использовал при использовании BusyBox во встроенном проекте Linux. BusyBox использует оболочку Almquist (также известную как A Shell, ash и sh), который не поддерживает массивы.
#!/bin/ash
for index in 1 2 3 4 5; do
value=$(($index * 1024))
eval array$index=\"array[$index]: $value\"
done
for i in 1 3 5; do
eval echo \$array$i
done
Будьте осторожны при цитировании при использовании eval
!
Вывод:
array[1]: 1024
array[3]: 3072
array[5]: 5120
В зависимости от вашего конкретного сценария может быть достаточно script, аналогичного приведенному ниже.
#!/bin/ash
echo "Provide sleep time in the form of NUMBER[SUFFIX]"
echo " SUFFIX may be 's' for seconds (default), 'm' for minutes,"
echo " 'h' for hours, or 'd' for days."
read -p "> " delay
echo "begin allocating memory..."
for index in $(seq 1000); do
value=$(seq -w -s '' $index $(($index + 100000)))
eval array$index=$value
done
echo "...end allocating memory"
echo "sleeping for $delay"
sleep $delay
В моем кратком тестировании этот script потреблял от 570M до 575M физической памяти * за указанный период времени 5 минут.
* Мониторинг с использованием программ top и memprof в отдельных тестах
Ответ 2
Лично я бы пошел с Ником, потому что делать это на C будет намного проще.
Но... если вы действительно хотите избежать написания суперпростой C-программы, чтобы сделать это, тогда (если в системе работает Linux с правильным встроенным материалом), вы должны иметь возможность сделать это, установив tmpfs с ограничением по размеру любой памяти, которую вы хотите использовать, а затем извлечения данных в файл в этом tmpfs для его заполнения (например, путем копирования данных из бесконечного источника (например, /dev/zero
).
Программа C действительно проще, хотя, если вы можете скомпилировать ее для платформы.
Ответ 3
Вам нужно различать выделенное и рабочее ОЗУ. Легко есть память в bash:
A="0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
for power in $(seq 8); do
A="${A}${A}"
done
но если script часто перебирает данные, тогда эти страницы памяти являются хорошими кандидатами для замены.
Ответ 4
@JohnBartholomew
Ваша идея о монтировании tmpfs также не так сложна, и вы можете быть уверены, что она фактически потребляет ОЗУ, верно? (см. комментарий Криса Додда в ответ Ник)
mount -t tmpfs none /new/path/for/temp -o size=32m
dd if=/dev/zero of=/new/path/for/temp/zero.txt bs=32m count=1
Вероятно, dd
будет жаловаться, что на устройстве нет места. Кроме того, я не знаю, сколько оперативной памяти будет использоваться точно, но если вы говорите о MB, это должно быть хорошо.
Ответ 5
Если у вас есть устройство /dev/shm
, вы можете записать в файл, расположенный там, поскольку по умолчанию он имеет tmpfs.
Ответ 6
Я придумал это. /dev является tmpfs
#!/bin/sh
mntroot rw
cd /dev
while :
do
dd > /dev/null 2>&1 if=/dev/zero of=myfile1 count=25000 bs=1024 # eat up 25 MB of RAM
usleep 1
rm myfile1
done