Показаны сообщения с ярлыком linux. Показать все сообщения
Показаны сообщения с ярлыком linux. Показать все сообщения

воскресенье, 22 марта 2009 г.

CeBootLin - автозагрузка Linux/Android из WinCE на Loox 5XX (560/550)

Написал "bootloader" для загрузки Linux/Android из WinCE автоматически при включении КПК. Это не настоящий bootloader, так как он не имеет ничего общего с загрузочными секторами, это просто WinCE приложение, которое начинает свою работу как можно раньше, чтобы загрузить Linux. Я сделал это именно так, а не иначе, из-за того, что не хотел убить свою КПК изменением бут секторов или иметь сложный механизм перепрошивок, обновлений и т.д. Автозагрузка из WinCE мне показалась досточно неплохим решением, имеющим разве что 3-4 секундный проиграш, если сравнивать с нормальным bootloader'ом, который еще помучиться реализовать надо. Также, такая рализация позволяет достаточно легко пропустить загрузку Linux и продолжить загрузку WM5 или WM6.. Код основан на утилите Haret (спасибо им), но я удалил ненужные мне части. Так как загрузчик использует аппаратные регистры для работы с клавиатурой и подсветкой (GPIO/CPLD) Fujitsu Siemens Loox N560/C550, то без изменений кода данный загрузчик не заработает на другой модели КПК...
Когда КПК включается и начинается загрузка WinCE, то ядро WinCE читает список приложений из HKEY_LOCAL_MACHINE\init и запускает их. Таким способом загружается CeBootLin. CeBootLin начинает мигать подсветкой клавиатуры и ждет одну секунду. В то время, пока клавиатура подмигивает, пользователь может нажать и отпустить какую-нибудь кнопку КПК - это сигнал для CeBootLin не продолжать загрузку Linux. Если никакие кнопки нажаты не были, то CeBootLin попытается открыть \CeBootLin\default.txt и будет использовать его в качестве скрипта Haret для загрузки Linux'а.

Итого, чтобы поставить и настроить CeBootLin, надо проделать такие шаги:
1. Скачать CeBootLin.
2. Распаковать содержимое архива в корень основной памяти КПК. CeBootLin.exe должен быть доступен по пути \CeBootLin\CeBootLin.exe.
3. Поместить default.txt в каталог \CeBootLin. Файл default txt может например выглядеть так (для загрузки Andorid'а, например):

set MTYPE 1454
set KERNEL "\CeBootLin\zImage"
set CMDLINE "root=179:3 mem=62M rootdelay=3 boot_delay=0 init=/init console=tty0 fbcon=rotate:0 androidboot.console=tty0 android.checkjni=1"
set RAMADDR 0xA0200000
bootlinux

4. Поместить zImage в каталог \CeBootLin\.

5. Добавить в HKEY_LOCAL_MACHINE\init значение для Launch82 ="CeBootLin.exe" и Depend82 = 14 00.


6. Добавить в HKEY_LOCAL_MACHINE\Loader\SystemPath путь \CeBootLin\

7. Подождать 5 минут или типа того (WinCE нужно время, прежде чем она сохранит обновление в registry).
8. Перезагрузить КПК

Если возникнут какие-то проблемы, то первым делом стоит проверить, а грузит ли CeBootLin.exe вообще ядро... для этого достаточно просто его запустить.

В дальнейшем при желании можно сделать нормальный cab с setup'ом внутри, который, например, будет ставить андройд..

Здесь находятся исходные коды CeBootLinux. CeBootLinux лицензирован под GNU GPL.

воскресенье, 15 марта 2009 г.

Фотографии Android и Linux на Fujitsu-Siemens Loox N560


Сегодня судьба WM5 - загрузить Linux


Haret.. все что нужно - нажать Run


Android на Loox N560


Установка Debian'а на Loox N560


Установка Debian'а на Loox N560

Тестирование памяти на Loox N560/C550

Недавно набросал "утилиту" для тестирования памяти на Fujitsu-Siemens Loox N560/C550. Нужна она тем, кто перепаевает память (с 64М на 128М) и хочет проверить ее работоспособность "на месте" без переустановки WM5. Итак, для того, чтобы протестировать память КПК:
1. Качаем LooxMem128-v0.zip (чтобы тестировать 128Мб памяти) или LooxMem64-v0.zip (чтобы тестировать 64Мб памяти).
2. Заливаем распакованный архив на SD карточку.
3. Карточку вставляем в Loox и перегружаем КПК.
4. Не давая КПК заснуть, запускаем haret.exe из архива, что распаковывали на SD карточку.
5. После запуска haret.exe нужно нажать на Run.
6. Загрузится linux и появится предупреждение.
7. Читаем предупреждение и либо нажимаем на RESET (на попе у КПК) либо нажимаем enter..
ВНИМАНИЕ: Накачественная память при тестировании может сгореть (собственно "утилита" для этого и нужна, чтобы выявлять такую память). Ни я, ни авторы memtester ни кто иной кроме вас никакой ответственности за это нести не будет. Вы тестируете память на свой страх и риск!!

Замечание: При тестировании необходимо раз в 3-5 минут нажимать какую-нибудь кнопку КПК, чтобы КПК не заснула...
(Для портирования "утилиты" на другую платформу достаточно заменить ядро zImage и поправить default.txt.)

суббота, 14 марта 2009 г.

Ядро linux для Loox N560/C550 с рабочим CPLD и светодиодами

Добавил поддержку CPLD и светодиодов. Для CPLD был заюзан драйвер htc-gpio с перечислением адресов регистров CPLD на Fujitsu-Siemens Loox 5XX (N560/C550). Теперь CPLD доступен для других драйверов.

Примечательно, как в Linux'е реализована работа с CPLD. По сути, CPLD это чип, содержащий очень простую логику (за счет чего он очень быстр по сравнению с CPU), имеющий входные и выходные "ножки" (pins). Входные и выходные ножки - регистры - проецируются на определенную область памяти CPU. С логической точки зрения работа с CPLD заключается в переключении битов в регистрах CPLD в 0 или 1 (можно еще и читать оттуда, но я об этом тут не буду рассказывать..). Таким же образом выглядит работа с GPIO - общим вводом/выводом CPU: биты регистров CPU таким же образом принимают значение 0 или 1. В ядре Linux уже имеется драйвер GPIO, предоставляющий функции для работы с GPIO разработчикам платформенных драйверов. Также драйвер GPIO имеет механизм расширения, позволяющий другим драйверам/модулям проецировать заданные интервалы портов GPIO таким образом, что при обращении к такому порту произойдет вызов указанных при проецировании функций. Этот механизм используется CPLD драйвером htc-egpio для проецирования CPLD регистров на GPIO порты. Таким образом работа с CPLD идет через обыкновенные методы типа gpio_set_value.
На основе работающиго CPLD драйвера для Loox N560/C550 реализовал драйвер управления светодиодами КПК. Драйвер экспортирует методы и константы которые другие драйвера (wifi, gps, bluetooth, pm, ...) должны использовать для управления светодиодами. Также драйвер позволяет контролировать светодиоды из userspace пространства путем манипуляций с файлами sysfs.

Ниже перечисленны файлы и значения которые могут находиться:
/sys/devices/platform/loox5xx-leds.1/keyboard: on, off, any
- подсветка клавиатуры

/sys/devices/platform/loox5xx-leds.1/left_green: on, off, any
- зеленый светодиод с левой стороны. WM5 использует для индикации активности WiFi

/sys/devices/platform/loox5xx-leds.1/left_blue: on, off, any
- голубой светодиод с левой стороны. WM5 использует для индикации активности Bluetooth

/sys/devices/platform/loox5xx-leds.1/left_orange: on, off, any
- оранжевый светодиод с левой стороны. WM5 использует для индикации активности GPS на Loox N560

/sys/devices/platform/loox5xx-leds.1/right_green: on, off, any
- зеленый светодиод на правой стороне КПК. WM5 использует как светодиод доступный приложениям (нотификации и т.д.)

/sys/devices/platform/loox5xx-leds.1/right_orange: on, off, blink, any
- оранжевый светодиод с правой стороны КПК. WM5 использует для индикации процесса зарядки

Где:
on - светодиод включен независимо от желаний ядра,
off - светодиод выключен независимо от желаний ядра,
blink - светодиод мигает независимо от желаний ядра,
any - светодиод контролируется ядром.

Например, если установить right_orange в состояние on, то светодиод зарядки будет гореть независимо от того, заряжается КПК или нет. Это будет продолжаться до тех пор, пока в файл right_orange не будет записано значение any. После чего, первое же событие (установка КПК в крэдл и т.д.) переключит светодиод в соответствующее состояние. Sysfs интерфейс для светодиодов позволяет использовать светодиоды из программ для нотификации о событиях (пришла почта, кончается заряд и т.д.) с помощью всех доступных на устройстве светодиодов - насколько хватит фантазии. Например следующий shell код мигает подсветкой клавиатуры:

while true;
do echo on > /sys/devices/platform/loox5xx-leds.1/keyboard;
sleep 0.1;
echo off > /sys/devices/platform/loox5xx-leds.1/keyboard;
sleep 0.1;
# Condition for break...
done
echo any > /sys/devices/platform/loox5xx-leds.1/keyboard;


Актуальный патч на cupcake ядро андройда качать здесь.

вторник, 10 марта 2009 г.

Полезные команды для межплатформенной работы

Несмотря на то, что debian/emdebian уже содержат громадное количество пакетов под armel, иногда нужно собрать или пересобрать что-то из исходников.

Сборка пакетов в emdebian происходит например так:
emsource --arch armel -b memtester

Установка собранного пакета НЕ на целевом устройстве, а на хостовом, выполняется например вот так:

dpkg-cross -a armel -i zlib1g-dev_1.2.3.3.dfsg-13em1_armel.deb
При этом команда dpkg -l | grep zlib1g выдаст:

ii zlib1g-dev-armel-cross 1:1.2.3.3.dfsg-13em1

(dpkg-cross автоматически переназвала установленный пакет и разместила его содержимое в /usr/arm-linux-gnueabi)

Чтобы пользоваться командой emsource без привелегий root'а, надо настроить ~/.apt-cross/emsource например вот так:

workingdir: /home/akshaal/.apt-cross-working-dir

Сборка пакета под armel из исходников, которые уже развернуты и имеют каталог debian производится командой:

dpkg-buildpackage -aarmel

понедельник, 9 марта 2009 г.

Установка emdebian на PDA (C550/N560)

Последовательность действий, выполнив которую я без проблем установил debian на свой Fujitsu-Siemens Loox N560. Я предполагаю, что emdebian-tools уже установлен, а также стоят всякие кросскомпиляторы под arm платформу.

Первым делом необходимо собрать архив базовой системой:
cd /tmp;
mkdir grip/
sudo debootstrap --arch=arm --foreign lenny grip/ http://www.emdebian.org/grip/
cd grip/
sudo tar -czf /tmp/emdebian-grip-arm-debootstrap.tgz .
Теперь необходимо переразбить SD карточку выделив на ней раздел под linux:

cfdisk /dev/sdX
mkfs.ext3 /dev/sdXy

где sdX - это устройство с SD картой, а sdXy это раздел который предполагается использовать под linux. Теперь монтируем раздел и разворачиваем туда emdebian-grip-arm-debootstrap.tgz:

mount /dev/sdXy /mnt
cd /mnt
tar zxpvf /tmp/emdebian-grip-arm-debootstrap.tgz
ln -s bin/sh init
cd /tmp
umount /mnt

Теперь, когда раздел подготовлен, загружаем с него linux и выполняем следующие команды:
cd /debootstrap
export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
run ./debootstrap --second-stage
dpkg --configure -a
rm /init
cd /
ln -s sbin/init init
Теперь перегружаем linux еще раз. В этот раз должно появится приглашение залогинится. Используем root без пароля. И конфигурируем основные настройки:

echo 'nameserver 1.1.1.1' > /etc/resolv.conf
echo '127.0.0.1 localhost' > /etc/hosts
echo '172.16.0.2 myhost 172.16.0.2' >> /etc/hosts
echo 'myhost' > /etc/hostname

Вместо 1.1.1.1 нужно использовать IP DNS сервера. И снова перегружаем КПК. Теперь конфигурирем сеть:

ifconfig usb0 172.16.0.1 netmask 255.255.255.0
route add default gw 172.16.0.1
Убеждаемся, что сеть работает. Апгрейдим пакеты:

echo 'deb http://www.emdebian.org/grip/ sid main' > /etc/apt/sources.list
echo 'deb http://ftp.debian.org/debian/ sid main contrib non-free' >> /etc/apt/sources.list
apt-get update
apt-get dist-upgrade
apt-get install ...что угодно...

И теперь настраеваем сеть так как это положено (собственно это можно было зделать и раньше, но тут можно уже залогинится через ssh и нормально все сделать с помощью copy&paste с ББ...):
cat > /etc/network/interfaces
auto lo
iface lo inet loopback
allow-hotplug usb0
iface usb0 inet static
address 172.16.0.2
netmask 255.255.255.0
network 127.16.0.0
broadcast 172.16.0.255
gateway 172.16.0.1
dns-nameservers 1.1.1.1
dns-search your.domain

суббота, 7 марта 2009 г.

Ядро linux для Loox N560/C550 с рабочим usbnet'ом

После 3х дней мучений все-таки собрал ядро linux для Fujitsu-Siemens Loox N560/C550. Ядро брал с http://www.asm32.ru. Потратив еще несколько часов разобрался как запустить usbnet (сеть через обычный usb шнурок). Для этого пришлось дополнительно пропатчить pxa27x_udc.c. Сделал diff между текущей версией ядра андройда и теми исходниками (за 02-03-09), что выложены на asm32. В дальнейшем при обновлении ядра в cupcake'овской ветке можно будет просто накладывать этот патч сверху имея в результате и изменения под c550/n560 и исправления/дополнения внесенные в cupcake ветку. Вот итоговый патч в который также включены изменения для работы usbnet. В патче уже имеется .config, но там не включена поддержка usbnet. Вот другой config, он отличается от того, что в патче (а там тот, что выложен на asm32) поддержкой usbnet, выключенной power management (зачем не знаю, потом надо будет включить обратно), и настройкой для более крупного шрифта в консоли.. может еще чем-то.

Собирать ядро можно с помощью любого toolchain'а. Я пробовал собирать с помощью: crosstool-ng, emdebian, а также того, что идет вместе с ядром андройда. Остановился на emdebian'е. Для сборки ядра emdebian'ом необходимо выполнить:
make ARCH=arm CROSS_COMPILE=arm-linux-gnueabi-
Предварительно emdebian конечно же нужно установить, например так:

apt-get install emdebian-tool
emsetup --arch arm
Добавить:

deb http://www.emdebian.org/debian/ unstable main

в /etc/apt/sources.list и выполнить:
apt-get install linux-kernel-headers-arm-cross gcc-4.2-arm-linux-gnu


Готовое ядро запускается haret'ом с конфигом:

set MTYPE 1454
set KERNEL zImage
set CMDLINE "root=179:2 mem=60M rootdelay=3 boot_delay=0 init=/init console=tty0 fbcon=rotate:0 androidboot.console=tty0 android.checkjni=1"
set RAMADDR 0xA0200000
bootlinux

И самое главное! После того, как ядро закинуто на sd карточку, эту sd карточку нужно вставить в КПК и ребутнуть КПК. А уже только после этого грузить haret'ом ядро! Ибо ядро не грузится (либо грузится с вероятностью 10%), если:
1. КПК заснула, а потом ее разбудили.
2. Вы только что вставили в КПК карточку.
Наверное это бага драйвера wince...

P.S. Cupcake на который накладывается выложенный патч качается отсюда http://source.android.com/download

P.P.S. При сборке с поддержкой usbnet опцию CONFIG_USB_ETH_RNDIS
включать не следует! Ибо в этом случае ПК не может нормально соеденится с КПК.. ни cdc_ether ни cdc_subset не видят usb устройство.

среда, 4 февраля 2009 г.

Microsoft Windows Environment

Каждый раз перезжая на новое рабочую машину, я думаю - это последний раз, больше не придется.

1. Установить http://virtuawin.sourceforge.net/ и назначить переключение рабочих столов на Win-0 ... Win-9 - как общие столы.
Win-C для стола с Eclipse.
Win-I для всяких чатов.

2. Установить http://www.skynergy.com/hotkeyz.html
Назначить Win-z для запуска rxtv с zsh
Назначить Ctrl-Shift-f12 на закрытие окна
Win-Enter - maximize window
Shift-Win-Enter - restore window

3. Установить http://www.cygwin.com/ с пакетами python, perl, zsh, diff, patch, make, mc и еще кучей ползеных программ и утилит.

4. Если вдруг оказалось, что cygwin считает домашней директорией сетевой диск и из-за этого тормозит, то незабыть поменять home директорию в /etc/passwd

5. В /etc/passwd прописать /usr/bin/zsh А в домашнюю директорию положить .zshrc следующего содержания:

alias ls='ls --color'
alias ll='ls -l --color'
alias dfh='df -h'
alias duh='du -h'
alias rm="rm -i"
alias mc="mc -a"

alias c="cd /cygdrive/c"

alias cdp='cd /cygdrive/c/projects/'

export INPUTRC=$HOME/.inputrc

export HISTSIZE=80000
export HISTFILE=~/.history
export SAVEHIST=80000

setopt hist_ignore_dups append_history bsd_echo multios
setopt hist_ignore_all_dups
setopt SHARE_HISTORY

prompt=`echo -ne "%{\033[31m%}%n@%M:%B%30<..<%~%#%b "`

export EDITOR=vim

unsetopt beep

# ##########################################################################3
# -+--+-+ --+-+-

bindkey "\e[1~" beginning-of-line
bindkey '\eOH' beginning-of-line
bindkey "\e[2~" end-of-history
bindkey "\e[3~" delete-char
bindkey "\e[4~" end-of-line
bindkey "\eOF" end-of-line
bindkey "\e[5~" history-incremental-search-backward
bindkey "\e[6~" history-incremental-search-forward
bindkey "\e[A" history-beginning-search-backward
bindkey "\e[B" history-beginning-search-forward
bindkey "\e[C" forward-char
bindkey "\e[D" backward-char
bindkey "\e[7~" beginning-of-line
bindkey "\e[8~" end-of-line
bindkey "\e[3~" backward-delete-char
bindkey "\e[3~" delete-char


# ###########################################################################
chpwd precmd () {
laststatus=$?
[[ $laststatus != 0 ]] && print "\033[1,33m**** \033[1,31mExit code: $laststatus\n"

[[ -t 1 ]] || return
case $TERM in
*xterm*|*rxvt*|*(dt|k|E)term*) print -Pn "\e]2;%n@%M:%15<..<%~%<<\a"
;;
esac
}

preexec () {
[[ -t 1 ]] || return
case $TERM in
*xterm*|*rxvt*|*(dt|k|E)term*) print -Pn "\e]2;%n@%M:%15<..<%~%<< (%15>..>$1%>>)\a"
;;
esac
}

chpwd

# The following lines were added by compinstall

zstyle ':completion:*' completer _expand _complete
zstyle ':completion:*' expand prefix suffix

autoload -Uz compinit
compinit -u
# End of lines added by compinstall

6. В c:/cygwin положить файлик rxvt.bat:
@echo off

C:
chdir C:\cygwin\bin

set CYGWIN=codepage:oem tty binmode title
set TERM=cygwin
rxvt -geometry 90x30 -bg black -fg white -sr -sl 5000 -fn 10x20 -e c:/cygwin/bin/zsh --login -i

понедельник, 11 августа 2008 г.

Зедаржки в Java

Так как для задач управление домашней автоматикой я сделал не совсем очивидный выбор - Java, то, естественно, мне было необходимо настраивать работу Java приложения под требование иметь минимальные задержки на события. В результате, для того, чтобы получить имеющийся результат, пришлось предпринять следующие действия:

1. Пускать приложение с schedtool -n -20 -R -p 1 -e /opt/mywire/bin/mywire
Данная команда позволяет запустить приложение в realtime группе с приоритетом 1. Все приложение linux имеют приоритет 0 независимо от nice level'а. Таким образом работа нашего mywire всегда приоритетнее любой задачи.

2. В некоторых критичных нитях, с помощью обращения к native методу происходит установка приоритета в значение 40. Таким образом внутри самого приложения нити имеют разные приоритеты. Это опасно и может привести к блокировкам!

3. Для того, чтобы ни в коем случае mywire не оказался в свопе, память лочится с помощью обращения к native методу mlockall.

4. Сам java процесс пускается со следующими опциями:

-Xms30m -Xmx64m -XX:PermSize=15m -XX:MaxPermSize=30m
-XX:+UseTLAB -jvm server
-XX:MaxGCPauseMillis=20 -XX:+UseConcMarkSweepGC -XX:+CMSIncrementalMode
-XX:+CMSClassUnloadingEnabled
-XX:+ExplicitGCInvokesConcurrentAndUnloadsClasses
-XX:+BackgroundCompilation

Количество памяти, которое я отдаю под heap выбранно таким образом, чтобы сразу после сборки мусора (full gc), свободной памяти было где-то 60%.

Надеюсь ничего не забыл. Как результат мы имеем задержки порядки 10-16мс. При том, что библиотека quartz сама работает с дискретеностью в 10мс. Тоесть если ей сказать, что таску нужно запустить через 5мс, она ее все равно запустить через 10.

К сожалению раз в час происходит full gc или что-то типа того и это влечет за собой неожиданные задержки. Величина зависит от того, как совпадут время срабатывания и начало сборки мусора. В среднем это 200мс. Бывает и 500мс и 700мс. Будем думать как это побороть.

Вот графики:
Latency:


Память.


Видно, что в момент сборки мусора был всплеск задержек.

Предугадывая вопросы:
Java - чтобы писать быстрее.

Latency - в данном случае, это разница времени момента срабатывания таймера и времени, в которое данный таймер должен был сработать. Тоесть, например, если было сказано спать 100мс, а таймер проспал 120мс, то задержка 20мс.

Важность Latency заключается в том, что опрашивать некоторые датчики необходимо весьма часто, скажем датчик движения 2 раза в секунду. В моем варианте датчик движения замыкает размыкает контакты конденсатора давая ему зарядится, таким образом датчик напряжения 1-wire успеет заметить какой-нибудь заряд, даже если он пропустит сам импульс. Так вот если Latency будет слишком высокой (скажем 2-3 секунды), то срабатывания датчик может просто остаться незамеченным.

Кто озадачился вопросом, почему датчик движения не может сам сообщить о срабатывании, отвечу: 1-wire сеть может иметь только одного master'а, все остальные slave'ы.

четверг, 26 июня 2008 г.

Linux 2

Ну вроде разобрался с проблемой зависания. Это определенно не дрова видюхи - без них в консоли все равно висло. Это не перегрев - в винде все ok. Четыре зависших попыток компиляции ядра 2.6.25.9 под ядром 2.6.25.8 показали, что проблема воспроизводима легко. Под 2.6.24 удалось собрать 2.6.25.9. Но собрать под 2.6.25.9 ради теста саму 2.6.25.9 не получилось - висла. Скачал 2.6.26-rc8. Тестовая сборка под этим ядром прошла нормально. Проблемы с протоколом Samba исчезли (интересно, что scp как работала нормально, так и работает). Вроде жизнь наладилась. Всем спасибо за советы.

Итого. 2.6.25.6, 2.6.25.7, 2.6.25.8, 2.6.25.9 - на моей машине (64 бита, AMD) оказались не рабочими.

вторник, 24 июня 2008 г.

Linux

Задалбывает меня это. Вот все было круто, не знал я печали, как начались глюки. С чем связано понять не могу, но сходу:

Эпизодически, несколько раз в день система фризится напроч. Тоесть мышиный курсор не двигается, музыка не играет и т.д.
Если я в это время залогинен по VNC на зафризенную машину, то в момент этот, я могу максимум что сделать - запустить zsh и все. И то наверное потому, что он в кэш памяти сидит. Изображение прорисовывается по нажатию на кнопку. Например набрал su , но ничего не произошло. Нужно любую кнопку нажать, чтобы увидеть запрос на логин. Странное поведение. В логах ничего подозрительного нет. shutdown -r now не отрабатывает (программа вообще не похоже, что запускается).

Если копирую что-то по smb протоколу, то в файле только первые несколько кил нормальные, а дальше нули идут. Тоесть mp3 музыка играет пару сек и затыкается, если играть smb share'ы. При этом с другого компа доступ к томуже smb ресурсу работает без проблем и глюков. Если копируют mp3'ки мне на шару, то играет все нормально.
Даже не знаю что думать. Куллеры крутятся.. все как обычно. Винда на компе работает нормально, в т.ч. и Crysis. Ядро 2.6.25.(от 6 до 8). Никому ничего не напоминает?

понедельник, 19 мая 2008 г.

OWFS 2.7p4

Нашел багу в OWFS 2.7p4. Немного криво написанная блокировка приводила к обращению к уже освобожденному участку памяти. Проявлялось через 1сек-5мин (как повезет) при паралелльном обращении к датчикам: owfs выключалась либо молча либо с сообщением функции tsearch из glibc о поврежденном списке. GDB помог не сильно. Valgrind помог весьма - отличная тулзень, давно ей пользуюсь.
==16965== Thread 9:
==16965== Invalid read of size 4
==16965== at 0x405F7A5: LockGet (ow_locks.c:142)
==16965== by 0x4066195: FS_r_given_bus (ow_read.c:229)
==16965== by 0x40663B2: FS_read_distribute (ow_read.c:191)
==16965== by 0x40668AD: FS_read_postparse (ow_read.c:106)
==16965== by 0x4066AEA: FS_read (ow_read.c:58)
==16965== by 0x409E26D: fuse_fs_read (in /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A2A12: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A5F48: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A6EAF: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A86D5: fuse_session_process (in /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A4AD4: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40C8382: start_thread (in /lib/libpthread-2.7.so)
==16965== Address 0x43b8dc8 is 0 bytes inside a block of size 16 free'd
==16965== at 0x402465C: free (vg_replace_malloc.c:323)
==16965== by 0x41B281A: tdelete (in /lib/libc-2.7.so)
==16965== by 0x405F62B: LockRelease (ow_locks.c:164)
==16965== by 0x40662AD: FS_r_given_bus (ow_read.c:236)
==16965== by 0x40663B2: FS_read_distribute (ow_read.c:191)
==16965== by 0x40668AD: FS_read_postparse (ow_read.c:106)
==16965== by 0x4066AEA: FS_read (ow_read.c:58)
==16965== by 0x409E26D: fuse_fs_read (in /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A2A12: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A5F48: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A6EAF: (within /usr/lib/libfuse.so.2.7.3)
==16965== by 0x40A86D5: fuse_session_process (in /usr/lib/libfuse.so.2.7.3)

Пропатченная версия работает уже 2 часа без проблем. Если до вечера доработает без ошибок напишу в mailing list owfs.

Патч.

P.S. Valgrind показал мемори ликов на 4кб. Надо будет глянуть.. это конечно не 4мб, но если там не дебри, то почему бы не пофиксить...

воскресенье, 27 апреля 2008 г.

Linux: Thread Priorities in Java

Грустно мне. Приоритеты нитей в linux джава игнорирует.
http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4813310

Update: Решение кажется нашел. Разберусь до конца опишу подробнее.

пятница, 8 февраля 2008 г.

VNC

Посвящается тем, кто как я (до того как составил таблицу) мучается со вводом русских букв из виндового vncclient'а при работе на юниксовом vncserver'е.

Самое простое решение, что я нашел, без всяких извратов и прочего - это:
1-х. Нужно составить таблицу соответствия виндовых keysym'ов к keysym'ам linux'a и запускать vnc4 с аргументом -RemapKeys, так у меня получилось вот что:
0xb8->0x6a3,0xe9->0x6ca,0xf6->0x6c3,0xf3->0x6d5,
0xea->0x6cb,0xe5->0x6c5,0xed->0x6ce,0xe3->0x6c7,0xf8->0x6db,
0xf9->0x6dd,0xe7->0x6da,0xf5->0x6c8,0xfa->0x6df,
0xf4->0x6c6,0xfb->0x6d9,0xe2->0x6d7,0xe0->0x6c1,
0xef->0x6d0,0xf0->0x6d2,0xee->0x6cf,0xeb->0x6cc,
0xe4->0x6c4,0xe6->0x6d6,0xfd->0x6dc,0xff->0x6d1,
0xf7->0x6de,0xf1->0x6d3,0xec->0x6cd,0xe8->0x6c9,
0xf2->0x6d4,0xfc->0x6d8,0xe1->0x6c2,0xfe->0x6c0,
0xa8->0x6b3,0xc9->0x6ea,0xd6->0x6e3,0xd3->0x6f5,
0xca->0x6eb,0xc5->0x6e5,0xcd->0x6ee,0xc3->0x6e7,
0xd8->0x6fb,0xd9->0x6fd,0xc7->0x6fa,0xd5->0x6e8,
0xda->0x6ff,0xd4->0x6e6,0xdb->0x6f9,0xc2->0x6f7,
0xc0->0x6e1,0xcf->0x6f0,0xd0->0x6f2,0xce->0x6ef,
0xcb->0x6ec,0xc4->0x6e4,0xc6->0x6f6,0xdd->0x6fc,
0xdf->0x6f1,0xd7->0x6fe,0xd1->0x6f3,0xcc->0x6ed,
0xc8->0x6e9,0xd2->0x6f4,0xdc->0x6f8,0xc1->0x6e2,
0xde->0x6e0


2-х. Нужно сообщить xmodmap'у о том, какие символы он должен знать аутофбокс так сказать. vncserver конечно и сам их добавить может, но он сопровождает это сообщениями да и заглавные литеры при этом себя ведут не очень хорошо. Так что лучше все-таки заранее добавить. Я поместил в ~/.vnc/xstartup вот такие строки:
xmodmap -e "keycode 252 = Cyrillic_shorti Cyrillic_SHORTI"
xmodmap -e "keycode 251 = Cyrillic_tse Cyrillic_TSE"
xmodmap -e "keycode 250 = Cyrillic_u Cyrillic_U"
xmodmap -e "keycode 249 = Cyrillic_ka Cyrillic_KA"
xmodmap -e "keycode 248 = Cyrillic_ie Cyrillic_IE"
xmodmap -e "keycode 247 = Cyrillic_en Cyrillic_EN"
xmodmap -e "keycode 246 = Cyrillic_ghe Cyrillic_GHE"
xmodmap -e "keycode 245 = Cyrillic_sha Cyrillic_SHA"
xmodmap -e "keycode 244 = Cyrillic_shcha Cyrillic_SHCHA"
xmodmap -e "keycode 243 = Cyrillic_ze Cyrillic_ZE"
xmodmap -e "keycode 242 = Cyrillic_ha Cyrillic_HA"
xmodmap -e "keycode 241 = Cyrillic_hardsign Cyrillic_HARDSIGN"
xmodmap -e "keycode 240 = Cyrillic_ef Cyrillic_EF"
xmodmap -e "keycode 239 = Cyrillic_yeru Cyrillic_YERU"
xmodmap -e "keycode 238 = Cyrillic_ve Cyrillic_VE"
xmodmap -e "keycode 237 = Cyrillic_a Cyrillic_A"
xmodmap -e "keycode 236 = Cyrillic_pe Cyrillic_PE"
xmodmap -e "keycode 235 = Cyrillic_er Cyrillic_ER"
xmodmap -e "keycode 234 = Cyrillic_o Cyrillic_O"
xmodmap -e "keycode 233 = Cyrillic_el Cyrillic_EL"
xmodmap -e "keycode 232 = Cyrillic_de Cyrillic_DE"
xmodmap -e "keycode 231 = Cyrillic_zhe Cyrillic_ZHE"
xmodmap -e "keycode 230 = Cyrillic_e Cyrillic_E"
xmodmap -e "keycode 229 = Cyrillic_io Cyrillic_IO"
xmodmap -e "keycode 228 = Cyrillic_ya Cyrillic_YA"
xmodmap -e "keycode 227 = Cyrillic_che Cyrillic_CHE"
xmodmap -e "keycode 226 = Cyrillic_es Cyrillic_ES"
xmodmap -e "keycode 225 = Cyrillic_em Cyrillic_EM"
xmodmap -e "keycode 224 = Cyrillic_i Cyrillic_I"
xmodmap -e "keycode 223 = Cyrillic_te Cyrillic_TE"
xmodmap -e "keycode 222 = Cyrillic_softsign Cyrillic_SOFTSIGN"
xmodmap -e "keycode 221 = Cyrillic_be Cyrillic_BE"
xmodmap -e "keycode 220 = Cyrillic_yu Cyrillic_YU"

понедельник, 21 января 2008 г.

WayBack

Иногда возникает необходимость запустить приложение не в настоящем времени, а в прошлом или будущем. Обычно это нужно для тестирования приложения или для обхода устаревания evaluation license. Достигается это переводом системных часов, либо запуском приложения в vmware - оба этих метода имеют свои очевидные недостатки. К счастью в linux есть такая замечательная вещь как LD_PRELOAD, позволяющяя "переопределить" импортируемые функции приложения. Так, например, если подменить time, gettimeofday и clock_gettime - то программа с большой долей вероятности будет жить в том времени который нам нужен, в то время как вся остальная система будет жить в обычном временном русле. Для этих целей я написал небольшую C'ную библиотеку. Устанавливается библиотека как обычно make install.

Для примера, небольшое тестовое приложение на C:

void main () {
printf ("%lu\n", time(0));
}

Запускаем:

akshaal@...:/tmp% ./test
1200947571

akshaal@...:/tmp% WAYBACK_TODAY=1970.01.01 LD_PRELOAD=libwayback.so.0 /tmp/test
63225

akshaal@...:/tmp% WAYBACK_LOG_LEVEL=3 WAYBACK_TODAY=1970.01.01 LD_PRELOAD=libwayback.so.0 /tmp/test
Delta time: 3094082896
time modified
63257


Библиотека libwayback не возвращает константу. После запуска, она определяет разницу между текущим временем и желаемым и запоминает ее как delta. В дальнейшем все вызовы к функция возвращающим время перехватываются и delta прибваляется к результату. Таким образом время не стоит на месте и в то же время она очень близко к желаемому.

Например приложение на Java и стандартная утилита date:

import java.util.Date;

public class test {
public static void main (String[] args) {
System.out.println (new Date());
}
}

akshaal@...:/tmp% java test
Mon Jan 21 22:39:26 EET 2008

akshaal@...:/tmp% WAYBACK_TODAY=2010.11.27 LD_PRELOAD=libwayback.so.0 java test
Sat Nov 27 20:40:39 EET 2010

akshaal@...:/tmp% date
Mon Jan 21 22:41:20 EET 2008

akshaal@...:/tmp% WAYBACK_TODAY=2010.11.27 LD_PRELOAD=libwayback.so.0 date
Sat Nov 27 20:41:50 EET 2010


К сожалению данный способ может быть использован для обхода устаревания лицензии :) у программ к которым есть evaluation license ограниченная на определенный срок (например JProfiler 5, YourKit Profiler 7, InteliJ Idea и еще много). Я не проверял работает ли (но уверен, что да :) ) ибо предпочитаю опенсоурс софт и вообще это плохо и я против использования библиотеки для этих целей :).

В библиотеке существует опция WAYBACK_RESET, которая определяет сколько секунд будет происходить подмена времени. К сожалению и эта опция может быть использована в целях обмана программ проверяющих срок действия лицензии. К примеру, если программа проверяет лицензию при запуске, то WAYBACK_RESET несознательный человек установит в 5 секунд, и после 5с получит пройденную проверку и программу с актуальным временем.

Библиотека написана за час и не является Абсолютным Решением. Кому надо - юзают на свой страх и риск, а с меня никакого спросу.

P.S. Больше всего напарился с одной вещью. Запускаю свинговое приложение, а оно виснет. Думаю че за нахрен. Копался-копался... оказывается java юзает pthread_condwait и ей в качестве параметра передается не относительное время (время когда ожидание прекращается), а абсолютное! Пришлось и эту функцию переопределить и вычитать дельту. Но как я искал.. strace говорит, что нить висит на futex каком-то.. и только чудом догадался, что futex может быть более нижним лаером под pthread'ом, а там уже полез смотреть как работа с X'ами идет в libawt.

суббота, 5 января 2008 г.

CollectD

Грубо говоря - ни дня без патчей (хотя бы так, чем ничего). Провозившись с collectd нашел ошибку. Исправил. Патч (аж из трех новых строк) отослал. Может кто-то тоже возится, пытаясь понять, почему unixsock plugin для collectd не проставляет права на socket.
diff -urN old/src/unixsock.c new/src/unixsock.c
--- old/src/unixsock.c 2007-11-10 17:15:39.000000000 +0200
+++ new/src/unixsock.c 2008-01-05 20:45:17.000000000 +0200
@@ -29,6 +29,7 @@
#include <pthread.h>

#include <sys/socket.h>
+#include <sys/stat.h>
#include <sys/un.h>

#include <grp.h>
@@ -365,6 +366,8 @@
return (-1);
}

+ chmod (sa.sun_path, sock_perms);
+
status = listen (sock_fd, 8);
if (status != 0)
{

вторник, 23 октября 2007 г.

locale

Теперь так:
> echo $LANG
en_GB.UTF-8

Избавился еще от одной олдскульной вещи: локали в виде ru_RU.koi8-r. Пока пришлось заменить rxvt на rxvt-unicode-lite. Остальное вроде слега поднастроить и допилить. Centericq глючит (позицианирует курсор как будт-то вместо одного символа вставляются два (считает не символы а байты сволочь), но в пределах нормы, тем более, что в планах избавление от centericq. Рано или поздно это должно было случится.

суббота, 7 апреля 2007 г.

Сломал

На второй день после покупки сломал dreambox 500 (ресивер на linux для спутникового телевиденья). Циклится при загрузке. Как это чинить - идей нет, поэтому решил перепрошить. Щас с легкостью перепрошивается.

Такая вот фигня при загрузке:
[...]
Multiplex thread got Data
Command='ZAP'
Zap data ,
Multiplex thread got Data
Dropping connection
active count=0
rc=0 '0,'
------------> changed! 0
no transponder 1 444
[TUNE] tune failed
Segmentation fault

воскресенье, 25 марта 2007 г.

mmc

Сделал патч для MMC (консольный клиент для mud игр). С этим патчем mmc поддерживает 256 цветов в xterm/rxvt/putty, кривые терминалы (это когда "terminal cannot insert/delete characters") и символы с кейпада. Скриншот.

вторник, 13 марта 2007 г.

OSD Desktop

Еще один пост, который давно откладываю (уже годы). Вобщем, я записал ролик о том, как мой десктоп выглядит (640x480 10fps 2mb или 1024x768 10fps 6mb). Идея сделать его OSD'ным витала в воздухе задолго до того, как я написал первые строки кода. В результате эволюции десктопа, я привык работать в полноэкранном режиме. Часики, измерители и прочие пищали быстро сгинули с моего рабочего стола. И несмотря на то, что я оказался в мире без уведомлений, я был счастлив. И тогда OSD пришло ко мне как решение удержать программы в полноэкранном режиме и в то же время быть в курсе событий. Используя python и библиотеку OSD для него, я написал демона событий. Демон читает строки из файла ~/log/events и парсит их согласно шаблонам:
  • string - добавляет строку в список отображаемых строк.
  • [][][]\d\d\d\d: string - тоже самое, что и в предыдущем случае, но отображает строку заданное количество мс.
  • \d\d\:\d\d:\d\d: string - тоже, что и первый случай, но с датой. Дата не отображается на экране.
  • \d\d\:\d\d:\d\d: [][][]\d\d\d\d: string - тоже, что и второй случай, но с комментарием из третьего случая.
    После этого пришло время реализовать программы, которые писали бы в файл ~/log/events. Первой такой программой стала aktimelog, которая пишет события о текущем времени каждые 25 минут. Еще сделал: плагин для irssi, чтобы видеть публичные сообщения, приватные или и то и то, мониторить переключение раскладки клавиатуры, переключение рабочих столов, уведомления о почте, уведомления шела. Так же стоит сказать, что переключение рабочих столов происходит по шоткатам. Например, если вы нажимаете MOD-E, то в дополнение к переключению, ion3 проверяет а запущен ли emacs, и если не запущен и вы подтвердите запуск, то запускает его. Я обычно знаю, куда хочу переключиться, поэтому не трачу время на бег по списку программ или тыкание на тулбар (как это делают виндузятники и прочие линуксойды). Итого, MOD-e для emacs, MOD-p -- revelation, MOD-c -- eclipse, MOD-b -- browser, MOD-1 -- первый терминал, MOD-2 -- второй терминал... и тд. Вот так устроен мой десктоп. А ваш как? :)

    Исходники.
  •