Подтвердить что ты не робот

Каков максимальный размер значения переменной среды?

Существует ли ограничение на количество данных, которое может быть сохранено в переменной среды в Linux, и если да: что это такое?

В Windows я нашел следующую статью статью в KB, которая суммирует: Windows XP или более поздней версии: 8191 символов Символы Windows 2000/NT 4.0: 2047

4b9b3361

Ответ 1

Я не думаю, что для Linux существует ограничение на переменную среды. Общий размер всех переменных среды, собранных вместе, ограничен во время execve(). Подробнее см. "Ограничения по размеру аргументов и среды" здесь.

Процесс может использовать setenv() или putenv() для расширения среды за пределами исходного пространства, выделенного exec.

Вот быстрая и грязная программа, которая создает переменную среды 256 МБ.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

int main(void)
{
    size_t size = 1 << 28; /* 256 MB */
    char *var;

    var = malloc(size);
    if (var == NULL) {
        perror("malloc");
        return 1;
    }

    memset(var, 'X', size);
    var[size - 1] = '\0';
    var[0] = 'A';
    var[1] = '=';

    if (putenv(var) != 0) {
        perror("putenv");
        return 1;
    }

/*  Demonstrate E2BIG failure explained by paxdiablo */
    execl("/bin/true", "true", (char *)NULL);
    perror("execl");   


    printf("A=%s\n", getenv("A"));

    return 0;
}

Ответ 2

Ну, это по крайней мере 4M на моей коробке. В этот момент мне стало скучно и блуждало. Надеюсь, выход терминала будет завершен, пока я не вернусь на работу в понедельник: -)

export b1=A
export b2=$b1$b1
export b4=$b2$b2
export b8=$b4$b4
export b16=$b8$b8
export b32=$b16$b16
export b64=$b32$b32
export b128=$b64$b64
export b256=$b128$b128
export b512=$b256$b256
export b1k=$b512$b512
export b2k=$b1k$b1k
export b4k=$b2k$b2k
export b8k=$b4k$b4k
export b16k=$b8k$b8k
export b32k=$b16k$b16k
export b64k=$b32k$b32k
export b128k=$b64k$b64k
export b256k=$b128k$b128k
export b512k=$b256k$b256k
export b1m=$b512k$b512k
export b2m=$b1m$b1m
export b4m=$b2m$b2m
echo $b4m
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
:    :    :    :    :    :    :    :    :    :    :    :
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA

Если вы обеспокоены тем, что 4M может быть недостаточно для вашей переменной среды, вы можете переосмыслить, как вы это делаете.

Возможно, было бы лучше поместить информацию в файл, а затем использовать переменную среды для ссылки на этот файл. Я видел случаи, когда переменная имеет форму @/path/to/any/fspec, она получает фактическую информацию из файла path/to/any/fspec. Если он не начинается с @, он использует значение самой переменной среды.


Интересно, что с учетом всех этих переменных каждая отдельная команда начинает жаловаться на то, что список аргументов слишком длинный, поэтому, даже если он позволяет вам их устанавливать, возможно, он не сможет запускать программы после того, как вы это сделали (поскольку он должен передать среду этим программам).

Ответ 3

Я провел быстрый тест на моем Linux-компьютере со следующим фрагментом:

a="1"
while true
do
    a=$a$a
    echo "$(date) $(numfmt --to=iec-i --suffix=B --padding=7 ${#a})" 
done

На моей коробке (Gentoo 3.17.8-gentoo-r1) это приводит к (последние строки вывода):

Wed Jan  3 12:16:10 CET 2018   16MiB
Wed Jan  3 12:16:11 CET 2018   32MiB
Wed Jan  3 12:16:12 CET 2018   64MiB
Wed Jan  3 12:16:15 CET 2018  128MiB
Wed Jan  3 12:16:21 CET 2018  256MiB
Wed Jan  3 12:16:33 CET 2018  512MiB
xrealloc: cannot allocate 18446744071562068096 bytes

Итак: предел довольно высок!

Ответ 4

Не знаю точно, но быстрый эксперимент показывает, что ошибки не возникает, например. с 64 КБ значения:

% perl -e 'print "#include <stdlib.h>\nint main() { return setenv(\"FOO\", \"", "x"x65536, "\", 1); }\n";'\
| gcc -x c -o envtest - && ./envtest && echo $?
0

Ответ 5

Я использовал этот очень быстрый и грязный php-код (ниже), изменяя его для разных значений и обнаружил, что он работает для переменной длины до 128k. После этого по какой-либо причине это не сработает; никакое исключение не возникает, ошибка не сообщается, но значение не отображается в подоболочке.

Может быть, это ограничение по php? Возможно, есть настройки php.ini, которые могут повлиять на него? Или, может быть, существует ограничение на размер варов, которые наследует подоболочка? Возможно, есть соответствующие настройки конфигурации ядра или оболочки.

В любом случае, по умолчанию, в CentOS, предел для установки var в среде через putenv в php, по-видимому, составляет около 128k.

<?php

  $s = 'abcdefghijklmnop';
  $s2 = "";
  for ($i = 0; $i < 8100; $i++) $s2 .= $s;
  $result = putenv('FOO='.$s2);
  print shell_exec('echo \'FOO: \'${FOO}');
  print "length of s2: ".strlen($s2)."\n";
  print "result = $result\n";
?>

Информация о версии -

[[email protected] scratch]# php --version
PHP 5.2.6 (cli) (built: Dec  2 2008 16:32:08) 
<..snip..>

[[email protected] scratch]# uname -a
Linux localhost.localdomain 2.6.18-128.2.1.el5 #1 SMP Tue Jul 14 06:36:37 EDT 2009 x86_64 x86_64 x86_64 GNU/Linux

[[email protected] scratch]# cat /etc/redhat-release 
CentOS release 5.3 (Final)

Ответ 6

Командная строка (со всем аргументом) плюс переменная среды должна быть меньше 128 тыс.

Ответ 7

очень полезно getconf -a |grep MAX или xargs --show-limits