• Arduino denetleyicilerinde fiziksel olarak yerleşik en uygun iletişime bakalım. I2C protokolü üzerinden Arduino veri alışverişi

    I2C, arasındaki iletişim için seri asimetrik bir veri yoludur. Entegre devreler elektronik cihazların içinde. Yani bu protokol iletişim, bir cihaz kutusu içinde veya bir kalkan içinde interkom iletişimi için tasarlanmıştır. Verileri iletmekle görevli değildi. uzun mesafeler, bu yüzden maksimum iletişim menzili hakkında pek çok efsane var - biri için 50 cm'de, biri için 2 m'de zaten iyi çalışmıyor.

    I2C veriyolunda en fazla 128 cihaz bulunabilir. 0'dan 127'ye kadar adresler.

    Arduino denetleyicileri, onlara iki bilgi kablosu aracılığıyla bağlanmanıza izin veren I2C fiziksel iletişimine sahiptir. çeşitli sensörler, ayrık giriş-çıkışların genişleticileri, dijital-analog ve analogdan dijitale dönüştürücüler ve diğer denetleyiciler.

    Üreticinin web sitesi aktarım hızı hakkında yazmıyor. Ancak protokolün genel belgelerine göre en az 100 kbps olmalıdır.


    Şimdi I2C veri yolunun gerçekten ne kadar iyi olduğunu ve üzerindeki birkaç Arduino denetleyicisi arasında veri alışverişinin ne kadar zor olduğunu test etmek istiyorum.

    Üç denetleyici alacağım, onları bir I2C veriyoluna bağlayacağım ve bunun üzerinden nasıl veri alışverişi yapacağımı bulacağım. İlk kontrolör master, diğer ikisi ise slave olacaktır.

    Verileri görüntülemek için, aynı iletişim veriyoluna bağlanacak bir I2C modülü ile 1602 LCD göstergesi kullanacağım.

    Ana denetleyici, ikinci ve üçüncü denetleyicileri sırayla yoklayacaktır. İlk kontrolör alınan verileri göstergede göstermelidir. Arduino Nano köleleri 1 zaman/sn sıklıkta yoklanacaktır.

    Bağlantı şeması

    4 cihazın her birinden dört kablo paralel bağlanmalıdır. Sonuç A4 arduino panoları Nano, I2C protokolü SDA veriyoludur ve A5, SCL'dir.

    Kolay bağlantılar için Nano kontrolörler için montaj kalkanları kullanacağım.

    Güç, denetleyicilerden birine basit bir şekilde sağlanacaktır. küçük USB giriş.

    I2C ağındaki LCD adresi varsayılan olarak 27'dir.İkinci kontrolör için adresi 2, üçüncü kontrolör için 3 olarak ayarladık.Baştaki ilk kontrolör için adrese gerek yoktur.

    Denetleyici programı - sihirbaz.

    #katmak #katmak // 16 karakter ve 2 satırlık bir ekran için LCD adresini 0x27 olarak ayarlayın LiquidCrystal_I2C lcd(0x27, 16, 2); int nano1=0; int nano2; int nano3; void setup() ( Serial.begin(9600); // LCD'yi başlat lcd.begin(); // Siyah ışığı aç ve bir mesaj yazdır. lcd.backlight(); ) void loop() ( lcd.setCursor( 0, 0); lcd.print(nano1); Wire.requestFrom(2, 2); // bağımlı cihaz #8'den 6 bayt iste int i=0;nano2=0; while (Wire.available()) ( / / köle istenen bayttan daha az gönderebilir c = Wire.read(); // Serial.print(c) karakteri olarak bir bayt alır; if (i==0) nano2 = ((c & 0xff)<< 8); else nano2 = nano2 | c; i++; } Serial.println(""); Serial.println(nano2); lcd.setCursor(9, 0); lcd.print(nano2); delay(100); Wire.requestFrom(3, 2); // request 6 bytes from slave device #8 i=0;nano3=0; while (Wire.available()) { // slave may send less than requested byte c = Wire.read(); // receive a byte as character Serial.print(c); if (i==0) nano3 = ((c & 0xff) << 8); else nano3 = nano3 | c; i++; } lcd.setCursor(0, 1); lcd.print(nano3); delay(100); nano1++; delay(800); }

    Birinci denetleyici, tamsayı türü değişkenini değiştirir ve değerini göstergede görüntüler. Ayrıca sırasıyla 2. ve 3. adreslerle köleyi sorgular. Onlardan iki bayt bilgi ister, onları bir tamsayı değişkenine dönüştürür. Sonuç olarak, ilk denetleyicide üç Nano'dan üç değişken dönüyor ve bunları göstergede görüntüleyebilir.

    İkinci kontrol programı

    #katmak int nano2=0; bayt yüksek; void setup() ( Wire.begin(2); // i2c veriyoluna #8 adresiyle katılın Wire.onRequest(requestEvent); // olayı kaydet) void loop() ( delay(1000); nano2--; ) // master tarafından her veri istendiğinde yürütülen işlev // bu işlev bir olay olarak kaydedilir, bkz. setup() void requestEvent() ( high = (nano2 >>

    Üçüncü Arduino Nano Programı

    #katmak int nano2=0; bayt yüksek; void setup() ( Wire.begin(3); // i2c veriyoluna #8 adresiyle katılın Wire.onRequest(requestEvent); // olayı kaydet) void loop() ( delay(1500); nano2--; ) // master tarafından veri istendiğinde yürütülen işlev // bu işlev bir olay olarak kaydedilir, bkz. setup() void requestEvent() ( high = (nano2 >> 8); high = (nano2 & 0xff); Wire.write(high) ); // 2 baytlık mesajla cevap ver Wire.write(high); )

    Son iki program, Wire.begin(3) işlevindeki adrese göre farklılık gösterir; ve değişkenin değişim oranı.

    Bu programlar sürekli tamsayı değişkenini değiştirir ve master'dan bir istek bekler. İstendiğinde, bu değişken iki bayta ayrıştırılır ve ana denetleyiciye isteğe yanıt olarak gönderilir.

    Bu sayede I2C haberleşme işlemi LCD üzerinde üç değişkenin değişen değerleri ile izlenebilir.

    sonuçlar

    Her şey yolunda gidiyor - ekrandaki sayılar değişiyor. İkinci ve üçüncü arasındaki kabloyu uzatmaya çalıştım. Arduino denetleyicileri. 3 m uzunluğundaki iletişim veri yolunun ön gerilim olmadan çalışmasını kontrol ettim. Artık denemedim ama birçok kişi bana I2C'nin 0,5 ... 2 m'nin ötesinde çalışmadığını söyledi ve ben de 3 m uzunluğundan ilham aldım.

    Kendi adıma, üç Nano arasında böyle bir bağlantıyı nereye uygulayacağımı zaten görüyorum.

    Master'dan slave'e veri aktarımını henüz denemedim. Denerseniz lütfen abone olun.

    Buradaki dezavantajlar kısa mesafelerüstünlükten belirgin şekilde daha az.

    İhtiyacın olacak

    • -Arduino;
    • - dijital potansiyometre AD5171;
    • - Işık yayan diyot;
    • - 220 ohm direnç;
    • - 4,7 kOhm'luk 2 direnç;
    • - bağlantı kabloları.

    Talimat

    IIC seri iletişim protokolü (ayrıca I2C - Inter-Integrated Circuits, inter-chip bağlantısı olarak da adlandırılır), veri aktarımı için seri veri yolu adı verilen iki çift yönlü iletişim hattı kullanır. SDA(Seri Veri) ve saat veriyolu SCL(Seri Saat). Ayrıca iki elektrik hattı var. SDA ve SCL veri yolları, dirençler aracılığıyla güç rayına çekilir.
    Ağda en az bir ana cihaz var ( Usta), veri aktarımını başlatan ve senkronizasyon sinyalleri üreten. Ağ ayrıca bağımlı cihazlara sahiptir ( köle) ana bilgisayarın isteği üzerine veri ileten. Her bağımlı aygıtın, ana aygıtın onu adreslediği benzersiz bir adresi vardır. Cihazın adresi pasaportta (veri sayfası) belirtilmiştir. Birkaç master dahil olmak üzere bir I2C veriyoluna 127 adede kadar cihaz bağlanabilir. Cihazlar çalışma sırasında bus'a bağlanabilir, örn. çalışırken takmayı destekler.

    Arduino, I2C arabiriminde çalışmak için iki bağlantı noktası kullanır. Örneğin, içinde arduino uno ve Arduino Nano analog bağlantı noktası A4, SDA'ya karşılık gelir, A5 analog bağlantı noktası SCL'ye karşılık gelir.
    Diğer tahta modelleri için:
    Arduino Pro ve profesyonel mini - A4 (SDA), A5 (SCL)
    arduino mega- 20 (SDA), 21 (SCL)
    arduino leonardo- 2 (SDA), 3 (SCL)
    Arduino nedeniyle- 20 (SDA), 21 (SCL), SDA1, SCL1

    I2C veri yolu üzerinden cihazlarla veri alışverişini kolaylaştırmak için Arduino için standart "Wire" kitaplığı yazılmıştır. Aşağıdaki özelliklere sahiptir:
    başlamak(adres)- kütüphane başlatma ve I2C veriyoluna bağlantı; adres belirtilmemişse, bağlı cihaz ana cihaz olarak kabul edilir; 7 bitlik adresleme kullanılır;
    requestFrom()- master tarafından slave'den belirli sayıda bayt talep etmek için kullanılır;
    iletim başla(adres)- belirli bir adreste bağımlı cihaza veri aktarımının başlatılması;
    son İletim()- köleye veri iletiminin sonlandırılması;
    yazmak()- bir talebe cevaben köleden gelen verilerin kaydedilmesi;
    mevcut()- ikincil öğeden alınabilecek bilgilerin bayt sayısını döndürür;
    Okumak()- köleden anaya veya anadan köleye aktarılan bir baytın okunması;
    alındığında()- bağımlı, ana birimden bir iletim aldığında çağrılacak bir işlevi belirtir;
    istek üzerine()- master, slave'den bir iletim aldığında çağrılacak bir işlevi gösterir.

    I2C veri yolu ile nasıl çalışılacağını görelim arduino.
    İlk olarak şekildeki gibi devreyi kuralım. I2C veriyoluna bağlı olan AD5171 dijital 64 konumlu potansiyometreyi kullanarak LED'in parlaklığını kontrol edeceğiz. Potansiyometreye ulaşacağımız adres 0x2c'dir (ondalık olarak 44).

    Arduino, günümüzde oldukça popüler olan I2C de dahil olmak üzere birçok veri aktarım arayüzünü desteklemektedir. Bir zamanlar bu iletişim protokolü Philips tarafından icat edilmiş ve patentli “I2C” adı altında tescillenmiş, TWI, 2 hatlı arayüz isimleri altında da karşılayabilirsiniz ama hepsi aynı prensipte çalışıyor.

    I2C veri yolunun tüm noktası, büyük (128) miktarda asabilmenizdir. çeşitli cihazlar, sıcaklık sensörlerinden mikrodenetleyicilere.

    Ancak aynı zamanda, I2C, temel çalışma ilkeleri nedeniyle hız açısından UART ve SPI'den daha düşüktür, çünkü. iki çizgi her zaman dirençlere (Vcc) kadar çekilir, bu da grafikte hayır elde ettiğimiz anlamına gelir. dikdörtgen darbeler, ancak yamuk, yukarıdakinin aksine.

    SDA - bilgi aktarımından sorumludur (aktarım başlangıcı, adres, veri)
    SCL - otobüs saati

    I2C cihazlarında Master ve Slave olmak üzere iki tip olabilir.

    Şimdi standart Wire.h kitaplığını kullanarak programlamanın temel ilkelerini inceleyelim:

    Wire.begin(uint8_t adresi) - cihazı başlatmak için kullanılır, bağımlı modda adresi girmeniz gerekir, ana modda Wire.begin() . Tel yerine başka herhangi bir kelime kullanılabilir.

    Wire.requestFrom(uint8_t adresi, uint8_t miktarı) - belirli bir cihazdan (7 bit adres) belirli sayıda bayt alma isteği. Okunan bayt sayısını döndürür.

    Wire.beginTransmission(uint8_t adresi) - iletimin başlangıcı

    Wire.endTransmission() - iletimin sonu, hata numarası veya başarı(0) döndürür

    Wire.write(uint8_t verisi) - tek bir baytın (değer), birkaç baytın (dize), belirli bir uzunluktaki bir dizinin (veri, uzunluk) değerini alabilir. Şunlar arasında yer alır: beginTransmission ve endTransmission. Yazılan bayt sayısını döndürür.

    Wire.available() - İşleme için uygun bayt sayısını döndürür. requestFrom'dan sonra master tarafından çağrılır.

    Wire.read() - Köleden bir bayt okur. requestFrom'dan sonra yazılır.

    Standart bir düzenleyici ile birlikte geldiği için kitaplıkları Arduino IDE'ye bağlamak zor değildir.

    Birkaç işlev daha var, ancak bence bu temel bilgiler başlamak için yeterli, ayrıca hemen hemen her çevre birimi için bir kitaplık bulabilirsiniz.

    Örneğin, ivmeölçer ve jiroskop Gy-521'in bağlantısını ve çalışmasını düşünün.

    Şemaya göre bağlanıyoruz (çekme dirençleri modüle yerleştirilmiştir):

    Modül hem 3,3 volttan hem de 5'ten çalışabilir.

    #katmak // i2c arabirimi ile çalışmak için kitaplığı bağlayın const int MPU_addr = 0x68; // I2C adresi GY-521 int16_t AcX, AcY, AcZ, Tmp, GyX, GyY, GyZ; // değerleri yazmak için değişkenler kurulumu geçersiz kılar() ( Wire.begin(); // i2c veri yolunu başlat Wire.beginTransmission(MPU_addr); // iletimi başlat Wire.write(0x6B); // başlatmak için belirli kayıtları yaz Wire modülü.write(0); // modülü uyandırmak için null gönder Wire.endTransmission(true); Serial.begin(9600); ) void loop() ( Wire.beginTransmission(MPU_addr); Wire.write(0x3B) ; // bu kayıttan başla Wire.endTransmission(false); Wire.requestFrom(MPU_addr, 14, true); // tüm kayıtları oku AcX = Wire.read()<< 8 | Wire.read(); // 0x3B AcY = Wire.read() << 8 | Wire.read(); // 0x3D AcZ = Wire.read() << 8 | Wire.read(); // 0x3F Tmp = Wire.read() << 8 | Wire.read(); // 0x41 GyX = Wire.read() << 8 | Wire.read(); // 0x43 GyY = Wire.read() << 8 | Wire.read(); // 0x45 GyZ = Wire.read() << 8 | Wire.read(); // 0x47 Serial.print("AcX = "); Serial.print(AcX); // выводим данные в Serial Serial.print(" | AcY = "); Serial.print(AcY); Serial.print(" | AcZ = "); Serial.print(AcZ); Serial.print(" | Tmp = "); Serial.print(Tmp / 340.00 + 36.53); // выводим температуры по формуле Serial.print(" | GyX = "); Serial.print(GyX); Serial.print(" | GyY = "); Serial.print(GyY); Serial.print(" | GyZ = "); Serial.println(GyZ); delay(333); }

    Mikrodenetleyici tabanlı geliştirilen sistemin işlevselliği nasıl genişletilir? Evet, bu soru elektronik cihazların prototipleri üzerinde çalışan birçok devre mühendisinin ilgisini çekiyor. Şaşırtıcı bir şekilde, Philips mühendisleri tarafından 30 yılı aşkın bir süre önce geliştirilen bir bus, devreyi değiştirmeden sisteme yeni bloklar eklemeye izin verecek.

    I2C arayüzü sayesinde, mikrodenetleyiciyi birkaç yüz mikro devreyi bağlayabileceğiniz basit bir kurucuya dönüştürebilirsiniz. Sayılarının 400 pF veri yolu kapasitesi ile sınırlı olduğu hemen belirtilmelidir, ancak bu, I2C'nin birkaç dezavantajından biridir.

    İnterkom şeması - bugün hemen hemen her elektronik cihazda bulunabilen otobüsün adını bu şekilde deşifre edebilirsiniz. Philips'in pratik açıdan böylesine başarılı bir çözümün patentini aldığını ve diğer üreticilerin I2C'yi başka isimler altında çoğalttığını belirtmekte fayda var.

    Ekranların, kameraların, cep telefonlarının dış dünyasıyla iletişim kurmak için kurulan bu veri yolu. I2C kullanan cihazlara bağlanan çevre birimlerinin sayısı genellikle sayılamaz. Arayüzün faydaları nelerdir?

    I2C'nin ana avantajları ve dezavantajları

    I2C, elektronik cihazların içindeki entegre devreler arasındaki iletişim için seri asimetrik bir veri yoludur. İki çift yönlü iletişim hattı (SDA ve SCL) kullanır.

    Veri yolu iki iletkenden oluşur ve arayüzü kontrol etmek için bir mikrodenetleyici yeterlidir. Şaşırtıcı bir şekilde, bu kadar basitlik, çalışma sırasında mikro devreleri kapatmanıza izin verir. Özel bir yerleşik filtre, işlenen bilgilerin güvenliğini sağlayarak patlamalarla başa çıkabilir.

    I2C'nin dezavantajları arasında, sınırlı kapasitenin yanı sıra, programlamanın karmaşıklığı ve düşük seviyeli bir durumda bir arızayı tanımlamanın zorluğu yer alır.

    Başlangıçta veri yolu hızı yalnızca 100 kbps idi ve ona yalnızca 120 cihaz bağlanabiliyordu. 90'lı yıllarda standartlar değişti ve veri aktarım hızı 4 kat arttı ve 1000'e kadar mikro devreye bağlanmak mümkün hale geldi.

    Bununla birlikte, çoğu arayüz üreticisi, bağlı 120 cihazla 400 kbps'ye takılıp kalmıştır.

    Bağlantı ve çalışma prensibi

    Bara iletkenleri artıya 1-10k dirençlerle bağlanır, iletkenlerden biri veri yolu, diğeri saattir. Böyle bir şema basit bir şekilde çalışır: hatta bir ana cihaz (mikrodenetleyici) ve birkaç çevresel cihaz vardır. Hatlar artıdan beslendiği için bağlı olan slave'in (slave elemanı) kabloyu toprağa bastırarak 0 iletmesi yeterlidir.

    Çevresel cihaz teli serbest bıraktığında, tel üzerinden 1 iletilir Her şey temeldir, ancak ortak çalışma sırasında kölelerden biri 0 verirse, veri yoluna bağlı diğer cihazların beklemesi gerekecektir. Mikrodenetleyici, hattın boş olup olmadığını önceden belirledikten sonra saat ve iletim gerçekleştirir. Bunu yapmak için SCL ve SDA'ya 1 iletilir, ardından bir başlatma koşulu oluşturulur - SCL değeri 1 olduğunda SDA satırına basılır.

    İşin bir sonraki aşaması, iletişim kurmak istediğiniz cihazın adresinin aktarılmasıdır.

    Unutulmamalıdır ki veri SCL=1 iken okunur ve iletim en anlamlı bit ile devam eder.

    İlk 7 bit cihaz adresi, 8 yazma (0) veya okuma (1) komutudur.

    Köle, sekiz sinyalin hepsini alacaktır, kendisi için her şey açıksa, dokuzuncu SCL döngüsünde SDA hattına basın. Değilse, bir durdurma sinyali üretilir ve veriler tekrar iletilir. İş bittiğinde SCL'ye dokunulmazken SDA hattı serbest bırakılır.

    Bağlı çip sinyali yavaş işlese bile SCL'yi tutacaktır.

    çoklu ana mod

    Devrede demokrasi sorunları düzenlenir. Ana cihazın işin sonucunu kontrol edebilme yeteneğine dayanır. Çizginin serbest bırakılıp bırakılmadığını iki kez kontrol etmek zorunludur, eğer serbest bırakılırsa, o zaman usta şu anda liderdir, eğer değilse, o zaman daha önemli bir şey çizgiyi tutmaktır. Bu durumda, ışığı beklemeniz ve göründüğünde işinizi yapmanız gerekir.

    Ancak tüm ustaların aynı anda iş yapmaya karar vermesi de oldukça olasıdır. Bu durumda şampiyonluk, saatçiliği ilk başlatan ve hızlı yapan ustanın olacaktır. İki cihaz aşırı senkronize çalışırsa, rakibinden biraz daha hızlı 0 üreten ilk kazanır.