Автор Тема: Включить SPI  (Прочитано 430 раз)

Оффлайн fat laser

  • Новичок
  • *
  • Сообщений: 2
  • Лайков: 2
  • Карма: +0/-0
  • Замедлитель данных
    • Просмотр профиля
Включить SPI
« : Июнь 16, 2019, 10:00:06 pm »
Приветствую!

Для решения сельскохозяйственных задач широкого профиля возникла необходимость связать OrangePiZero и STM32 через SPI. Сказано - сделано. Точнее не сделано или сделано на половину. Провода припаял, рабочий код для Orange и STM запилил (благо там и там С), SPI на STM включил, дошел до SPI апельсина и всё... (Далее сквозь текст будут сочиться боль, разочарование и уныние) Две недели танцев с бубном, однотипных непонятных телодвижений и тонна перелопаченного интернет трафика.
По пунктам что и как делал:
1. Скачал с armbian.com образ для PiZero. Накатил на карту памяти.
2. Загрузил armbian с карты на апельсине. Через armbian-config подключил spi. В armbianEnv.txt добавил строчки с spi. Ребут.
3. Набираю ls -l /dev/*spi* и лицезрею строчку с spi0.0.
4. Ставлю WiringOp-Zero от товарища vladikoms. Билдю что поставилось. Запускаю sudo gpio readall. Радуюсь.
5. Набираю sudo gpio load spi. А в ответ
modprobe: FATAL: Module spi-sun7i not found in directiry /lib/modules/4.19.50-sunxi
gpio: Unable to load spi-sun7i


Поднял виртуалку с Lubuntu, думал собрать ядро как пишут armbian.com, но в настройке будущего ядра нигде в настройках нет явного указания включить spi. Для пущей уверенности собрал с десяток разных ядер. Лососнул. Честно сходил на linux-sunxi.org. Ничего не понял. Но периодически снова иду туда и через муки непонимания ищу знакомые буквы, так как подозреваю что модуль spi-sun7i их детище.

Короче, прошу помощи, подскажите, что нужно сделать, дабы оживить spi на апельсине.

П.С. Только что нашел на страничке http://linux-sunxi.org/Allwinner_SoC_Family где нерусским по белому написано что камню AllWinner H2+ (то бишь OrangePiZero) соответствует sun8i (кстати что sun8i вообще такое? Прошивка? Драйвер? Патч?). Сижу теперь чешу репу, какого хрена gpio просит spi-sun7i?
И Родина щедро поила меня желудочным соком...

Оффлайн AlDemin

  • Житель
  • ****
  • Сообщений: 496
  • Лайков: 162
  • Карма: +25/-1
  • OPi, OPi+, OPiOne, OPiZero, OPiPC2, BPi, RPiB.
    • Просмотр профиля
Re: Включить SPI
« Ответ #1 : Июнь 18, 2019, 09:50:15 pm »
sun8i, sun7i - это можно так сказать архитектура SoC.
Цитировать
ls -l /dev/*spi* и лицезрею строчку с spi0.0
- означает что модуль либо уже загружен либо перманентно вшит в ядро, lsmod посмотри на предмет spi.
Цитировать
WiringOp-Zero от товарища vladikoms.
- похоже сырая недоделка которая не понимает на каком SoC его запустили и какой модуль соответственно нужно загружать, если вообще нужно.

Оффлайн fat laser

  • Новичок
  • *
  • Сообщений: 2
  • Лайков: 2
  • Карма: +0/-0
  • Замедлитель данных
    • Просмотр профиля
Re: Включить SPI
« Ответ #2 : Июнь 19, 2019, 09:01:13 am »
Обожаю opensource и linux в частности, за то, что пока ищешь ответ на свой вопрос параллельно научишься собирать ядра, поднимать виртуалки, выучишь наизусть штук тридцать шелл команд, проштудируешь теорию SPI, освоишь осциллограф и приобретешь еще много полезных навыков  ;D ;D ;D

Ах, вы бы видели, господа, как я виртуозно наловчился, используя связку Filezilla + Putty, ничтоже сумняшеся править код в потрохах апельсина и тут же на лету его компилить  8)

Но ближе к делу. AlDemin, Вы правы. Это реально сырая недоделка. Люди, которые придут сюда по поисковому запросу - gpio: Unable to load spi-sun7i , имейте ввиду, на момент написания этого текста, данная библиотека для работы с SPI непригодна (и для работы с I2C кстати тоже). Я влез в исходники WiringOp-Zero (что надо был сделать сразу же) и честно говоря, не совсем понял логику автора этой библиотеки в разрезе работы с SPI. Вполне возможно, что там на перспективу заложен какой-то мне неведомый пока функционал. А вот ядро, которое качается с armbian.com уже имеет рабочий драйвер SPI. И все прекрасно с ним работается через стандартную «йобтель» функцию. Кстати, прикол еще в том, что в библиотеке WiringOp-Zero используется та же ioctl()  ;D

Короче, ручками запрограммировал работу с SPI на апельсине, благо там все уложилось в три команды: initSPI(), writeSPI и readSPI(). Так что народное хозяйство жди, автоматизация грядет!
Товарищи! Путь наш тернист, но перспективы радужны! (С) Великий Кормчий Мао.
И Родина щедро поила меня желудочным соком...

Оффлайн Dmitry

Re: Включить SPI
« Ответ #3 : Ноябрь 12, 2019, 04:19:18 pm »
Всем привет!

Тоже столкнулся проблемой включения SPI на Orange Pi Zero. Установил Debian Buster minimal от 03.11.2019 г, скачанную с armbian.com
armbianEnv.txt написал следующим образом:
verbosity=1
logo=disabled
console=serial
disp_mode=1920x1080p60
overlay_prefix=sun8i-h3
overlays=spi-spidev usbhost2 usbhost3 w1-gpio
param_spidev_spi_bus=0
param_spidev_spi_cs=0
param_w1_pin=PA20
param_w1_pin_int_pullup=1
rootdev=UUID=09e9478d-c7f2-4b16-a2d7-66f5313ff813
rootfstype=ext4
usbstoragequirks=0x2537:0x1066:u,0x2537:0x1068:u

Настраивал как указано тут: https://micro-pi.ru/включение-шины-spi-на-orange-pi/
После ребута появился /dev/spidev0.0

с помощью ictl пытаюсь работать с SPI (wiringOp пробовал - не заработало):

#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <iostream>
#include <linux/types.h>
#include <string.h>

int main(int argc, char *argv[])
{
struct spi_ioc_transfer tr;
int fd;
memset(&tr, 0, sizeof(struct spi_ioc_transfer));
fd = ::open("/dev/spidev0.0", O_RDWR);
        if(fd<0)
        {
            std::cout << "Can't open port" << std::endl;
        }
        else
        {
            std::cout << "Open port ok" << std::endl;
        }

const std::vector<char> v={'h','e', 'l', 'l', 'o'};
            std::vector<char> data(v);
            for(;;)
            {
                auto res=111;
                tr.len = data.size();
                tr.tx_buf = (uintptr_t)data.data();
                tr.tx_buf = (uintptr_t)data.data();

                res=ioctl(fd, SPI_IOC_MESSAGE(1), &tr);
                if(res<0)
               {
                      std::cout << "Can't transfer data. size=" << data.size() << std::endl;
                      perror(nullptr);
               }
               
                std::cout << "write res=" << res << std::endl;
                data=v;
            }
return 0;
}

Работа с ioctl вынесена в класс, тут написал в main(), чтобы не загромождать место.
Код отрабатывает (пишет, что write res=5), но на осциллографе тишина. Если код запускаю на Rasperyy Pi 3, то все нормально. Что еще нужно сделать? Спасибо!

Оффлайн Dmitry

Re: Включить SPI
« Ответ #4 : Ноябрь 13, 2019, 09:37:17 am »
Удалось поднять. Оказывается, нужно было указать param_spidev_spi_bus=1. Тогда в системе SPI будет /dev/spi1.0.
На сколько понял, на spi0.0 висит флешка.