<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Erinome Lane &#187; грабли</title>
	<atom:link href="https://tt.erinome.net/tag/%d0%b3%d1%80%d0%b0%d0%b1%d0%bb%d0%b8/feed" rel="self" type="application/rss+xml" />
	<link>https://tt.erinome.net</link>
	<description>a bit of this, a bit of that...</description>
	<lastBuildDate>Mon, 23 Mar 2026 12:51:51 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>https://wordpress.org/?v=4.2.38</generator>
	<item>
		<title>qemu и эмуляция ARM</title>
		<link>https://tt.erinome.net/2020/02/912</link>
		<comments>https://tt.erinome.net/2020/02/912#comments</comments>
		<pubDate>Tue, 25 Feb 2020 07:52:13 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Софт]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=912</guid>
		<description><![CDATA[QEMU позволяет запускать программы, собранные для архитектур, отличающихся от архитектуры хост-машины, как известно. Чуть менее известно то, что с его помощью можно запустить эмулятор всей ЭВМ целиком и установить в него целую операционную систему иной архитектуры. И если с запуском &#8230; <a href="https://tt.erinome.net/2020/02/912">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>QEMU позволяет запускать программы, собранные для архитектур, отличающихся от архитектуры хост-машины, как известно. Чуть менее известно то, что с его помощью можно запустить эмулятор всей ЭВМ целиком и установить в него целую операционную систему иной архитектуры. И если с запуском x86_64 никаких проблем не возникнет (а на обычных PC по факту это просто виртуализация, а не эмуляция), то при попытке запустить эмулятор для ARM может обнаружиться, что систему туда так просто не установить: у эмулятора ARM нет ничего похожего на BIOS, который любезно организует старт установки с виртуального дисковода или флешки, а после установки &#8211; будет передавать загрузку в grub или его аналоги.<span id="more-912"></span></p>
<p>Попробуем организовать эмулятор для ARMv7 при помощи QEMU 4.20 и установим какой-нибудь Linux.</p>
<p>Для начала нам понадобится скачать так называемый netboot образ системы для armhf, состоящий из двух компонент: vmlinuz и initrd.gz. После ряда экспериментов выяснилось, что современные инсталляторы Ubuntu по умолчанию непригодны для этих целей, так что возьмем Debian Buster<a href="http://ftp.debian.org/debian/dists/buster/main/installer-armhf/current/images/netboot/" target="_blank" rel="noopener">[1]</a>.</p>
<p>Подготовим файл образа &#8220;диска&#8221;, в который будем устанавливать систему:</p>
<pre class="console">qemu-img create -f qcow2 debian.qcow2 8G</pre>
<p>В ряде инструкций рекомендуется подготовить сеть, подняв на хост-машине tap-интерфейс, что позволит иметь возможность достучаться с хост-машины в гостевую, но для упрощения ситуации запустим сеть в usermode &#8211; она работает достаточно быстро и для ряда задач её хватит.</p>
<p>Собираем файлы в одном месте и запускаем эмулятор со следующими параметрами:</p>
<pre class="console">qemu-system-arm -smp 4 -m 1024 -M virt \
   -kernel vmlinuz \
   -initrd initrd.gz \
   -append "root=/dev/ram" \
   -netdev user,id=n1
   -device virtio-net-device,netdev=n1 \
   -drive if=none,file=debian.img,format=qcow2,id=hd \
   -device virtio-blk-device,drive=hd \
   -no-reboot</pre>
<p>Параметры:</p>
<ul>
<li>smp &#8211; количество ядер;</li>
<li>m &#8211; объем памяти;</li>
<li>M &#8211; тип машины, virt &#8211; абстрактно-виртуальный ARM;</li>
<li>netdev &#8211; тип сети, user &#8211; самый простой вариант, не требующий настройки хост-машины;</li>
<li>device virtio-net-device &#8211; устройство &#8220;сетевой карты&#8221;, и выбирать следует именно это, а не упомянутое в различных инструкциях, т.к. иначе с огромной вероятностью вы наткнетесь на сообщение о том, что инсталлятор системы не обнаружил никаких сетевых устройств в системе;</li>
<li>drive if=none,file=debian.img,format=qcow2 &#8211; образ жесткого диска;</li>
<li>device virtio-blk-device &#8211; устройство &#8220;жесткого диска&#8221;, аналогично сети, этот вариант обнаруживается установщиком, многие другие &#8211; нет;</li>
<li>no-reboot &#8211; перезапуск системы приведет к остановке эмулятора.</li>
</ul>
<p>Если запускаем qemu-system-arm в консоли без графического интерфейса, то дописываем &#8220;-nographic&#8221;.</p>
<p>Устанавливаем Debian как обычно. На количестве ядер не следует экономить, т.к. в процессе установки есть этапы, которые, по всей видимости, могут неплохо параллелиться, а однопоточная производительность эмулятора далека от производительности хост-машины: в среднем на установку системы уходило около часа на четырехъядерном Intel Xeon 3.5 GHz.</p>
<p>Ближе к концу установки инсталлятор ругнется на невозможность установки grub &#8211; так и должно быть в этом эмуляторе.</p>
<p>Далее, когда инсталлятор сообщит о завершении, выберите &#8220;Go back&#8221; и из главного меню установщика выберите пункт про вход в консоль. В консоли целевой диск, куда производилась установка, будет доступен по пути /target. Поскольку у эмулятора нет загрузчика, нам понадобится вытащить уже из установленной системы соответствующие ей vmlinuz и initrd.img. Для этого можно сделать <em>chroot /target</em> и, используя набор стандартных утилит &#8211; например, scp &#8211; откопировать файлы, находящиеся в /target/boot (а после chroot так просто в /boot) куда-нибудь вовне эмулятора. Если установленных утилит не хватает, то уже в chroot-е можно легко использовать apt и apt-get для установки недостающего. После копирования выходим из консоли и в меню инсталлятора выбираем пункт завершения установки. Когда установщик выполнит перезагрузку, эмулятор просто выключится согласно опции no-reboot.</p>
<p>Конечно, в качестве альтернативы можно вынуть vmlinuz и initrd из установленной системы и при помощи средств конвертации и распаковки qcow2 файлов &#8211; таких инструкций в интернете уйма. В этом случае прежде, чем что-то сделать с образом диска, не забывайте остановить эмулятор, чтобы не повредить образ.</p>
<p>Причина же, по которой изначально не удалось использовать современные образы Ubuntu, состоит в том, что в них после установки по малопонятной причине не генерируется файл initrd.img &#8211; в директории /target/boot есть битые симлинки на него, тогда как сам initrd отсутствует. [<strong>Update</strong>: Способ исправления был найден в комментариях на gist.github.com<a href="https://gist.github.com/takeshixx/686a4b5e057deff7892913bf69bcb85a#gistcomment-2876366" rel="noopener" target="_blank">[2]</a>]</p>
<p>Итак, после описанных действий у вас должен оказаться на руках образ debian.img с установленной ОС и файлы vmlinuz и initrd.img, взятые из этого же образа. Старые vmlinuz и initrd.gz с netboot-инсталлятором можно удалить &#8211; они больше не понадобятся. Теперь для запуска системы нужно переписать аргументы qemu-system-arm на следующие:</p>
<pre class="console">qemu-system-arm -smp 4 -m 1024 -M virt \
   -kernel vmlinuz \
   -initrd initrd.img \
   -append "root=/dev/vda2" \
   -netdev user,id=n1
   -device virtio-net-device,netdev=n1 \
   -drive if=none,file=debian.img,format=qcow2,id=hd \
   -device virtio-blk-device,drive=hd \
   -no-reboot</pre>
<p>Вот, в общем-то, и всё.</p>
<p>Для того, чтобы зайти извне в такую гостевую машину по SSH, можно заменить <em>-netdev user,id=n1</em> на <em>-netdev user,hostfwd=tcp::10022-:22,id=n1</em>, и тогда при подключении к порту 10022 на хост-машине соединение будет перенаправлено на 22 порт гостевой машины. Либо воспользоваться ssh-туннелем, подняв из гостевой машины подключение к удаленному ssh-серверу с дополнительным параметром <em>-R 10022:localhost:22</em> &#8211; в этом случае порт 10022 на удаленном сервере будет перенаправлен на порт 22 гостевой машины. </p>
<p>Теперь можно пробовать собирать программы нативным компилятором нужной архитектуры, а не кросс-компиляцией. Ну или зачем там вы ещё запускали этот эмулятор.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2020/02/912/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Bitrix, opcache и утечки памяти</title>
		<link>https://tt.erinome.net/2019/09/904</link>
		<comments>https://tt.erinome.net/2019/09/904#comments</comments>
		<pubDate>Sun, 22 Sep 2019 16:23:07 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Софт]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=904</guid>
		<description><![CDATA[Появилась задача разобраться, отчего некий самописный компонент битрикса, где в цикле выполняется охренеллиард однотипных запросов к базе данных, после обновления PHP с 7.1 на 7.2 внезапно начал падать то в пустой экран, то в классический Fatal error: Allowed memory size &#8230; <a href="https://tt.erinome.net/2019/09/904">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Появилась задача разобраться, отчего некий самописный компонент битрикса, где в цикле выполняется охренеллиард однотипных запросов к базе данных, после обновления PHP с 7.1 на 7.2 внезапно начал падать то в пустой экран, то в классический <em>Fatal error: Allowed memory size of &#8230; bytes exhausted</em>.<span id="more-904"></span></p>
<p>После изучения означенного вопроса оказалось, что суть проблемы сводится к битриксовому API CIBlockElement::GetList() и соответствующему ему GetNext(), которые при <em>некоторых</em> условиях переставали высвобождать память после <em>каждого</em> своего вызова. Очевидно, что после попытки выполнения их по нескольку десятков тысяч раз внутри одного скрипта (который по расписанию перегенерирует карту сайта), разрешенный объем памяти в PHP довольно быстро заканчивался.</p>
<p>Тот факт, что ранее тот же самый код работал без подобных проблем, со временем вывел расследование на opcache, а конкретно &#8211; к оптимизации <em>ZEND_OPTIMIZER_PASS_6 (1&lt;&lt;5) /* DFA based optimization */</em>. По счастью, настройки opcache позволяют выбирать активные оптимизации и отключать те, что могут вызывать проблемы. Соответственно, в конфигурацию была добавлена следующая опция, отключающая только проблемную оптимизацию и оставляющая все остальные:</p>
<pre class="console">opcache.optimization_level=0x7FFEBFDF</pre>
<p>Понятно, что это могло привести к какой-то деградации производительности в opcache, но при выполнении означенных ранее циклов полностью перестала утекать память.</p>
<p>Для справки, полный список опциональных оптимизаций:</p>
<pre class="console">#define ZEND_OPTIMIZER_PASS_1		(1&lt;&lt;0)   /* CSE, STRING construction     */
#define ZEND_OPTIMIZER_PASS_2		(1&lt;&lt;1)   /* Constant conversion and jumps */
#define ZEND_OPTIMIZER_PASS_3		(1&lt;&lt;2)   /* ++, +=, series of jumps      */
#define ZEND_OPTIMIZER_PASS_4		(1&lt;&lt;3)   /* INIT_FCALL_BY_NAME -&gt; DO_FCALL */
#define ZEND_OPTIMIZER_PASS_5		(1&lt;&lt;4)   /* CFG based optimization       */
#define ZEND_OPTIMIZER_PASS_6		(1&lt;&lt;5)   /* DFA based optimization       */
#define ZEND_OPTIMIZER_PASS_7		(1&lt;&lt;6)   /* CALL GRAPH optimization      */
#define ZEND_OPTIMIZER_PASS_8		(1&lt;&lt;7)   /* SCCP (constant propagation)  */
#define ZEND_OPTIMIZER_PASS_9		(1&lt;&lt;8)   /* TMP VAR usage                */
#define ZEND_OPTIMIZER_PASS_10		(1&lt;&lt;9)   /* NOP removal                 */
#define ZEND_OPTIMIZER_PASS_11		(1&lt;&lt;10)  /* Merge equal constants       */
#define ZEND_OPTIMIZER_PASS_12		(1&lt;&lt;11)  /* Adjust used stack           */
#define ZEND_OPTIMIZER_PASS_13		(1&lt;&lt;12)  /* Remove unused variables     */
#define ZEND_OPTIMIZER_PASS_14		(1&lt;&lt;13)  /* DCE (dead code elimination) */
#define ZEND_OPTIMIZER_PASS_15		(1&lt;&lt;14)  /* (unsafe) Collect constants */
#define ZEND_OPTIMIZER_PASS_16		(1&lt;&lt;15)  /* Inline functions */

#define ZEND_OPTIMIZER_IGNORE_OVERLOADING	(1&lt;&lt;16)  /* (unsafe) Ignore possibility of operator overloading */</pre>
<p>PS: Всё это не было бы особо мозголомно, если бы не тот факт, что вся эта проблема наблюдалась на одном сайте и не наблюдалась на другом &#8211; в разных пулах PHP-FPM в рамках одного и того же сервера. Объяснение тому оказалось прямолинейным: там, где проблема не наблюдалась, opcache отчего-то не функционировал. Нет, не был выключен в настройках &#8211; он был включен, но просто перестал работать. После перезапуска FPM проблема начала одинаково воспроизводиться на обоих сайтах. Впоследствии, к слову, это же вынудило переустановить PHP из репозитория Remi, раз в официальном и версия PHP получала лишь обновления безопасности к старому релизу, а не обновления к более новым, и происходили подобные вещи. К сожалению, начальную проблему с DFA это обновление не исправило.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2019/09/904/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>FTP, passive mode и RHEL8</title>
		<link>https://tt.erinome.net/2019/08/901</link>
		<comments>https://tt.erinome.net/2019/08/901#comments</comments>
		<pubDate>Thu, 15 Aug 2019 08:36:36 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Софт]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=901</guid>
		<description><![CDATA[Мамонтовый протокол FTP предусматривает два режима работы для передачи данных &#8211; так называемые активный и пассивный режимы. Для активного режима требуется, чтобы у клиента был публичный IP-адрес и открытые порты, для пассивного &#8211; аналогичное должно быть сделано со стороны сервера. &#8230; <a href="https://tt.erinome.net/2019/08/901">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Мамонтовый протокол FTP предусматривает два режима работы для передачи данных &#8211; так называемые активный и пассивный режимы. Для активного режима требуется, чтобы у клиента был публичный IP-адрес и открытые порты, для пассивного &#8211; аналогичное должно быть сделано со стороны сервера. Удивительно то, что большинство современных инструкций по настройке vsftpd или proftpd предлагают просто выделить конкретный диапазон портов, прописать их в конфигурации FTP-сервера и разрешить к ним доступ в файрволе. Но зачем это делать, когда долгие годы существуют изощренные системы полностью автоматического разрешения доступа к портам при работе с FTP? А потому что по умолчанию они не работают.<span id="more-901"></span></p>
<p>Наглядный пример &#8211; RHEL8. Для чистого iptables и аналогов есть модули nf_conntrack_helper и, в частности, nf_conntrack_ftp. Интернет подсказывает, что в ядрах версии 4.7 и выше они по умолчанию отключены и требуют или ручного включения, или отдельной маркировки соединений. Но вот только у RHEL8 предлагается использовать надстройку FirewallD, мануал которого ещё в 2016 году <a href="https://firewalld.org/2016/10/automatic-helper-assignment" rel="noopener" target="_blank">упоминал автоматическое использование</a> соответствующего helper-а, если в конфигурации файрвола активирован стандартный сервис ftp, открывающий доступ к 21-му порту. Так, утверждается, что в выбранном по умолчанию режиме <em>AutomaticHelpers = system</em> должно проверяться значение <em>/proc/sys/net/netfilter/nf_conntrack_helper</em> (которое в >4.7 выключено) и, в зависимости от него, будут предприниматься необходимые меры для автоматического открывания портов для передачи данных через FTP. Но проблема в том, что этого не происходит.</p>
<p>Практический же опыт показывает, что помимо активации в файрволе сервиса ftp всё же необходимо в firewalld.conf дописать <em>AutomaticHelpers = on</em>, после чего никаких отдельных настроек портов для passive mode FTP не понадобится. Отчего это не работает в режиме <em>system</em> в релизной версии RHEL8 &#8211; неизвестно.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2019/08/901/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Статическая сборка pdns_server</title>
		<link>https://tt.erinome.net/2019/08/898</link>
		<comments>https://tt.erinome.net/2019/08/898#comments</comments>
		<pubDate>Sat, 10 Aug 2019 20:11:47 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Софт]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=898</guid>
		<description><![CDATA[При ручной сборке в ./configure у PowerDNS Authoritative Server есть ключи &#8211;enable-static и &#8211;enable-static-boost, позволяющие собрать бинарники статически, поскольку не всегда есть время и возможности угадывать, что и, главное, каких именно версий окажется установлено или доступно к установке на целевой &#8230; <a href="https://tt.erinome.net/2019/08/898">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>При ручной сборке в <em>./configure</em> у <strong>PowerDNS Authoritative Server</strong> есть ключи <em>&#8211;enable-static</em> и <em>&#8211;enable-static-boost</em>, позволяющие собрать бинарники статически, поскольку не всегда есть время и возможности угадывать, что и, главное, каких именно версий окажется установлено или доступно к установке на целевой операционке. Если вам не повезло иметь операционку, где готового пакета с pdns не существует, а готовый к сборке чего попало сервер уже налажен.</p>
<p>Вот только при запуске успешно собранного бинарника можно увидеть ошибку <em>pdns_server: /lib64/libstdc++.so.6: version `GLIBCXX_3.4.26&#8242; not found (required by pdns_server)</em><span id="more-898"></span></p>
<p>Она говорит о том, что указанная библиотека ни черта не прилинковалась статически.</p>
<p>Заставить ее это сделать можно дописыванием <em>LDFLAGS</em> перед запуском <em>./configure</em>:</p>
<pre class="console">LDFLAGS="-static-libstdc++" ./configure --with-modules="gmysql" --without-lua --enable-static --enable-static-boost --prefix=/</pre>
<p>Это отвяжет зависимость от версии <em>libstdc++</em> на целевой машине.</p>
<p>Говорят, для другого софта может пригодиться вбивание <em>-static-libgcc</em>, если он собирается CC, а общий <em>-static</em> попытается собрать всё остальное статически.</p>
<p>А так-то понятно, что лучше не собирать на коленке вручную, а использовать готовые пакеты требуемого софта для имеющейся операционной системы. Когда они есть в природе. Правда ведь, RHEL8?</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2019/08/898/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Miranda + ICQ</title>
		<link>https://tt.erinome.net/2018/04/868</link>
		<comments>https://tt.erinome.net/2018/04/868#comments</comments>
		<pubDate>Thu, 05 Apr 2018 14:52:39 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Разное]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=868</guid>
		<description><![CDATA[Последние год-два при попытке использовать ICQ в неофициальных клиентах вроде Miranda можно было столкнуться с тем, что часть клиентов всегда отображается находящейся в сети, даже когда это совсем не так, а также с фактом наличия пропущенных оффлайновых сообщений. Связано это &#8230; <a href="https://tt.erinome.net/2018/04/868">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Последние год-два при попытке использовать ICQ в неофициальных клиентах вроде Miranda можно было столкнуться с тем, что часть клиентов всегда отображается находящейся в сети, даже когда это совсем не так, а также с фактом наличия пропущенных оффлайновых сообщений.<span id="more-868"></span></p>
<p>Связано это с использованием любыми официальными клиентами (в т.ч. веб-интерфейсом) &#8220;обновленного&#8221; протокола ICQ, в котором клиент считается всегда находящимся в как-бы-в-сети, а также при подключении предполагает, что настоящий клиент самостоятельно запросит непрочтенные оффлайновые сообщения, висящие на псевдоонлайновом статусе, а не будет ждать, пока в него их насильно запихнут.</p>
<p>И если со статусами ничего сделать не получится, то с неприемом оффлайновых сообщений кое-как разобраться можно:</p>
<p>1. Добавляем в контакты бота по имени <em>aolsystemmsg</em>;<br />
2. Отправляем ему единицу &#8211; <em>1</em>.</p>
<p>Это разлогинит все имеющиеся сессии, включая псевдоонлайновые, кроме текущей. Если после этого заходить в ICQ <em>только</em> со старых клиентов, то они будут вполне корректно получать оффлайновые сообщения. Естественно, любой заход через современный официальный клиент приведет к тому, что его сессия после выхода останется висеть &#8220;в сети&#8221; и потребует нового сброса псевдоонлайновых сессий.</p>
<p>ЗЫ: А почему это до сих пор не исправят разработчики сторонних клиентов &#8211; так, похоже, никому это уже и не нужно.<br />
ЗЗЫ: Бот отвечает ещё до отправки вашего запроса. Машины времени и всё такое, да.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2018/04/868/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Акадо &#8217;18 [или никому не верь]</title>
		<link>https://tt.erinome.net/2018/03/859</link>
		<comments>https://tt.erinome.net/2018/03/859#comments</comments>
		<pubDate>Fri, 30 Mar 2018 17:30:05 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Разное]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=859</guid>
		<description><![CDATA[Чуть менее 10 лет назад я уже однажды распрощался с этим провайдером (что характерно, никогда к нему не подключаясь &#8211; он просто в то время мог позволить себе скупать чужие сети). Условия по тем временам складывались совсем не в его &#8230; <a href="https://tt.erinome.net/2018/03/859">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Чуть менее 10 лет назад я уже однажды распрощался с этим провайдером (что характерно, никогда к нему не подключаясь &#8211; он просто в то время мог позволить себе скупать чужие сети). Условия по тем временам складывались совсем не в его пользу, но теперь в какой-то момент времени оказалось, что у него можно получить чуть более лучший набор услуг, чем у моего прежнего ISP, при этом платя примерно в 1,94 раза меньше денег. А кроме того можно было бы ожидать, что резалка-крайне-запрещенных-по-мнению-роскомпозора-сайтов там будет работать не настолько отвратительно хотя бы потому, что хуже вряд ли есть куда. Так, спрашивается, почему бы и нет?<span id="more-859"></span></p>
<h3>Оформление заявки на сайте</h3>
<p>Заполнение формы заявки отличилось тем, что после нажатия на кнопку &#8220;Отправить&#8221; она радостно плевалась ошибкой, что я, бестолочь, не соизволил выбрать улицу. Пару раз вернувшись обратно, я удостоверился в том, что форма указания адреса, в целом, в курсе того, что в моем городе улицы для идентификации адресов не используются, но вот форме подключения про это никто не сказал. Полагаю, что не требуется говорить о том, что после каждого ухода со страницы с заполненной формой, эта форма сбрасывалась.</p>
<p>Клерк в чате отказался отвечать, действительно ли данный провайдер категорически не хочет подключать пользователей из городов с нестандартным форматом адреса, и предложил звонок менеджеру.</p>
<h3>Оформление заявки менеджером</h3>
<p>Описав менеджеру необходимые условия подключения, тот перепроверил адрес и заявил, что там подключение возможно только по коаксиальному кабелю, стоить будет в полтора раза дороже, а ещё и модем нужно будет брать в аренду. И никакой витой пары в моем доме нет и быть не может. &#8220;Точно?&#8221; &#8220;Точно!&#8221;</p>
<p>Странное дело, но мы, как неблагодарные абоненты, после таких новостей вдруг решили резко попрощаться, заявив, что на таких условиях нам это напрочь неинтересно. И ведь с нами попрощались, разве что безуспешно попытавшись прорекламировать ихнее телевидение, которое никого также нисколько не заинтересовало.</p>
<p>Однако, спустя символические пять минут, раздался звонок, суть содержания которого сводилась к следующему: они вдруг передумали, техническая возможность подключения по витой паре вдруг нашлась, а стоимость всего этого именно такая, как была изначально заявлена. Мистика? Ну, конечно.</p>
<h3>Ограничь всё, или как вытрясти денег</h3>
<p>По умолчанию этот провайдер подключает абонентов на приватные адреса из диапазона 10.0.0.0/8. А шел 2018 год. А про внешнюю динамику никто никогда и не слышал. Ну ладно, зато вдвое дешевле, причем за чуть более высокую скорость. </p>
<p>Но это не всё. Про DHCP и автоматическую раздачу сетевых настроек в этой сети тоже не слышали, поэтому при подключении на руки выдается листочек с параметрами сети. DNS-серверов в нем перечислено целых 4 штуки, и, похоже, не зря в интернете пишут, что они периодически падают (или падали в прошлом?). Но, казалось бы, зачем нам это &#8211; в интернете есть масса беспроблемных DNS-ок, можно просто пользоваться ими. Верно же? Неверно. Обращения ко внешним DNS-ам порезаны напрочь. Ну, вот просто так. И про GRE тоже можно не вспоминать.</p>
<p>Но решение, конечно, есть: купить статический внешний адрес. А это должно и разрыв по ценам подсократить. Впрочем, статика оказалась сравнительно недорогой &#8211; в сравнении с конкурентами. С обратной стороны это должно означать, что и здесь должен быть какой-то подвох.</p>
<h3>Приобретение статики</h3>
<p>В любом случае мне внешний адрес был нужен, поэтому я отправился смотреть возможности его получения. Официальный сайт утверждает о том, что можно отправить заявку через личный кабинет, и исполнена она будет не раньше, чем с первого дня следующего месяца, либо же советует обратиться к техподдержке, где могут быть и другие варианты. Я решил совместить приятное с полезным и обратиться к техподдержке через личный кабинет: невероятно, но там, в отличие от <del>мегафн</del>&#8230; в общем, там можно и такое.</p>
<p>Через двадцать минут после написания обращения, мне сообщили, что да, они могут подключить статический внешний адрес не дожидаясь начала месяца. Вот только денег при этом будет списано как за весь месяц целиком. Я мысленно поблагодарил работника техподдержки и мысленно пожелал провайдеру не лопнуть от жадности. После чего проследовал нажимать на кнопку автоматического подключения данной услуги в личном кабинете, потому что один фиг придется ждать.</p>
<h3>Тайна настроек, да и остальной набор тайн</h3>
<p>На следующее утро я обнаружил полностью неработающий интернет. После более внимательного осмотра я обнаружил, что сайт провайдера, как и личный кабинет, в общем-то доступны и работают. А уже их осмотр подсказал, что деньги за выделение статики (несколько сотен) и её поддержку (несколько копеек) списаны со счета уже прямо сейчас.</p>
<p>Вспоминая, что автоматически настройки в этой сети никто не выдает, вырисовывался логичный вывод: несмотря на утверждения, что через ЛК услугу можно получить только в следующем отчетном периоде, и несмотря на заверения о том, что если требовать ее подключить прямо сейчас, то у вас съедят впустую кучу денег &#8211; почему-то не сложилось ни то, ни другое. А адрес был выделен почти сразу, но сетевых настроек никто мне никуда не сообщил. И вообще, узнать их в ЛК нельзя. А со старыми настройками ничего не работает. По-моему, удобно.</p>
<h3><del>Доверяй, но проверяй.</del> Нет, просто проверяй</h3>
<p>Никуда не торопясь, ибо я заранее настроил роутер на работу с двумя провайдерами, я отписал в ту же удобную форму техподдержки в личном кабинете всё то, что я думаю о том, когда процесс подключения новых услуг организован на до такой степени высоком уровне. Заодно, запросил набор новых настроек, которые, естественно, тоже необходимо указывать вручную.</p>
<p>Ждать здесь пришлось на пару часов дольше, но в конечном счете я получил ответы на спрошенное. И не абы какие, а такие, что если внимательно вглядеться в полученную маску подсети, то можно было заметить, что указанный IP-адрес и указанный основной шлюз по таким настройкам попадают в разные подсети. Впрочем, по IP-калькулятору нетрудно подобрать более правильную маску, которая накроет оба адреса одновременно. Но домохозяек жалко.</p>
<h3>Резюме</h3>
<p>В общих чертах, оно работает. Просто на некоторые вещи лучше закрыть глаза.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2018/03/859/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>PPTP-клиент за NAT на основе Linux-сервера</title>
		<link>https://tt.erinome.net/2015/10/839</link>
		<comments>https://tt.erinome.net/2015/10/839#comments</comments>
		<pubDate>Thu, 29 Oct 2015 09:49:04 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Сеть и интернет]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[network]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=839</guid>
		<description><![CDATA[Небольшая локальная сеть на несколько компьютеров получала доступ в интернет через сервер на базе CentOS 6 &#8211; обычным NAT маскарадингом через iptables. Обнаружилось, что в такой конфигурации по умолчанию невозможно поднять VPN-туннель PPTP (протокол &#8211; GRE) с компьютеров, находящихся за &#8230; <a href="https://tt.erinome.net/2015/10/839">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Небольшая локальная сеть на несколько компьютеров получала доступ в интернет через сервер на базе CentOS 6 &#8211; обычным NAT маскарадингом через iptables. Обнаружилось, что в такой конфигурации по умолчанию невозможно поднять VPN-туннель PPTP (протокол &#8211; GRE) с компьютеров, находящихся за таким шлюзом.<span id="more-839"></span></p>
<p>Симптомы: на виндовых машинах подключение к VPN виснет на &#8220;проверке имени пользователя и пароля&#8221;, затем выдается ошибка 619. В логах PPTP-сервера видно, что он не получает отклика от клиента и сбрасывает подключение по таймауту, а в трафике видны только исходящие GRE-пакеты в сторону PPTP-клиента. На NAT-шлюзе в трафике при этом присутствуют и входящие, и исходящие GRE-запросы.</p>
<p>Спустя время было выявлено, что затык именно на стороне клиента, а именно на NAT-шлюзе: для работы PPTP на нем нужно подгрузить следующие модули (для CentOS):</p>
<pre class="console">modprobe ip_nat_pptp
modprobe ip_conntrack_pptp
modprobe ip_gre</pre>
<p>Несмотря на то, что, казалось бы, каких-либо открываний портов, или разрешений протоколов в файрволе, или других настроек на NAT-шлюзе для использования на стоящих за ним компьютерах PPTP-клиента не требуется, все-таки кое-что сделать придется. Так как с настройками по умолчанию (по крайней мере, для CentOS 6) GRE-трафик пропускаться не будет.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2015/10/839/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>icecast relay и редиректы</title>
		<link>https://tt.erinome.net/2015/09/830</link>
		<comments>https://tt.erinome.net/2015/09/830#comments</comments>
		<pubDate>Fri, 25 Sep 2015 08:24:29 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Сеть и интернет]]></category>
		<category><![CDATA[c/c++]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=830</guid>
		<description><![CDATA[Сервер icecast может использоваться не только для организации вещания новых сетевых медиапотоков, но и для ретрансляции уже существующих. Источник исходного потока при этом может являться распределенной структурой других icecast-подобных серверов, в которых для распределения нагрузки на головном сервере может использоваться &#8230; <a href="https://tt.erinome.net/2015/09/830">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Сервер icecast может использоваться не только для организации вещания новых сетевых медиапотоков, но и для ретрансляции уже существующих. Источник исходного потока при этом может являться распределенной структурой других icecast-подобных серверов, в которых для распределения нагрузки на головном сервере может использоваться простой http-редирект (код 302) на дополнительные узлы.</p>
<p>Хотя relay-функциональность icecast и позволяет разбирать этот код и реагировать на него соответствующим образом, работает это не всегда.<span id="more-830"></span></p>
<p>Можно столкнуться со следующей ситуацией: головной source-сервер перегружен и выдает редиректы на дополнительные серверы, при проверке браузером все корректно, но наш icecast-ретранслятор их будто &#8220;не замечает&#8221; и выдает клиентам ошибку 404. В логах нашего icecast&#8217;а при этом можно увидеть следующие записи:</p>
<pre class="console">[2015-09-25  10:58:40] INFO slave/start_relay_stream Starting relayed source at mountpoint "/&lt;mountname>"
[2015-09-25  10:58:40] INFO slave/open_relay_connection connecting to &lt;main.source>:80
[2015-09-25  10:58:40] INFO slave/open_relay_connection redirect received HTTP://&lt;fallback.source>
</pre>
<p>После этого клиенту выдается ошибка 404 и более ничего содержательного в лог не попадает. Так в чем же дело?</p>
<p>В исходном коде icecast можно найти следующие строки:</p>
<pre class="console">            ICECAST_LOG_INFO("redirect received %s", uri);
            if (strncmp (uri, "http://", 7) != 0)
                break;
</pre>
<p>Так выясняется, что если полученная ссылка из 302-го редиректа не начинается на &#8220;http://&#8221; (в НИЖНЕМ регистре!), то наш icecast с ней не будет делать вообще ничего и сделает вид, что никакого редиректа не было. А как видно из лога, наш источник рассылает редиректы, начинающиеся на HTTP:// в верхнем регистре.</p>
<p>Очевидно, надо научить icecast не обращать внимание на разницу регистров в протоколе. Это можно сделать разными способами, оптимальность и красота которых зависит от качества вашего владения <del>кунг-фу</del> Си. Можно, например, сделать как-то так:</p>
<pre class="console">--- icecast-2.4.2/src/slave.c   2015-04-08 11:06:13.000000000 +0300
+++ icecast-2.4.2-mod/src/slave.c       2015-09-25 10:55:29.495738535 +0300
@@ -238,13 +238,19 @@
         if (strcmp (httpp_getvar (parser, HTTPP_VAR_ERROR_CODE), "302") == 0)
         {
             /* better retry the connection again but with different details */
-            const char *uri, *mountpoint;
-            int len;
+            const char *uri, *mountpoint, *proc = "http://";
+            int i, len;

             uri = httpp_getvar (parser, "location");
+
             ICECAST_LOG_INFO("redirect received %s", uri);
-            if (strncmp (uri, "http://", 7) != 0)
-                break;
+            for (i = 0; i < 7 &#038;&#038; uri[i]; i++) {
+                if ((tolower(uri[i]) - tolower(proc[i])) != 0) {
+                    i = 10;
+                    break;
+                }
+            }
+            if (i == 10) break;
             uri += 7;
             mountpoint = strchr (uri, '/');
             free (mount);
</pre>
<p>Пересобираем, подключаемся, смотрим лог:</p>
<pre class="console">[2015-09-25  11:08:40] INFO slave/start_relay_stream Starting relayed source at mountpoint "/&lt;mountname>"
[2015-09-25  11:08:40] INFO slave/open_relay_connection connecting to &lt;main.source>:80
[2015-09-25  11:08:40] INFO slave/open_relay_connection redirect received HTTP://&lt;fallback.source>
[2015-09-25  11:08:40] INFO slave/open_relay_connection connecting to &lt;fallback.source>:80
[2015-09-25  11:08:40] WARN format/format_get_type Unsupported or legacy stream type: "audio/mpeg". Falling back to generic minimal handler for best effort.
[2015-09-25  11:08:40] INFO source/source_main listener count on /&lt;mountname> now 1</pre>
<p>И все работает.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2015/09/830/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Firefox: &#8220;Blocked: May contain a virus or spyware&#8221;</title>
		<link>https://tt.erinome.net/2015/04/816</link>
		<comments>https://tt.erinome.net/2015/04/816#comments</comments>
		<pubDate>Wed, 29 Apr 2015 14:59:05 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Сеть и интернет]]></category>
		<category><![CDATA[firefox]]></category>
		<category><![CDATA[грабли]]></category>
		<category><![CDATA[тупость]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=816</guid>
		<description><![CDATA[В отдельных ситуациях Firefox может возомнить себя намного умнее своего пользователя и напрочь блокирует возможность загрузки файлов с сайтов, которые его левой пятке захотелось посчитать небезопасными. При этом в окне загрузки отображается надпись вида &#8220;Blocked: May contain a virus or &#8230; <a href="https://tt.erinome.net/2015/04/816">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>В отдельных ситуациях <strong>Firefox</strong> может возомнить себя намного умнее своего пользователя и напрочь блокирует возможность загрузки файлов с сайтов, которые его левой пятке захотелось посчитать небезопасными. При этом в окне загрузки отображается надпись вида <em>&#8220;Blocked: May contain a virus or spyware&#8221;</em>, и нет никакой наглядной возможности обойти эту блокировку.<span id="more-816"></span></p>
<p>Проблема проявляется в виду того, что FF использует гугловскую базу ненадежных сайтов, которая запросто может ошибаться. Что любопытно &#8211; в Google Chrome применяется иной реестр вредоносных сайтов, и зачастую то, что [ошибочно] заблокировано в FF, успешно открывается в Хроме.</p>
<p>Так или иначе, но с проблемой нужно бороться &#8211; достаточно того, что наше любимое правительство решает, какие сайты нам смотреть можно, а какие &#8211; нельзя. Не хватало еще, чтобы и браузер начал указывать, что какой-нибудь архив или документ к скачиванию недопустим, а, следовательно, пожелавший его скачать пользователь может идти лесом (в другой браузер). И всё &#8211; из-за того, что разработчики FF не соизволили добавить кнопку одноразового обхода блокировки. Нет, такие удобства нам не нужны.</p>
<p>По счастью, выключать одним махом все проверки вредоносных сайтов не потребуется. Для решения проблемы нужно открыть страницу настроек &#8211; <em>about:config</em>, и переключить параметр <strong>browser.safebrowsing.downloads.enabled</strong> в положение <strong>false</strong>. Теперь FF позволит скачивать любые файлы.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2015/04/816/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>OpenWrt, libiconv и Full Language Support</title>
		<link>https://tt.erinome.net/2014/12/758</link>
		<comments>https://tt.erinome.net/2014/12/758#comments</comments>
		<pubDate>Tue, 23 Dec 2014 08:52:58 +0000</pubDate>
		<dc:creator><![CDATA[root]]></dc:creator>
				<category><![CDATA[Сеть и интернет]]></category>
		<category><![CDATA[openwrt]]></category>
		<category><![CDATA[грабли]]></category>

		<guid isPermaLink="false">http://tt.erinome.net/?p=758</guid>
		<description><![CDATA[Бывают ситуации, когда в OpenWrt не хватает полной языковой поддержки. Особенно, когда дело касается работы с кириллицей в кодировке UTF-8. Для таких случаев в OpenWrt предусмотрена неурезанная версия библиотеки libiconv-full, а также глобальная опция Compile with full language support. Вот &#8230; <a href="https://tt.erinome.net/2014/12/758">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
				<content:encoded><![CDATA[<p>Бывают ситуации, когда в <strong>OpenWrt</strong> не хватает полной языковой поддержки. Особенно, когда дело касается работы с кириллицей в кодировке UTF-8. Для таких случаев в <strong>OpenWrt</strong> предусмотрена неурезанная версия библиотеки <strong>libiconv-full</strong>, а также глобальная опция <em>Compile with full language support</em>.</p>
<p>Вот только скомпилировав прошивку с данными опциями выясняется, что никакой поддержки кириллических кодировок как не было, так и нет.<span id="more-758"></span></p>
<p>Разгадка кроется в малозаметном патче к <strong>libiconv-full</strong> под названием <em>100-strip-charsets.patch</em>. Пролистав его можно с удивлением обнаружить, что пакет, вроде бы имеющий в названии слово &#8220;full&#8221;, ничего общего с этим словом не имеет: доблестные разработчики <strong>OpenWrt</strong> в &#8220;полной&#8221; версии <strong>libiconv</strong> просто выпилили 97% всех кодировок, включая все упоминания кириллических, и оставив лишь несколько западноевропейских.</p>
<p>Наиболее простое решение &#8211; просто удалить патч <em>100-strip-charsets.patch</em> из пакета <strong>libiconv-full</strong>. Но так размер данной библиотеки увеличится в несколько раз! По этой причине мы сделали исправленную версию исходного патча, в которой оставлены кириллические кодировки, но вырезано большинство прочих.</p>
<p>Скачать исходный код модифицированного <strong>libiconv-full</strong> можно из <a href="http://fs.erinome.net/openwrt/packages/libiconv-full" target="_blank">нашего архива</a>.</p>
]]></content:encoded>
			<wfw:commentRss>https://tt.erinome.net/2014/12/758/feed</wfw:commentRss>
		<slash:comments>14</slash:comments>
		</item>
	</channel>
</rss>
