Skip to main content

Digital I/O (DIO)

Программируемый GPIO: 10-pin гребёнка на I2C GPIO-экспандере NXP PCA9554PW. Сидит на SMBus PCH, который общий с BMC (AST2500) — поэтому управляется и из хост ОС, и из BMC (даже при выключенном хосте). В BIOS setup и веб-морде BMC отдельных настроек нет. Единственная дока из мануала — Appendix D (только регистры).

Механизм​

  • Шина: SMBus PCH (Intel C620 i801, IOBASE 0x0780). Шина общая с BMC: на BMC она видна как i2c-0 (i2c-as-0), там видны те же устройства, и BMC управляет DIO даже при выключенном хосте
  • I2C адрес: 0x22 (7-bit). В мануале дефолт 0b0100100x = 0x24, но на плате A0..A2 припаяны как 010
  • Логика: 5В (чип питается от 5В, pull-up входов тоже на 5В)
  • Выходы push-pull, регистр input отражает реальное состояние пинов (включая выходы) — удобно как readback
  • По-умолчанию (после сброса) все пины — входы с подтяжкой вверх (config = 0xff)

Распиновка​

1DIO1GPIO0out2DIO8GPIO7in
3DIO2GPIO1out4DIO7GPIO6in
5DIO3GPIO2out6DIO6GPIO5in
7DIO4GPIO3out8DIO5GPIO4in
9NC——10GND——

Ряд выходов (1,3,5,7) — нечётные пины, ряд входов (2,4,6,8) — чётные, но пронумерованы «назад» (DIO8→pin2 … DIO5→pin8).

Регистры​

Командный байт — первый байт после адреса, указатель на регистр:

CmdРегистрДоступ
0Input portRead only
1Output portR/W
2Polarity inversionR/W
3ConfigurationR/W (0=out, 1=in)

Дефолты: config=0xff (всё входы), output=0xff, polarity=0x00.

Примеры​

Все примеры требуют i2c-tools и sudo.

Прочитать входы (биты 7:4)​

все входы — 1 (пул-ап), выходы в 0
$ i2cget -y 0 0x22 0
0xf0

Настроить GPIO3:0 как выходы и включить все​

$ i2cset -y 0 0x22 3 0xf0 # GPIO7:4 = in, GPIO3:0 = out
$ i2cset -y 0 0x22 1 0x0f # все 4 выхода в 1 (5В)

Включить конкретные пины​

Маска выхода = биты 0..3 → пины 1,3,5,7:

$ i2cset -y 0 0x22 1 0x05 # пины 1 (GPIO0) и 5 (GPIO2)
$ i2cset -y 0 0x22 1 0x00 # все выходы в 0

Readback выходов​

Input port отражает и выходы — записали, прочитали:

$ i2cset -y 0 0x22 1 0x0f && i2cget -y 0 0x22 0
0xff

Вернуть в стоковое состояние​

$ i2cset -y 0 0x22 3 0xff # всё входы
$ i2cset -y 0 0x22 1 0xff

Управление из BMC​

Шина общая, так что DIO можно дёргать с BMC. ВАЖНО: чип запитывается только при включённом хосте — без хоста запись ioctl-ом проходит, но пины остаются 0В (проверено на стенде). Так что для «джампер ресета BIOS» это не годится — для удалённого сброса BIOS используй IPMI boot flags.

В нашем моде dio лежит в payload-слоте, busybox-апплеты в /var/applets:

BMC
$ /var/payload/dio/dio.sh status # out=.. in=.. cfg=..
$ /var/payload/dio/dio.sh on 0x05 # GPIO0 и GPIO2 в 1 (пины 1 и 5)
$ /var/payload/dio/dio.sh pulse 0x01 2 # GPIO0 в 1 на 2 сек, потом в 0
$ /var/payload/dio/dio.sh off # все выходы в 0
$ /var/payload/dio/dio.sh reset # вернуть в сток

Прямые команды: /var/payload/dio/dio r /dev/i2c-0 0x22 <reg> / w. Проверено: запись с BMC видна с хоста и наоборот (при включённом хосте).

Заметки​

  • Чтобы определить направление/землю гребёнки без мануала: включить все выходы (0x0f) — 0В останется только на GND (pin 10) и NC (pin 9).
  • Выходы реально дёргают пины (проверено на стенде: input-port меняется за записями).
  • Без включённого хоста чип (PCA9554) обесточен — записи «проходят» (ACK), но напряжения на пинах нет; чтения с общей шины при выключенном хосте падают (известный баг host-off I2C).
  • 0x48 на той же шине — не DIO (весь регистр-флаг 0xff, похоже на EEPROM/другое устройство); 0x2f — термомонитор nct7802.