Mikrodenetleyici için gerçek zamanlı işletim sistemleri. Gömülü Sistemler ve OS Onlar için

Merhaba, habr!
Bugün size böyle ilginç bir şeyden bahsediyorum. işletim sistemi Gerçek zamanlı (OSR). Deneyimli programcılar için ilginç olacağından emin değilim, ama bence yeni başlayanları seveceğim.

OSR nedir?

Wikipedia'ya bakarsak, 4 tanımını göreceğiz.
Kısaca söylerseniz, OSR, dış olaylara belirli bir süre içinde yanıt veren bir işletim sistemidir. Buradan, OSR'nin temel amacını anlayabiliriz - olaylara hızlı bir yanıtın gerekli olduğu cihazlar (ancak hiçbir durumda OSR'nin çalışmalarını kesintilerle karıştırmaz).

Neden ona ihtiyacımız var?

Bu, oldukça fazla sebep.
İlk olarak, OSRV çoklu görev, semafor süreçlerinin önceliklerini ve çok daha fazlasını desteklemektedir.
İkincisi, çok kolaydır ve neredeyse kaynak gerektirmez.
Üçüncüsü, yukarıdakilerin hepsi neredeyse herhangi bir beze ulaşabiliriz (örneğin, Freertos 8-bit ATMEGA'da bile çalışıyor).
Dördüncü olarak, sadece kendin oyna ve tadını çıkar.

3 tanınmış OSRS'ye genel bakış.

Dikkat: Sonra kişisel görüşüme devam eder.
Freertos.
Bugün en popüler OSR'lerden biri. Çok miktarda demir olarak taşınır. Resmi site.
artış
1) ücretsiz
2) taşındı çok sayıda gland
3) Güçlü işlevsellik
4) Çeşitli kütüphaneler vardır: grafikler, internet ve daha fazlası.
5) İyi belgeler.
Eksi
1) Yeni bir demir için oldukça karmaşık bir portluk işlemi.

Sonuç: Gerçekten iyi belgelerle profesyonel bir paylaşımdır. Limanın zaten bir limanı varsa, başlangıç \u200b\u200biçin iyi olacak.

Keilrtx.
Son zamanlarda, bu OSRV ticari, ancak son zamanlarda açık oldu. Sadece kol mimarisinde çalışır. Resmi site.
artış
1) ücretsiz
2) Yeni ütüye kolayca bağlantı noktaları (kol mimarisinde).
3) Çeşitli kütüphaneler vardır: grafik, internet ve diğer.
Eksi
1) Keil'de çalışmak neredeyse gerçek değil
2) biraz kesilmiş bir işlevsellik
3) Sadece kol desteklenir.
4) (kişisel deneyimde) birçok hızı kaybeder.
Sonuç: Başlangıç \u200b\u200bve küçük projeler için idealdir.
uC / OS.
Güçlü ticari paylaşım. İnternet sitesi .
artış
1) Çok sayıda fonksiyon ve kütüphane.
2) çok fazla demir destekler
Eksi
1) Ticari.
2) Kullanımda kompleks.

Sonuç: Büyük bir gerginlikle bir acemi için diyebilirsiniz.

Diğer ilginç OSRV'ler

Rtlinux OSRV'ler sıradan Linux'u temel alarak.
UNIX'e göre QNX OSRV.

OSRV kullanarak geliştirme özellikleri

Öncelikle, aşağıdakileri anlamak gerekir: DRA Windows değil. Yüklenemez. Bu sistem programınızla birlikte derlenir.
OSR ile program yazarken, fonksiyonlar olağan anlayışlarında kullanılmaz. İşlevler yerine, işlemler (veya testler) kullanılır. İşlemlerin, işlevlerin aksine, sonsuz döngülerdir ve asla bitmez (sadece birisi veya öldürmezse - yani bellekten kaldırılmaz).
Birkaç işlem dahil edilirse, OSR bunları değiştirir, makine süresi ve kaynakları sırayla açar. Bu, işlemin önceliği kavramının ortaya çıktığı yerdir, eğer iki işlem bir kerelik motor zamanına ihtiyaç duyarsa, OSR daha fazla önceliğe sahip olana verecektir.
OSRV'de gecikmenin özel özellikleri vardır - böylece boşuna zamanın bir işlemin gecikmesi sırasında kaybolmadığından, ikincisi gerçekleştirilir.
Şimdi, bu tür bir şey hakkında konuşalım. Uygulamanın uygulama kaynaklarına erişimini kontrol eden bu tür bir şey. Her kaynak için bir işaretleyici vardır - işlemin kaynağa ihtiyacı olduğunda - onu alır ve bu kaynağı kullanır. İşaretleyici yoksa, süreç iade edilene kadar beklemek zorunda kalacaktır. Bir örnek vereceğim: farklı süreçler bir uart hakkında bilgi gönderir. Semafor olmasaydı, baytlar sırayla gönderirlerdi ve bir karışıklık olurdu. Ve böylece ilk işlem UART'ta işaretleyiciyi bir mesaj gönderdi ve ikinci (ve öylesine sonsuzluğa) verdi.

Ek OSR kütüphaneleri.

Genellikle, OSRV, örneğin grafik, internet vb. İle çalışmak için çeşitli kütüphaneler sunar. Onlar gerçekten rahat ve onları kullanmak zorunda kalmamalıdır. Ancak, OSR olmadan, yazdıkları OSR olmadan, çalışmayacaklarını unutmayın.
İşte örnek:
RTX için

İşletim sistemini duyduğunuzda akla ne geliyor? Elbette pencereler, linux, makro .. ya da böyle bir şey. Doğru ve ihtiyaç duyduğu soruya, herkes güvenle cevap verecek: müzik dinlemek, oyunu oyna (internette!), Diğeriyle Skype'ta konuşuyor. Aynı zamanda, LED yanıp sönmeyi düşünerek, yuart \u003d) bir bayt aldı.

Ve daha derin kazarsanız, sonra müzik dinlemek, internet üzerinden veri göndermek tüm tek işlemlerdir ve bir işlemcimiz olduğundan, aynı zamanda yalnızca bir görevi gerçekleştirebilir. Bu nedenle, görevler alternatif olarak küçük "kısımlarda" olarak gerçekleştirilir, osun özü kullanıcının özü, kullanıcı için anlaşılmaz bir şekilde yapılır: böylece sesin kısık olmadığı ve biketiği şarkı söylemez ve her şey aynı anda çalıştı. Aynı zamanda, eğer görevlerden biri "asılacak" ise, her şey çalışmaya devam eder.

Tüm ekstra çörekleri düşürürseniz ve çıplak özü bırakırsanız, önce işletim sisteminin öncelikle, kullanıcının katılımı olmadan, görevler arasındaki geçişler, bazı bölümler gerçekleştirir, bir parça yapar ve tekrar değiştiren bir zamanlayıcıdır. Çoğu görevin bir kuantumda tamamlamak için zamanın olmayacağını düşünmek de gereklidir, bu nedenle görevin durumunu diğerine geçiş sırasında kaydetmeniz gerekir ve bir dahaki sefere değişkenlerin durumunu geri yüklemek için . Bütün bunların yönetimi Görev Planlayıcısı tarafından yapılır.

İki ana işletim sistemi vardır: yer değiştirme ve kooperatif. İlk durumda, görevler arasında geçiş yapmak "zor" olacaktır. Zamanın kuantumu 1ms ise, önce ilk görev tam olarak 1ms, daha sonra ikinci kesin 1 ms, vb. Bu eksenler gerçek zamanlı olarak adlandırılır (ORVD). Kooperatif biraz daha basittir, sürecin "idam edildiğim" diymelidir, bu nedenle onları ataman imkansızdır.

Hızlı olağanüstü AVR çalışmayacak çünkü küçük sayı VERİ DEPOSU. Kooperatifler için mevcut seçeneklerden, MRTOS'tan etkilendim, bu sistemin ayrıntılarını yazarın web sitesinde (kolayca googles) okuyabilirsiniz. esas sebep Kullanımı basitlik, Cavr altında hazır bir versiyonun varlığı, anlayış için genel İlkeler En çok şey.

Böylece, ana sorular kaldı, neden ve ne zaman ekseni uygulanacak. Teorik olarak, eksenle yaptığınız her şey, onsuz geçebilirsiniz, için kaynaklar aynıdır. Projeye benimsemeniz gerçeğinden, uzayda MegaHertz çıkmaz, demir aynı kalacaktır, bu nedenle kaynaklar aynıdır.

Bu nedenle, kendinize birkaç soru sormalısınız:
1. Yetkili kaynakları yönetebilir misiniz?
2. Yazılımı yazma sürecinde aynı bisikleti icat etmeniz gerekmez mi?
3. Kodunuzu ne kadar okuyorsunuz? Yarım yılda yarım açıp çıkabiliyor musunuz?
4. Yazıyor musunuz veya gruplar mısınız?

İlk sorunun cevabını vermek zor, çünkü hepsi geliştiricinin müfredatına bağlıdır. İkincisi ile, birçok bağımsız görev varsa, her şey daha anlaşılırsa ve belirli aralıklarla onları gerçekleştirmesi planlanırsa, işletim sisteminin yanına bakmak daha iyidir. Üçüncüsü de açık, ana döngüdeki bağımlılıkları boyamaktan daha ayrı bir görevde anlaşılması çok daha kolaydır. Yalnız değilse, burada burada avantajlar var, çünkü herkesin görevlerini ayrı ayrı yazabilir, dinlenmeye müdahale etmeden.

Yukarıdakilerin birleştirilmesi, uygulamanın kapsamı belirli bir görev yelpazesinde oldukça spesifiktir. Her projeye girmeyin. Çoğu amatör radyo cihazları için, eksen gereksizdir, ancak daha önce onun hakkında bir fikir sahibi olmak, muhtemelen birkaç proje kaplar.

Şimdi kaputun altına bakın. MRTOS'u projeye başlatmak için, MRTOS.C ve Yayla MRTOS.H'yi bağlamanız gerekir. Kodun yapısı normalden biraz farklıdır

#Dahil etmek. #İnclude "mrtos.h" // burada süper kodunuzu yazdığımız vücut fonksiyonu Void görev1 () (iken (1) // herhangi bir işletim sistemindeki görevler sonsuz bir döngü temelinde inşa edilmiştir. { // İşte görevinizin kodu Sevk etmek; // Planner Yönetimi Fonksiyonu } ; } // zamanlayıcı kesme işleyicisi 0 Kesme [Tim0_OVF] Void Timer0_Ovf_ISR (geçersiz) (CHAR II; #ASM ("CLI") TCNT0 \u003d 0x9C; INC_SYSTIME (); (II \u003d 0; II)< init_tasks; ii++ ) if (tasks[ ii] .delay ) -- tasks[ ii] .delay ; #asm("sei") } void main(void ) { // periferin başlatılması İnit_mrtos (); // işletim sistemi başlatma // Burada PASSES (Görevler) 3 görev oluşturduk. Create_task (Görev1, 1, Aktif); // Bir görev oluştur (görev adı, öncelik, durum) Create_task (Görev2, 1, Aktif); Create_task (görev3, 1, aktif); Sheduler (); // zamanlayıcı başlatmak (1); )

#Dahil etmek. # "mrtos.h" // burada Super Code Void Görevinizi () yazdığımız fonksiyonun gövdesi (iken (1) // herhangi bir işletim sistemindeki görevler, sonsuz bir döngü (// burada) temelinde oluşturulur. Sevk Görevinizin Kodu; // Fonksiyon Şanzıman Zamanlayıcı Yönetimi);) // Zamanlayıcı Kesme İşlemi 0 Kesme Void Timer0_Ovf_ISR (Void) (CHAR II; #ASM ("CLI") TCNT0 \u003d 0x9C; INC_SYSTIME (); 0; ii

Şimdi biraz daha. Görevlerin sayısı MRTOS.H Expaines ApptAsks N. Görev, görev 1 () () (), Görev2 () () () () () () () () ve benzerleri, içinde (1) bir şey yazmanıza gerek yoktur, gerekli değildir İşlevleri aramak için, tüm bunlar yapacaksınız Planlayıcınız. Görevi görebileceğiniz gibi, sonsuz bir döngüden oluşur, normal olmalı ve yapılmalıdır, ancak görevin içinde planlayıcının kontrolünü vermeniz gerekir. Ya bekleme işlevi ya da gönderim. Bu yapılmazsa, görev sonsuz şekilde gerçekleştirilecektir.

Nasıl çalışır? Yanıp sönen görevi oluşturun.

Void görev1 () (iken (1) (portb.0 \u003d! Portb.0; beklemek (100););)

void görev1 () (iken (1) (portb.0 \u003d! Portb.0; beklemek (100););)

Bekleme, yalnızca belirli bir gecikmedir () bir analogdur, gecikme sırasında bir mikrodenetleyici hiçbir şey yapmaz ve boş döngüleri sürmez. Aynı bekleme sırasında, kontrol diğer görevlere iletilir. Şunlar. Farklı LED'leri yanıp sönerek bir sürü görevi oluşturabilir, farklı bekleyerek ve hepsi farklı frekanslarla yanıp söner. Gecikmeler gerekli değilse, sonunda UNPATCH kullanır.

Bekle kullanırken, tüm sistemin minimum bir Tic (kuantum (kuantum) olduğunu anlamak önemlidir, bu yüzden beklememiz (50) 50 MilciBundy, ancak 50 tik sistemi bekliyoruz. Kene Kurulumu, zamanlayıcının kesintilerinin sıklıkla nasıl çağrılacağına bağlıdır, yani 1MS'ye bir kesinti yapılandırdıysak, eylemimizin 1 ms için yürütüldüğünü varsayabiliriz. Deneyler, sistemin kene ile ~ 20 μs'leri bir saat 16 MHz ile azaltmanın mümkün olduğunu göstermiştir.

Zamanlayıcı ayarı daha önce çalışılanlarda farklı değildir, çünkü Timer0 yalnızca taşma kesintisi var, ardından tüm ayarlar buna bağlı. Cavr'ın en son sürümlerinde, zaman taleplerini yazmak çok uygundur, ayarlar otomatik olarak oluşturur.

Create_task (Görev1, 1, Aktif);

create_task (görev1.1, aktif);

Öncelikler ile her şey sadece değil. Farklı önceliğe sahip iki görev varsa ve büyük önceliği olan görev sürekli olarak gerçekleştirilirse, o zaman asla düşük önceliğe sahip olan göreve gitmeyeceğiz. Bu nedenle, tüm görevlerin erişebilmesi için iş organize etmeniz gerekir. Buna dikkat etmeyeceğiz, bir dahaki sefere paylaşmayacağız. Görev durumu, aktif - başladı, stoptask durdu.

Öyleyse, sadece LED'in yanıp sönmesi isteyenler için:

#Dahil etmek. # "mrtos.h" void görevi1 () () (iken (1) (bekleyin (1000); portb.0 \u003d! PORTB.0;)) // Timer 0 taşma kesme hizmeti rutin Kesme [Tim0_OVF] Void Timer0_Ovf_ISR (geçersiz) (CHAR II; #ASM ("CLI") TCNT0 \u003d 0XB2; INC_SYSTIME (); için (ii \u003d 0; ii)< init_tasks; ii++ ) if (tasks[ ii] .delay ) -- tasks[ ii] .delay ; #asm("sei") } void main(void ) { DDRB= (1 << DDB7) | (1 << DDB6) | (1 << DDB5) | (1 << DDB4) | (1 << DDB3) | (1 << DDB2) | (1 << DDB1) | (1 << DDB0) ; PORTB= (0 << PORTB7) | (0 << PORTB6) | (0 << PORTB5) | (0 << PORTB4) | (0 << PORTB3) | (0 << PORTB2) | (0 << PORTB1) | (0 << PORTB0) ; // Zamanlayıcı / Sayaç 0 Başlatma // Saat Kaynak: Sistem Saati // Saat değeri: 7.813 KHz TCCR0 \u003d (0<< CS02) | (1 << CS01) | (1 << CS00) ; TCNT0= 0x83 ; // Timer (s) / sayaç (lar) kesme (ler) başlatma Timsk \u003d (0<< OCIE2) | (0 << TOIE2) | (0 << TICIE1) | (0 << OCIE1A) | (0 << OCIE1B) | (0 << TOIE1) | (1 << TOIE0) ; Init_mRTOS() ; create_task(task1, 1 , Active) ; Sheduler() ; while (1 ) ; }

#Dahil etmek. # "mrtos.h" void görevi1 () () (iken (1) (bekleyin (1) (bekleyin (1000); portb.0 \u003d! Portb.0;)) // Timer 0 taşma kesme hizmeti rutin kesme void Timer0_OVF_ISR (geçersiz) (char ii) ; #Azy ("cli") tcnt0 \u003d 0xb2; inc_systime (); için (ii \u003d 0; ii

Bonus olarak, bir polifonik (iki saçlı) melodi "Dr.Mario Chill" yapmaya çalıştım. Buradaki fikir, kontrol cihazının her bir ayağının sürekli olarak ayrı bir task halinde ters çevrilmesi, böylece frekansı üretmesidir. Deklanşörü değiştirme Notların yüksekliğini değiştirebilirsiniz.

Void görev 2 (geçersiz) (iken (1) (eğer (sessiz \u003d\u003d 0) // oynamaya izin verilirse (if_ch2 [n_n] \u003d\u003d 0) // Bir duraklama bekliyorsanız, hiçbir şey oynamıyoruz (PORTB.4 \u003d 0; bekleyin (5);) başka (portb.4 \u003d! PORTB.4; // duraklatmazsa, ayağı istenen frekansla sıkın Bekleyin (not_ch2 [n_n]); )))))

void görev 2 (geçersiz) ((1) (eğer (1) (eğer (MUTE \u003d\u003d 0) // oynamanıza izin verilirse (if_ch2 \u003d\u003d 0) // Bir duraklama bekliyorsanız, hiçbir şey oynamıyoruz (PORTB. 4 \u003d 0; bekleyin (5);) başka (PORTB.4 \u003d! PORTB.4; // Duraklatmazsa, daha sonra istenen bekleme frekansı (not_ch2);))))))))

Fikirle uğraşmadım, 1 Tasque, Solo Partisi için Solo Partisi için, İkinci olarak, bas için ikincil bir dipnotla oluşturulmuştur. Her bir fikrin yüksekliği dizilerden alınır. TASQUE3'teki süre, anahtarlama ve kırılma.

Void görevi3 (boşluk) (bekleyin (1) (bekleyin (1500); // minimum not sayısını oyna için (sessiz \u003d 0; dilsiz< 500 ; mute++ ) // Birleştirmemek için notu tıklayın (PORTB.3 \u003d 0; PORTB.4 \u003d 0;); Dilsiz \u003d 0; // Ses oynatabileceğiniz bayrağı ayarlayın n_n ++; // bir sonraki nota git Eğer (n_n \u003d\u003d n_max) // bir dairede her şeyi oynadılarsa (n_n \u003d 0;))))

void görevi3 (geçersiz) (bekleme (1) (bekle (1500); // için notların minimum dili oynatma (sessiz \u003d 0; dilsiz< 500; mute++) //обрываем ноту, чтобы не сливались { PORTB.3 = 0; PORTB.4 = 0; }; mute = 0; //выставляем флаг, что можно воспроизводить звук n_n++; //переходим на следующую ноту if(n_n == n_max) //если сыграли все то идем по кругу { n_n = 0; } } }

İki kanalı karıştırmak için basit bir şema kullanılır.

Toplam küçük parça

Bellenim isteyenler için

10'dan fazla elektronik cihaz geliştirdim ve işletim sistemi olmadan düşük seviyeli çalışmalarında tamamen sorumluydum. Bir sonraki cihazın işlevselliği keskin bir şekilde genişlettiğinde durum değişti. Ek olarak, belirtilen zaman aralıkları ile çağrılan bir göreve ihtiyaç vardı ve aramanın doğruluğu sonucu etkiler. Ayrıca tahsis edilen süre için her şeyin işe yaramayacağı ve daha sonra yaratılacağı açıkça ortaya çıktı. Kısa bir yansıma sonrasında, projenin gerçek zamanlı işletim sistemini (ORVD veya RTOS) içermesi gerektiğini fark ettim.

Bir mikrodenetleyici OSR için sistem kaynakları ile çalışmak için işletim sisteminin daha fazla bir katman olduğu PC'den farklı olarak, bu öncelikle bir görev zamanlayıcıdır, aslında "gerçek zamanlı" içinde önemli bir rol oynar. Şu anda, "sözde paralel" görevlerin performansını sağlamam için önemlidir. Yani, aynı önceliğe sahip birkaç görev vardır ve belirtilen zaman aralıklarında belirli bir sırayla onlara neden olmak önemlidir.

Aşağıdaki örnek görsel olarak: Eurobot 2011 projesinde sistemde 18 periferik cihaz bulundu. 2 e-posta bir olarak birleştirilebilir. Maliyetleri azalır, güvenilirlik arttı (sistemdeki bileşen sayısını azalttı), durumdaki boş alan miktarı arttı. Bu durum, görevlerin sayısının orantılı olarak büyüdüğü ve burada artık işletim sistemi olmadan yapılmadığı gerçeğini de karmaşıklaştırır. Ayrıca, OSR, işlemcinin olası aksama süresini önlemeye yardımcı olur, örneğin, ADC dönüşümü sırasında, bu görevi engelleyebilir ve başkalarını gerçekleştirebilirsiniz, böylece cihazın çalışmasını doğru şekilde dağıtabilirsiniz. Şimdi, şimdi cihazın görevdeki bir başarısızlık nedeniyle düşmeyeceği de önemlidir, bunun yerine kısmi performansı korumak mümkündür (tahmin edilemez sonuçlara yol açabilir). Bu göstergelerin büyümesini sağladığımızdan dolayı? Aslında, hesaplamalı yeteneklerini etkin bir şekilde kullanarak, MC'den mümkün olan her şeyi sıkıyoruz.

Kısa bir aramadan sonra, seçim freertos'a düştü. Bu ord, C ve Limanlar üzerindeki kaynak kodunda 27 mimariye dağıtılır. Benim için son durum belirleyicidir. Diğer üreticilerin MK ile çalışırken işçilik maliyetlerini düşürür. Şimdi AVR için limanla daha çok ilgileniyorum.

Freertos'a genel bakışın mevcudiyeti Projeye genel bakış, yaklaşık 9.8 CB program programı ve 1.8 KB RAM. Örneğin, ATMEGA32 ve WinAVR derleyicisi için sırasıyla% 60 ve% 85'tir. Zaten bu model için, büyük işlevselliğe sahip bir cihaz oluşturun - yeterli bellek değil. Ancak, yeni AVR modellerini kullanırken bu sorun kaybolur. MEGA2560 için 256KB program programları ve 8 KB RAM ile tamamen kırılır. Gelecekteki MK'nın eğilimi yalnızca OSR'nin başarısına eşlik eder.

Runkun üzerinde koşmak, Rusça'da işletim sistemi üzerinde belgeler olmadığını gördüğüme şaşırdım. Peki burada ne var! Orijinal belgeler ek maliyet için geçerlidir. Durum, Andrei Kurtica makalesini basitleştirdi ( [E-posta Korumalı]) "Bileşenler ve Teknoloji" dergisinden. Yazar ile anlaşarak, makaleyi geri dönüştürülmüş versiyonda kullanacağım. Makalesi, Rusça'da belgeler olarak da hizmet verebilir. Ancak orijinal baskıda kullanılamıyor, dergi sitesi yatıyor, böylece malzeme biraz geri dönüşümlü olacak. Genel olarak, yazar mükemmel bir makale yaptı ve tekrar teoriyi geçmenin anlamı yok, burada tam olarak yayınlanacak. Orijinal makale yayının sonunda eklenecektir. Ayrıca, kullanıcıların OSR'yi derlemekte zorlandıklarını da fark ettim. Bunun nedeni, harici makefile'in, klasörlerin yollarının yazıldığı, kullanıldığı gerçeğinden kaynaklanmaktadır. Bu nedenle, AVR Studio ve AVR Eclipse için bir şablon şeklinde hazır bir proje uygulayacağım. Ne yazık ki, yerli makefile, RAM İstihdam derecesi ve programların hafızası gibi hata ayıklama bilgisini çekmez, uygun standart mücadeleyi ekleyerek sıkıntı yapmak zorunda kaldı.

Yani, ihtiyaç hakkında kısaca, projenizde Gerekirse OSR kullanmak arzu edilir:

Multiscy ve alternatif görevleri düzenleyin

Kesinlikle tanımlanmış zaman aralıklarında görev lansmanını sağlayın

Bilgi bir görevden diğerine aktarın

Gerektiği gibi yeni görevler ekleyin

ORV'den önce Avantajlarıİçin:

  1. Çoklu görev. OSRV, iyi dayanıklı mekanizmayı hazır bir programcı sağlar. Basit bir durumdaki her görev ayrı ayrı programlanabilir, tüm işler birkaç ekip üyesi arasında bozulur. Görevler arasında geçiş yapmakla ilgilenmeye gerek yok, planlayıcıyı yapacak.
  2. Geçici taban. Zaman aralıklarını ölçmek gerekir. OSRV bu alete sahip olmalıdır. Kesinlikle özel zaman aralıklarla eylemler yapmanıza izin verecektir.
  3. Görevler arasında veri alışverişi. Bu amaçla OSR'de bir sıra kullanılır.
  4. Senkronizasyon. Farklı görevler, seri bağlantı noktası gibi aynı kaynağı kullanırsa, muteksler ve kritik bölümler kullanılabilir. Görevleri sıkı bir sırayla gerçekleştirmeniz gerekiyorsa veya belirli bir olay meydana geldiğinde, görevleri senkronize etmek için semaforları veya sinyalleri kullanabilirsiniz.

OSRV Dezavantajları:

1. Programın çekirdeğini uygulamak için gerekli olan keskin bir artış

2. Her görevin yığını, semafor, sıralar, muteks ve diğer nesne çekirdek nesnelerinin yığını saklamak için gereken RAM'deki bir artış.

3. Bağlam koruma görevleri arasında geçiş yaparken gecikme.

Açıklamafreertos.:

Freertos, ücretsiz açık kaynaklı sert gerçek zamanlı işletim sistemidir. Tercihen C yazılı, ancak assembler ekler var. Özellikle gömülü sistemler için gerçek zamanlı mühendisler Ltd tarafından geliştirilmiştir. Son zamanlarda, "Safertos" projesi - IEC 61508 sürümüne uygunluk için IEC 61508 güvenlik standardına uygunluk için geliştirilmiş, belgelenmiş, test edilmiş ve geçmiş sertifikalandırma. Alman şirketi bu projede yer aldı ve şimdi havacılık endüstrisinde ve tıbbi teknolojide Safertos kullanılmaktadır. Ayrıca bir OpenRTOS projesi var - üreticinin garantisi ile ticari bir versiyon.

Fertrosun ana özellikleri:

1. Zamanlayıcı, 3 çeşit çoklu görev türünü destekler:

Göze çarpan

Kooperatif

Hibrit

2. Çekirdek boyutu, AVR için derlenmiş biçimde 9.8 KB'dir. (Winavr)

3. Core tabanının tabanını - C'deki 4 dosya

4. Görevleri ve Koprogramları destekler. Konveyörler, küçük bir ram hacmi ile MK için özel olarak oluşturulur.

5. Zengin iz yetenekleri.

6. Yığın taşmasını izlemek mümkündür.

7. Eşzamanlı olarak gerçekleştirilen görevlerin sayısında yazılım kısıtlaması yoktur.

8. Görev önceliklerinin sayısındaki kısıtlamalar yoktur.

9. Bazı görevler aynı önceliğe atanabilir.

10. "Görev Görevi" ve "Sorun Kesintisi" senkronizasyonu için geliştirilen araçlar:

Kuyruklar

İkili semaförler

Hesaplar Semaforları

Özyinelemeli semaforlar

Muteksler

11. Öncelikli mirasa sahip muteksler.

12. Cortex-M3 için bellek koruma modülü desteği

13. Çeşitli platformlar ve derleyiciler için demo projeleriyle borç verilir.

14. Ücretsiz. Kaynak kodunu genişletilmiş GPL lisansına uygun olarak açıklamadan projelerde kullanabilirsiniz.

15. Ücretli dokümantasyon, ancak burada çevrimiçi olarak kullanılabilir.

16. Kuvars'a 16 MHz ile AVR için bağlam anahtarlama süresi sadece 20.8 μs olacaktır. Verileri görev istifine kaydetmek ve aşağıdakileri aramanız çok gereklidir. (İlginç bir açıklama, Pic18xxx ile karşılaştırırsanız, AVR'den kontrol cihazı 4 kez daha hızlı yapar !!!, büyük olasılıkla derleyicinin kalitesinden kaynaklanıyor)

Yer değiştiren çoklu görev, düşük önceliğe sahip görevin, daha yüksek önceliğe sahip hazır bir görevle üst üste geldiği anlamına gelir. Görevler arasında geçiş yapmak, eşit zaman Quanta ile gerçekleşir. Bu nedenle, istihbarat görevi yürütmeye başlamadan önce, düşük öncelikli olduğunda mevcut zamanın mevcut kuantumu bitmesi gerekir.

Dolayısıyla, harici olaylar üzerindeki serbest olaylar üzerindeki freertos reaksiyon süresi, ayarlarda belirtilebilecek bir birden fazla zamanlayıcı zaman qualta değildir. Varsayılan olarak, 1 ms'ye eşittir.

Aynı önceliğe sahip birkaç görevi gerçekleştirmeye hazırsanız, bu durumda planlamacının her birini bir kuantumun bir kuantumunu tahsis eder, ardından kontrol aşağıdaki görevi aynı öncelikle ve benzeri bir daire içinde alır.

Kooperatif çoklu görev, planlayıcının, mevcut görevin yürütülmesini engelleyememden farklıdır, hatta görevi büyük bir öncelikle gerçekleştirmeyi tamamlayabilir. Her görev, zamanlayıcının yönetimini bağımsız olarak aktarmalıdır. Böylece, yüksek öncelikli görev, düşük önceliğin çalışmalarını tamamlanıncaya kadar beklenecek ve planlayıcının yönetimini verir. Bir harici olaya yönelik sistem reaksiyon süresi belirsiz olur ve mevcut görevin kontrolden önce ne kadar süre gerçekleştirileceğine bağlıdır. Windows 4 işletim sistemi ailesinde kooperatif çoklu görev kullanılmıştır.

Çoklu görevin yer değiştirmesi ve kooperatifi kavramı, bir meydan okuyan çağrı her kuantumun her kuantumunda meydana geldiği, ancak, yer değiştiren çoklu görevin aksine, programcı, görevin gövdesinde bu zorunlu yapabilme yeteneğine sahiptir. Bu mod, özellikle sistemin yanıt süresini kesmesi için gerekli olduğunda kullanışlıdır. Diyelim ki, şu anda düşük öncelikli görev yapıldı ve yüksek öncelikli bir kesinti bekliyor. Sonraki meydana gelir, ancak kesme işleyicisinin sonlandırılmasından sonra, yürütme mevcut düşük öncelikli göreve geri döner ve yüksek öncelik geçerli zaman kuantumunu bekler. Bununla birlikte, kesme işleyicisini çalıştırdıktan sonra, zamanlayıcı kontrolünü aktarın, yüksek öncelikli bir görevin kontrolünü aktarır, bu da harici bir olayla ilişkili sistem reaksiyon süresini azaltır.

Nedenüzerindesohbetb?

En son sürümünü yüklemekten, Freertos'u çalıştıran bir mikrodenetleyici cihazı geliştirmeye başlayabilirsiniz.

Freertos dağılımı sıradan veya kendiliğinden açılan bir zip arşivi olarak mevcuttur. Dağıtım, doğrudan çekirdek kodunu (birden fazla başlık dosyası ve kaynak dosyası olarak) ve gösteri projeleri (her port için her bir geliştirme ortamı için bir proje) içerir. Daha sonra, arşivi geliştirme istasyonunda uygun herhangi bir yerde paketinden çıkarmalısınız.

Arşivdeki oldukça çok sayıda dosyaya rağmen, dizinlerin yapısı aslında basittir. 1-2 geliştirme ortamında 2-3 mimariye cihazlar tasarlamayı planlıyorsanız, gösteri projeleri ve çeşitli geliştirme ortamları ile ilgili dosyaların çoğu gerekli olmayacaktır.

Dizinin ayrıntılı yapısı yamada verilir.

Çekirdeğin tüm kaynak kodu / kaynak dizinindedir.

İçerik:

1.Tasks.c. - Görev mekanizmasının uygulanması, zamanlayıcı

2. queue.c. - Mülkiyet Uygulaması

3. liste.c. - Planlayıcının iç ihtiyaçları, fonksiyonlar uygulama programlarında kullanılabilir.

4. croutine.c. - İfadenin uygulanması (eğer taşıyıcılar kullanılmazsa yok olabilir).

Dizinde olan başlık dosyaları Kaynak / dahil.

1. Görevler.h, queue.h, tist.h, croutine.h - Aynı adın kodunun dosyaları için sırasıyla başlık dosyaları.

2. Freertos.h. - Derleme yapılandırmak için ön işlem direktiflerini uygulayın.

3. mpu_wrappers.h. - Bellek Koruma Modülünü (MPU) desteklemek için Program Arabiriminin (API Fonksiyonları) Freertos'un işlevlerini içerir.

4. Portable.h.-Plappo'ya bağımlı ayarlar.

5. Projdefs.h.-Hext sistem tanımları

6. Semphr.h. - API işlevlerini, sıralar temelinde uygulanan semaforlarla çalışmak için tanımlar.

7. stackmacros.h. - Yığın taşmasını izlemek için makrolar içerir. Her bir donanım platformu, bu platformla Freertos etkileşimini uygulayan temel kodun küçük bir kısmını gerektirir. Platform bağımlı kodun tamamı alt dizindedir. / Kaynak / TaşınabilirSistematize edildiği ancak geliştirme ortamları (IAR, GCC, vb.) Ve donanım platformları (örneğin, atmemsam7s64, MSP430F449). Örneğin, alt dizin / Kaynak / Taşınabilir / GCC / ATMEGA323 Görevin bağlamını uygulayan / geri yükleyen port.c ve portmacro.h dosyalarını içerir, geçici bir veritabanı oluşturmak için zamanlayıcıyı başlatın, her görevin yığını ve Mega AVR ailesinin mikrodenetleyicileri için diğer donanımlara bağlı işlevleri başlatın ve Winavr Derleyici (GCC).

Ayrı olarak, alt dizini vurgulamak gerekir. / Kaynak / Taşınabilir / Memmanghangi dosyaları içerir heap_l.c, heap_2.c, heap_3.cDaha sonra ayrıntılı olarak açıklanacak olan Freertos'un ihtiyaçları için 3 farklı bellek tahsis mekanizması uygulanması.

/ Demo dizini derleme ve montaj gösterimi projeleri için hazırdır. Tüm tanıtım projeleri için kodun toplam kısmı, alt çizimde vurgulanır. / Demo / Common.

Projenizdeki Freertoları kullanmak için, çekirdek ve ilgili başlık dosyalarının kaynak kodunun kaynak kodunu etkinleştirmeniz gerekir. Onları değiştirmeye ya da uygulamalarını anlamaya gerek yoktur.

Örneğin, MSP430 mikrodenetleyicileri ve GCC derleyicisi için bağlantı noktasını kullanmayı planlıyorsanız, daha sonra bir proje oluşturmak için - sıfır "alt dizin" gerekecektir. / Kaynak / Taşınabilir / GCC / MSP430_GCC ve / Kaynak / Taşınabilir / Memmang. / Kaynak / Taşınabilir Dizin'den diğer tüm alt dizin gerekli değildir ve kaldırılabilir.

Mevcut bir demo projesini değiştirmesi planlanırsa (ki, eğer, Freertos'un çalışmasının başında yapmanız önerilir), daha sonra alt dizinlere de ihtiyacınız olacaktır. / Demo / MSP430_GCC ve / Demo / ortak. Alt dizinin / demoun geri kalanı gerekli değildir ve kaldırılabilir.

Bir uygulama oluştururken, kullanılması önerilir. makefile. (Geliştirme ortamının gelişim dosyası), ilgili gösteri projesinden bir başlangıç \u200b\u200bnoktası olarak. Montaj (oluşturma) dosyalarından / demo dizininden dışlanmasında, bunları kendi cihazınızla değiştirilmesi tavsiye edilir ve / kaynak dizininden dosyalar bozulmadan. Ayrıca başlık dosyası hakkında da bahsedin FRERTOSCONFIG.H.Her gösteri projesinde bulunan. FreertosConfig.h, Freertos çekirdeği ayarına izin veren tanımları (#define) içerir:

1. Bir dizi sistem işlevi.

2. İfadeyi kullanarak.

3. Görev ve Yapı Sayısı

4. Bellek boyutu (yığın ve yığınlar).

5. Saat frekansı MK.

6. Genellikle 1 ms'ye eşit olan her bir yürütme görevine tahsis edilen zaman planlayıcısının çalışma süresi. Bazı sistem fonksiyonlarını devre dışı bırakmak ve öncelik sayısını azaltmak (bellek tüketimini azaltır).

Freertos dağılımı ayrıca, zamanlayıcıdan alınan izleme bilgilerini metin formunda dönüştürme araçları da dahildir (dizin) / Tgssun.) ve lisansın metni (dizin / Lisans.).

sonuç

Döngünün ilk maddesinin yardımı ile okuyucu, Freertos la mikrodenetleyicileri için işletim sistemiyle tanıştı. İşin özelliklerini göstermek. Freertos dağılımının içeriğini tanımladı. Freertos'u çalıştıran bir cihazın geliştirilmesinin ana adımları başlatılmalıdır.

Aşağıdaki yayınlarda, çoklu görev mekanizmasına, yani görevler ve konveyörler için dikkat edilecektir. Zamanlayıcının bir örneği, ATMEL AVR Mikrodenetleyicileri ve Winavr Derleyici (GCC) kullanılarak örnek olacaktır.

Bu soruyu sürekli olarak hobinizde soruyorum, - 16 bitlik bir mikrodenetleyiciye dayanan bir otomatik kontrol (akıllı ev) bir ev sisteminin geliştirilmesi, bu gerçek yaklaşım mı? Bir ay, bir buçuk, blogumda "on yonga sistemlerine karşı mikrodenetleyiciler" konusundaki blogunda yazdım. Yani, tekrar yazacağım.

Kısmen bu, Stellaris Launchpad ve Arduino'nun ortaya çıkmasından dolayı istendi. Her ikisi de 32 bit mikrodenetleyicilere dayanırlar ve birçok yönden çok benzer. Şartname (veri sayfasını) her ikisine de çalıştım ve fiyatta terbiyeli olarak farklı olmalarına rağmen, bir hedef kitle için tasarlanmıştır. MSP430 ile Stellaris'e neler yapabileceğimi düşündüm ve hatta mikrodenetleyici yerine ahududu pi gibi bir şeyi kullanmak için temelde farklı bir sisteme aktarılabilir.

Hem Stellaris LaunchPad hem de Arduino nedeniyle çok güçlü, ancak Linux'u çalıştırmak için tasarlanmamıştır. Yürütülebilir bir kodla doğrudan kendileri için yazılmış veya gerçek zamanlı (RTOS) işletim sistemini çalıştırırlar, - minimalist OS, harici olaylara çok kısa bir yanıt süresi ile çalışırlar. Ayrıca, her ikisi de MSP430 veya 8 bit AVR'den çok daha karmaşıktır.

Öte yandan, gerçek hayatta (yurtdışında), çoğu, Linux'ta ahududu PI veya diğer yerleşik sistemleri kullanır. Mikrodenetleyicilerin kullanımı, karşılaştığım kişiler arasında oldukça nadir bir durum. Arduino bile, çevremde yerleşik Linux'tan çok daha az popüler. Anladığım kadarıyla, Arduino'yu, ahududu pi'yi satın alabileceğiniz birine satın almak, bu da daha çok ya da aynı veya daha az değerli olabilir? Linux altında büyük miktarda bitmiş yazılım vardır ve basit komut dosyaları dilleri kullanılarak programlanabilir.

Benim için şahsen, Linux'u kullanmak istememenin nedeni, işyerinde günlük kullandığım ve eve döndüğüm için, Linux benzeri sistemlerde tekrar çalışmanın mutluluğunu hissetmiyorum. Linux ile ilgili hiçbir problemim yok, ama her yerde çok fazla, beni eziyor. 8/16-bit mikroçiplerde basit elektronik cihazlarla çalışmam için çok daha ilginç.

Bununla birlikte, gerçeklikten uzak durmuyorum. Gerçek bir dünyayla aynı dalgada kalmak istiyorsam, gerçek dünyada kullanılan araçları kullanmalıyım. Aksi takdirde, buhar motorlu bir araba kullanma arzusu gibi görünüyor, ancak içten yanmalı motorun çok komik olduğundan, her zaman her zaman kullanıyorum. Dünyadaki dünya daha ileri teknolojiye gidiyorsa, ustalaşmanız gerekir, beğendim ya da değil. Özellikle, blogumun insanlarla ilgilenmesini ve alakalı kalmasını istersem.

Projemde akıllı evimde, gerçekten bu problemle karşılaştım. MSP430'daki kontrol sistemi için yerel bir ağ sürücüsü yaptım ve her şey çok layık görünüyor. Özünde, MSP430'da bir otomasyon sistemi için ihtiyacınız olan her şeyi yapabilirim. Yine de, bunu yapıp yapmadığımı düşünüyorum? Bir kaşık olduğunda çatal çorbası olup olmadığını mu deniyorum? Belki Linux daha uygun bir sistemdir? Açıklamama izin ver.

Kasım 2012'deki teknolojik gelişmelere göre, mevcut duruma durur ve bakarsanız. Kendimi soruyorum, mikrodenetleyiciler iyi ve uygundur ve Linux'u kullanarak yonga sistemleriyle karşılaştırıldığında alakalı mı?

Eğer kafasında bana gelen gömülü sistemlerdeki projeleri listeliyorsanız, o: Dronlar, robotlar, ev otomasyonu, motorlar kontrolörleri, sensörler, kol saatleri, 3B yazıcılar vb. Bu durumlardan hangisinde, yerleşik Linux mikrodenetleyicilerden daha uygundur? Ve neden?

Mikrodenetleyici en iyi seçim olduğunda üç durum olduğunu düşünüyorum: Anında (gerçek zamanlı) olaylar için önemli olduğunda; aşırı derecede düşük enerji tüketimi için gerekli olduğu; Ve cips'i mümkün olduğunca düşük kullanmanız gerekir.

Başlamak için, ucuz cipslerin kullanımı, benim için çok önemli değil. Ben hobimle kendim için uğraşıyorum ve hiç rekabetçi ürünler üretmeyecek. Arzu ettiğim küçük projeler için rekabetçi bir fiyat elde etmek için köle emeğini kullanan tesise üretim transferini düşünmek zorunda değilim. Yeteneklerim sayesinde, yapabilseydim, günde birden fazla tahtayı açarsam mutlu olurum!

Örneğin, bir akıllı evin projesi için, uzaktan kontrol edilen anahtarı geliştirebilirim. Işığı veya başka bir şeyi açabilir / kapatabilir. Aynı zamanda, yerel mağaza elektrik mühendisliğine gidebilir ve Çin'de üretilen 20 ABD doları için de aynı şeyi alabiliyorum. Kendi anahtarınızı satmaya çalışarak bu fiyatı hiç öldürebilir miyim? Mümkün olduğunu sanmıyorum.

Bunu düşünürseniz, ev otomasyonu için gerekli başka şeyler için de geçerlidir. Sıcaklık sensörleri, duman, hareket vb., Aynı şeyi yapabilmeliyim, ancak finansal faydaları ayırmanız muhtemel değildir. Hanehalkı ürünlerinde 20 dolara bulabilecekleri zaman 75 dolara bu tür şeyleri almayı umursuyor?

Hobinizden bir tür faydaların çıkarılmasını yansıtırsak, daha pahalı ve karmaşık ürünlere dikkat etmek daha iyidir. Örneğin, bir ev otomasyonu denetleyicisi veya bir termostat, genellikle 100 dolardan fazla maliyetlidir ve bireysel yaratıcılık için daha fazla özgürlük bırakın, bir tane inşa edebilir, komşularınızı satabilir ve hatta bir şeyler kazanabilirsiniz.

Ancak nihai cihazın daha karlı bir fiyatı elde etme arzusu, dünyadaki en ucuz mikrodenetleyiciyi kullanmanız gerektiği anlamına gelmez. Aslında, kötü bir fikir çünkü çünkü Geliştirme süresi aynı maliyetin yanı sıra kullanılan parçaları da yapar. Belki bir mikrodenetleyici ucuzdur, ancak bir kontrol kodu yazmak için daha fazla zaman gerektirir. Zaman paradır ve daha hızlı çalışırsanız, daha fazlasını elde etmek için zamanınız olacaktır.

Tüm bu yansımalar, kişisel tercihlerime rağmen, Linux'tan, Linux'u kullanmayın, Linux'u kullanmayın, Linux'u kullanmayın, Linux'u kullanmayın (Scriptlerden daha düşük bir programlamayı beğendim, Linux beni sıkıldım).

Konu konusuna geri dönerseniz, mikrodenetleyicilerin fiyatı, büyük şirketler için yeni bir ürünü serbest bırakacak, ancak bireysel düzeyde, Kickstarter tarzında iş yapmaya çalışırsanız, bu faktör Artık çok önemli değil, aslında, hızlı gelişme süresi, bileşenlerin maliyetinden daha önemlidir.

Öte yandan, mikrodenetleyiciler, düşük enerji tüketimi gerektiğinde sistem-on yongadan en iyi seçim olabilir. Bu tür sistemlerde iki nokta vardır: Diyagramın düşük tüketimi, çalışma sırasında ve kısa bir başlangıç \u200b\u200bzamanı. Küçük cihazlar için pili kaydetmenin tipik bir yolu kendi kendini kapatma (kapanır). Bilgisayarı Linux'ta kapattığınızda, işe geri dönmek için iyi bir zamana, bazen birkaç dakika kadardır. Bu süre gömülü sistemler için kabul edilemez.

Böyle bir mikrodenetleyici MSP430 olarak alırsanız, bir pilden yıllarca çalışabilir. Stellaris Launchpad ve Arduino, prensip olarak, aynı, aynı şekilde, MSP430'dan daha fazla enerji tüketir, ancak hala çok az, ahududu pi ile karşılaştırıldığında çok az. Ayrıca, MSP430, kapatıldıktan sonra anında başlayabilir.

Böylece, düşük voltaj işlemlerinin ihtiyaç duyduğu tüm durumlarda, mikrodenetleyicileri kullanmak mantıklı olduğuna eminim. Böyle bir ihtiyacın ortaya çıktığı piller üzerinde çalışan çok sayıda farklı cihaz vardır.

Üçüncü durumda, dediğim gibi, bir mikrodenetleyicinin kullanımı, anında reaksiyon gerektiren işlemlerde Linux'tan daha anlamlıdır (gerçek zamanlı yanıt). 3D yazıcılar ve CNC makineleri gibi cihazlar demek istediğim, okumak için çok zaman ayırmak için ne hakkında konuştuğumu biliyorum. Doğa ile, işte yüksek hassasiyet gerektiriyorlar, bu da komutların tepki süresine tamamen bağlıdır.

Örneğin, şu anda bir tahtadan veya metal parçasını kesen dairesel bir testere varsa, işlemi durduramazsınız, bunu kontrol etmesi nedeniyle, verileri bellekten çıkarmak bir duraklama alır. disk veya aynı damarda başka bir şey. Bir PC'yi kullanan herkes, normal çalışma sırasında periyodik olarak ortaya çıkan rastgele haddeleme aşinadır. Ve şimdi, bir PC'nin çalıştırdığınızı, bir aniden çalışma sırasında Windows için güncellemeleri kontrol etmeye başlayan ve buna değdiği tabloyu kontrol etmeye başlayan bir PC çalıştırmanızı hayal edin, çünkü Bilgisayar bunun üzerinde kontrolü kaybetti.

PC'ler ve yonga sistemlerinin gerçek zamanlı olarak çalışması amaçlanmamıştır, en azından pencerelerle bile, hatta Linux'la bile, ancak kendi başına daha yakın olmaya çalışıyorlar. Örnek olarak, Linux çekirdeği için gerçek zamanlı bir yama ve bu tür için oluşturulan özel bir CNC yazılımı vardır. Bu yama Linux ile yeterli değilim ve gerçek zamanlı olayları tamamlamak için ne kadar esnek olduğunu bilmiyorum. Ama bunun sadece olası bir alternatif olduğunu düşünüyorum, çünkü Linux, hangi yamaların üzerine düştüğü, kesme sistemleri nedeniyle bu alandaki mikrodenetleyicileri asla geçmeyecektir.
Sonuç olarak, projelerimdeki mikrodenetleyicilerin kullanımının bir avantajı olduğu yerleri bulmaya çalışırken çok zaman harcadığımı söylemek istiyorum. Ve her şey dünya hakimiyeti Ahududu Pi ve Beaglebones dönemine benziyor. Bu, DIY topluluğundaki mevcut durum. Çoğu durumda, bu sistemlerde gelişmesi daha hızlı ve daha kolay, bu nedenle çoğu proje için en iyi seçimdir.

Yalnızca düşük voltajlı cihazların alanları, gerçek zamanlı işlemler ve düşük maliyetli cihazlar mikrodenetleyiciler için kalır.

Mikrodenetleyicilerin PC'den daha eğlenceli görünebileceği gerçeğine bağlı değildir. Yarışmak için neyin geleceği budur.

İngilizceden Çeviri Orijinal Post