«

»

Oct
03

Arm Cortex Programlama – 1

Arm Cortex M serisi ile maceram yeni başladı. Arm Cortex programlama hakkında öğrendiklerimi yazı dizisi halinde yayınlamayı düşünüyorum. Bu ilk yazım bir nevi hello world yazısı olacak. Taskler ve onların tanıtılıp yaratılması ile real time programlamaya giriş yapılacak.

Kullandığım Araçlar:

Kit (Donanım): LPC 1114 LPCXpresso kiti. Üzerinde Arm Cortex M0 var. Usb kablo ile enerjilenebiliyor ve programlanabiliyor.

İşletim Sistemi: Ubuntu 11.04 Gnome Classic

LPCXpresso (IDE): Programları yazıp, derleyip kitimize yükleyebildiğimiz eclipse tabanlı IDE.

FreeRTOS: Küçük boyutlarda Real Time (gerçek zamanlı) işletim sistemi. LPC 1114 için oluşturulmuş hazır proje örneğini direkt atabiliyorsunuz kitinize.

Başlamadan Önce Önemli Not: Yazdığınız kodları kitinize atmanız zaman alabilir veya atarken donmalar olabilir, bazen de haza verebilir. Bunun gibi şeylerle karşılaştığınızda LPCXpresso’yu kapatın. Cihanızın USB kablosunu ayırın ve LPCXpressoyu yeniden çalıştırıp yükleme işlemini tekrarlayın. Yılmayın kodunuzda hata olmadığı sürece tekrar deneyin. Üçüncü denemenizde muhtemelen olacaktır. FreeRTOS’u içine gömdüğünüz için biraz uzun sürüyor ve hata verebiliyor.

Gerçek Zamanlı sistemleri basitleştirmek için aynı anda bir çok işi yapabilme olarak düşünebiliriz. Daha düzgün bir tanımı için belki bir yazı daha yazabilirim. Böylece ufacık kitinizde bir program parçası sensörden veri okurken diğer bir program parçası da internetten gelebilecek istekleri bekler konumda tutulabilir. Bu program parçacıklarına Task diyoruz.

Task / Thread Nedir, Neden Gereklidir?

Task aslında programcıların bildiği threaddir. Ancak gömülü sistemlerde task terimi daha çok kullanılmaktadır. Task nedir sorusunun yanıtı aslında neden kullanılır sorusunun yanıtıdır. Diyelim iki sonsuz döngünüz var kodunuzun içinde ve çalıştırdınız. Programınız birinci döngüye girer ve döngüyü kırmadığınız sürece oradan çıkamaz. Ancak elimizde iki tane sonsuz döngü var ve biz bu iki işlemin de sürekli olarak yapılmasını istiyoruz! İşte burada thread / task kavramı ortaya giriyor. İki task oluşturuyoruz ve işlemcinin bu ikisini de yapabilmesini sağlıyoruz.

FreeRTOS

Kendi seçimim olmayan hazır örneği olduğu için başlangıçta kullanıp real sistemlerini öğrenmeyi hedeflediğim işletim sistemi. Open-Source ve küçük boyutlarda olması en büyük artısı ancak kullanım klavuzu 60 dolar. İnternette bulmama rağmen hiç de hoşnut değilim. 170 sayfalık kitapçığın 60 dolara satılması gereksiz. En azından sitede başlangıç için bir iki makale olmasını isterdim o da yok. En kısa zamanda linux tabanlı veya açık kaynaklı daha düzgün bir RT sistemine geçmeyi planlıyorum.

FreeRTOS’un en güzel yanı ise elimizde src/ dizininin altında bir main.c dosyası olması ve onunla istediğimiz gibi oynayabilmemiz. Ayrıca ayarlamalar için diğer kütüphane dosyalarında oynamalar yapmamız gerekecektir ileride ancak başlangıç için hiçbir ayar yapmadan kodunuzu yazabiliyorsunuz.

Task / Thread Tanımlama

Açıkçası çok kolay geldi. Generik bir pointerla void olarak fonksiyonumuzu tanımlamamız yeterli. Elbette içinde bir sonsuz döngü olması mantıklı. Yoksa neden task kullanalım :)

Aşağıdaki kodda iki task oluşturduk. Bunun gibi bir çok taski kolayca oluşturabiliriz. Aşağıdaki kodda debug_puts fonksiyonu ile LPCXpresso’nun konsoluna hello world’umuzu yazdırmış oluyoruz.

void vTaskDebuggerHeartbeat1(void *pvParameters)
{
	while(1)
	{
		debug_puts("Merhaba Dunya! >> Task1");
		vTaskDelay(configTICK_RATE_HZ*3);
	}
}
 
void vTaskDebuggerHeartbeat2(void *pvParameters)
{
	while(1)
	{
		debug_puts("Merhaba Dunya! >> Task2");
		vTaskDelay(configTICK_RATE_HZ*3);
	}
}

Task / Thread Yaratma

Sıra geldi tanıttığımız taskleri kullanmaya: bunun için C API’nin xTaskCreate() methodunu kullanıyoruz. Bu fonksiyonları tahmin edilebileceği gibi main methodunun içinde kullanmalıyız.

xTaskCreate( vTaskDebuggerHeartbeat1, (const signed portCHAR * const)"ping", configMINIMAL_STACK_SIZE,
			NULL, 3, NULL);
xTaskCreate( vTaskDebuggerHeartbeat2, (const signed portCHAR * const)"ping1", configMINIMAL_STACK_SIZE,
			NULL, 3, NULL);

Ardından FreeRTOS Scheduler’ı başlatılır:

vTaskStartScheduler();

Eğer tek bir işlemci vsadarsa, işlemci üzerinde anlık olarak sadece bir task çalışabilir. Ardından başka bir taske geçilir. Bu sebeple taskin iki durumundan sözedebiliriz: Running ve not running. Not running’de başka şeyler de var. Ama kolaylık olsun diye şimdilik böyle ayırdık. Not running kısmında taskin durumu kaydedilir ve resume olması beklenir. Aşağıdaki şekil daha açıklayıcı olabilir:

 

 

Task geçişi not running kısmından running kısmına geçince “switching in” veya “swapped in” denilir. Tam tersi için ise “switched out” veya “swapped out” denilir. FreeRTOS Schedulerı bu switch in ve out işini yapan tek birimdir.

Pragramın Çalıştırılması

Eklediğimiz kısımlarla kodumuzu kaydediyoruz ve freertos projesine sağ tıklayıp run diyerek kodumuzu atıyoruz. Sonuç olarak LPCXpresso konsolunda aşağıdakine benzer bir çıktı aldım.

Merhaba Dunya! >> Task1
Merhaba Dunya! >> Task2
Merhaba Dunya! >> Task1
Merhaba Dunya! >> Task2
Merhaba Dunya! >> Task1
Merhaba Dunya! >> Task2

 Sonuç

Başka bir programlama dilinde thread kavramına hakimseniz çok da zorlanıcağınızı düşünmüyorum. Çalışmalarıma devam edip yeni şeyler öğrendikçe buradan yazmaya devam edeceğim. Ayrıca RTOS için önerilere açığım. Kendi sistemim için herhangi bir RTOS’u nasıl uygun hale getireceğim konusunda bilgi ve tecrübe eksikliğim var. Yardımcı olabilicekler varsa buradan yazabilirlerse sevinirim.

2 comments

  1. Ahmet Deniz says:

    Merhabalar. Güzel bir başlangıç.

    FreeRtos’u nereden temin ettiniz acaba bu işlemci için?
    Kitle beraber verilen LPCXpresso programında mı var örnek olarak.

  2. Hasan Erdem says:

    Merhabalar
    LPC 1114 için yazılmış FreeRTOS kodu yok gibi web sitesinde. Siz nereden buldunuz?
    LPC 1768 kodlarını mı kullandınız?

Leave a Reply

Your email address will not be published.

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre user="" computer="" escaped="">