Lompat ke konten Lompat ke sidebar Lompat ke footer

Volatile Bahasa C dan Fungsinya

Pada level lebih tinggi, kompilator mengkonversi bahasa C menjadi bahasa kode sehingga program eksekusi yang dapat dijalankan tanpa kode program sesungguhnya. Sama dengan teknologi interpreter lainnya, teknologi kompilator juga telah mengalami perkembangan dalam hal konversi bahasa C. Ketika mengartikan sumber kode menjadi bahasa mesin, kompilator pada dasarnya mencoba melakukan optimisasi output sehingga kebutuhan bahasa mesin mejadi lebih sedikit untuk dieksekusi pada tahap akhir. Salah satu bentuk optimisasi yang dilakukan kompilator tersebut adalah menghilangkan bahasa mesin yang tidak perlu untuk mengakses variabel yang tidak berubah dari sudut pandang kompilator. 


Sebelum mempelajari materi tentang Volatile Bahasa C dan Fungsinya, terlebih dahulu pelajari materi tentang: Kelas Penyimpanan Bahasa C dan Fungsinya, Variabel Static Bahasa C dan Fungsinya, dan Nilai Default Variabel Static Bahasa C dan Fungsinya.

Perhatikan potongan kode program berikut ini:
uint32 status = 0;
while (status == 0)
{/* Diasumsikan bahwa status tersebut tidak akan berubah pada saat looping ataupun selama program dijalankan */
/* Selama nilai status adalah NOL, lakukan looping */}

Pada proses tersebut kompilator melakukan optimisasi dalam memperlihatkan status yang tidak berubah pada saat loop. Sehingga tidak diperlukan akses status lagi dan lagi setiap kali melakukan iterasi dari pengulangan. Kompilator dapat mengkonversi perulangan menjadi infinite loop sehingga tidak perlu dilakukan proses pembacaan bahasa mesin. Catatan, bahwa kompilator tidak menyadari status khusus variabel yang dapat diubah dari luar program saat ini pada waktu apapun atau IO operasi terjadi pada perangkat peripheral untuk perangkat port IO yang telah dipetakan pada variabel. Pada kenyataannya, kompilator diharapkan untuk dapat mengakses status variabel setelah semua iterasi selesai, meskipun tidak dilakukan modifikasi ataupun perubahan pada program yang telah dikompilasi oleh kompilator tersebut.

Ketika ada pendapat yang mengatakan bahwa optimisasi kompilator dapat di turn-off untuk program, namun demikian hal tersebut belum tentu dapat dilakukan secara nyata karena beberapa hal berikut ini:
  • Setiap implementasi kompilator berbeda sehingga bukan merupakan solusi yang portabel untuk dapat melaksanakan hal tersebut.
  • Hanya karena satu variabel, bukan berarti harus mematikan semua proses optimisasi yang dilakukan oleh kompilator pada keseluruhan program.
  • Dengan mematikan semua proses optimisasi, program low level tidak dapat bekerja seperti yang diharapkan karena akan meningkatkan terlalu banyak ukuran dan penundaan eksekusi.

Untuk Mengatasi Permasalah Tersebut, maka Solusi yang Dapat Digunakan Adalah Menggunakan Volatile.

Penggunaan "volatile", pada dasarnya, dibutuhkan untuk instruksi kompilator yang statusnya variabel khusus sehingga proses optimisasi tidak bisa dilakukan pada variabel tersebut. Untuk itu, akan didefinisikan jenis variabel seperti berikut ini:

volatile uint32 status = 0;

Untuk penyederhanaan penjelasan, disajikan contoh seperti yang diperlihatkan sebelumnya. Namun, secara umum penggunaan volatile adalah dengan pointer seperti berikut ini:

volatile uint32 * statusPtr = 0xF1230000

Berikut ini statusPtr melakukan pointer ke lokasi memori pada konten yang dapat berubah pada waktu tertentu dari beberapa perangkat peripheral. Perlu dicatat bahwa program yang dibuat mungkin tidak memiliki kontrol apapun atau pengetahuan apapun ketika memori mengalami perubahan, sehingga tujuan dari penggunaan "volatile" adalah agar kompilator tidak melakukan optimisasi untuk variabel volatile yang ditunjuk (pointer) oleh statusPtr tersebut.

Dalam hal ini "volatile" mengikuti standar dari ISO/IEC 9899 C11 - clause 6.7.3

“An object that has volatile-qualified type may be modified in ways unknown to the implementation or have other unknown side effects.”

“A volatile declaration may be used to describe an object corresponding to a memory-mapped input/output port or an object accessed by an asynchronously interrupting function. Actions on objects so declared shall not be ‘‘optimized out’’ by an implementation or reordered except as permitted by the rules for evaluating expressions.”

Pada standar C variabel "volatile" dapat diubah dari luar program dan karena hal inilah kompilator tidak seharusnya mengoptimisasi aksesnya. Sehingga dapat diperkirakan bahwa ketika memiliki banyak variabel "volatile" dalam suatu program maka dapat mengurangi beban optimisasi yang dilakukan kompilator.

Keyword volatile dimaksudkan untuk mencegah kompilator melakukan optimisasi pada object yang dapat mengubah proses yang tidak dapat ditentukan oleh kompilator.

Deklarasi object sebagai volatile dihilangkan dari optimisasi karena nilainya dapat diubah oleh kode luar program dari kode program saat ini. Sistem selalu membaca nilai saat ini dari object volatile dari lokasi memori ketimbang mempertahankannya dalam register sementara pada titik dimana hal tersebut digunakan, meskipun isntruksi sebelumnya diminta untuk nilai dari object yang sama. Jadi pertanyaan sederhanyanya adalah, apakah nilai dari perubahan variabel yang sedemikian rupa tidak dapat diperkirakan oleh compiler. Perhatikan contoh kasus berikut ini untuk menjawab pertanyaan tersebut.
  • Variabel global dimodifikasi oleh pelayanan rutinitas interrupt dari luar scope: contoh, sebuah variabel global dapat merepresentasikan sebuah port data, biasanya berupa pointer global seperti pemetaan memori OP yang dilakukan pembaruan secara dinamis. Data yang membaca port kode harus dideklarasikan sebagai volatile dengan tujuan untuk mengambil data terakhir yang tersedia pada port. Jika mengalami kegagalan dalam pendeklarasian variabel volatile, maka kompilator akan mengomptimisasi kode program sedemikian rupa yang akan membaca port sekali saja dan menjaganya dengan menggunakan nilai yang sama pada register sementara untuk meningkatkan kecepatan program (speed optimization). Secara umum, ISR digunakan untuk melakukan pembaruan data port ketika terdapat interrupt terhadap ketersediaan data baru.
  • Penerapan variabel global dengan multi-threaded: Terdapat banyak cara untuk melakukan threads communicationvizmessage passingshared memorymail boxes, dan lain sebagainya. Sebuah variabel global adalah bentuk form sederhana untuk berbagi memori. Ketika dua threads berbagi informasi melalui variabel global, maka dibutuhkan kualifikasi dengan volatile. Ketika threads beroperasi secara sinkron, maka setiap pembaruan dari variabel global pada setiap threads harus ditambah oleh threads yang lebih baru. Kompilator akan membaca variabel global dan menempatkannya pada variabel sementara dari konteks threads saat ini. Untuk mengubahnya dalam bentuk null terhadap dampak dari optimisasi kompilator, seperti variabel global, maka harus dinyatakan dalam bentuk volatile.

Baca Juga:

Ketika tidak digunakan qualifier volatile, maka akan muncul beberapa bentuk masalah berikut:
  • Kode program mungkin tidak pekerja sesuai perkiraan ketika optimisasi diaktifkan.
  • Kode program tidak bekerja sesuai perkiraan ketika interrupt enabled dan berfungsi.

Perhatikan contoh program berikut untuk memahami bagaimana kompilator menginterpretasikan (interpreterkeyword volatile. Pada contoh berikut nilai dari object const dibuat nilainya menggunakan pointer dan dilakukan kompilasi kode tanpa pilihan optimisasi. Maka kompilator tidak akan melakukan proses optimisasi apapun yang akan mengubah nilai dari object const.

Contoh:

// Proses kompilasi program

// tanpa menggunakan optimi

// sasi oleh kompilator

#include <stdio.h>

 

int main(void)

{

const int local = 10;

int *ptr = (int*) &local;

 

printf("Inisialisasi nilai"

" variabel lokal : %d \n", local);

 

*ptr = 100;

 

printf("Modifikasi nilai "

"variabel lokal: %d \n", local);

 

return 0;

}


Ketika dilakukan kompilasi kode program dengan "-save-tempsoption dari gcc, maka akan dilakukan generate tiga output file:
  • Preprosesing kode program, yang menghasilkan ekstensi .i
  • Assembly kode program, yang akan menghasilkan ekstensi .s
  • Object code, yang akan menghasilkan ekstensi .0

Kode program dikompilasi tanpa melakukan tahap optimisasi, sehingga ukuran dari kode assembly yang dihasilkan akan menjadi lebih besar.

Output:
[narendra@ubuntu]$ gcc volatile.c -o volatile –save-temps
[narendra@ubuntu]$ ./volatile
Inisialisasi nilai variabel lokal : 10
Modifikasi nilai variabel lokal: 100
[narendra@ubuntu]$ ls -l volatile.s
-rw-r–r– 1 narendra narendra 731 2016-11-19 16:19 volatile.s
[narendra@ubuntu]$

Selanjutnya, lakukan kompilasi program dengan pilihan optimisasi. Pada code thr berikut ini, "local" dideklarasikan sebagai const (dan non-volatile), GCC kompilator melakukan optimisasi dan mengabaikan perintah untuk mengubah nilai dari object const. Dengan hasil nilai dari object const adalah sama.

Contoh:

// Kompilasi kode program de

// ngan tahapan optimisasi

#include <stdio.h>

 

int main(void)

{

const int local = 10;

int *ptr = (int*) &local;

 

printf("Inisialisasi nilai dari"

" variabel lokal : %d \n", local);

 

*ptr = 100;

 

printf("Modifikasi nilai dari var"

"iabel lokal: %d \n", local);

 

return 0;

}

Pada contoh sebelumnya, program melakukan optimisasi sehingga ukuran dari assembly code menjadi lebih kecil.

Output:
[narendra@ubuntu]$ gcc -O3 volatile.c -o volatile –save-temps
[narendra@ubuntu]$ ./volatile
Inisialisasi nilai dari variabel lokal : 10
Modifikasi nilai dari variabel lokal: 10
[narendra@ubuntu]$ ls -l volatile.s
-rw-r–r– 1 narendra narendra 626 2016-11-19 16:21 volatile.s

Selanjutnya dideklarasikan object const sebagai volatile dan kompilasi kode program dengan pilihan optimisasi. Meskipun dilakukan kompilasi kode program dengan pilihan optimisasi, nilai dari object const akan diubah, karena variabel dideklarasi sebagai volatile artinya adalah tidak melakukan optimisasi apapun pada program.

Contoh:

// Kompilasi kode program 

// dengan tahapan optimisaasi

#include <stdio.h>

 

int main(void)

{

const volatile int local = 10;

int *ptr = (int*) &local;

 

printf("Inisialisasi nilai var"

"iabel lokal: %d \n", local);

 

*ptr = 100;

 

printf("Modifikasi nilai var"

"iabel lokal: %d \n", local);

 

return 0;

}

Output:
[narendra@ubuntu]$ gcc -O3 volatile.c -o volatile –save-temp
[narendra@ubuntu]$ ./volatile
Inisialisasi nilai variabel lokal: 10
Modifikasi nilai variabel lokal: 100
[narendra@ubuntu]$ ls -l volatile.s
-rw-r–r– 1 narendra narendra 711 2016-11-19 16:22 volatile.s
[narendra@ubuntu]$

Catatan: Beberapa contoh program yang diberikan sebelumnya mungkin hanya bekerja pada beberapa compiler khusus, dimana tujuan dari penggunaan contoh program tersebut adalah untuk dapat memahami tujuan dari konsep volatile.

9 komentar untuk "Volatile Bahasa C dan Fungsinya"

  1. Apa fungsi keyword volatile pada bahasa C?

    BalasHapus
    Balasan
    1. Keyword atau kata kunci volatile pada bahasa C adalah suatu kualifikasi yang diterapkan ke suatu variabel tertentu ketika variabel tersebut dideklarasikan. Dengan menggunakan keyword volatile tersebut maka kompilator dapat mengetahui bahwa nilai variabel tersebut dapat berubah kapan saja tanpa tindakan apapun yang diambil oleh kode program yang ditemukan kompilator selama proses kompilasi.

      Hapus
  2. Keyword volatile dapat diubah dari luar kode program yang dikompilasi oleh kompilator. Contoh, sebuah program dapat memetakan variabel volatile ke register yang dipetakan oleh memori, dimana dalam hal ini kompilator tidak akan menerapkan optimisasi apapun ke dalam kode program yang menangani variabel volatile tersebut.

    BalasHapus
  3. Kapan keyword volatile dapat digunakan?

    BalasHapus
    Balasan
    1. Keyword volatile dapat digunakan ketika ingin mencegah kompilator untuk menerapkan suatu optimisasi apapun pada objek yang dapat berubah dengan cara yang tidak dapat ditentukan atau diprediksi oleh kompilator. Dimana objek yang dideklarasikan sebagai volatile tersebut akan dihilangkan dari proses optimisasi karena nilainya dapat diubah oleh kode program diluar dari cakupan kode program itu sendiri dan kapan saja.

      Hapus
  4. Secara umum, apa fungsi dari keyword volatile pada bahasa pemrograman?

    BalasHapus
    Balasan
    1. Dalam bahasa pemrograman komputer, khususnya dalam bahasa pemrograman C, C++, C£, dan Java, keyword atau kata kunci volatile digunakan untuk menunjukkan bahwa nilai variabel dapat berubah diantara akses program yang berbeda, meskipun kode program dari nilai variabel tersebut tidak dimodifikasi.

      Hapus
  5. Apa fungsi dari keywor volatile secara sederhana?

    BalasHapus
    Balasan
    1. Keyword volatile digunakan untuk mengubah nilai variabel dengan suatu thread yang berbeda. Dimana hal ini juga digunakan untuk membuat thread secara aman atau terlindungi. Dengan keyword volatile tersebut maka beberapa thread dapat menggunakan beberapa method atau fungsi dan instance kelas secara bersamaan tanpa muncul permasalahan atau pesan error apapun. Keyword volatile dapat digunakan baik pada tipe data objek ataupun tiped ataupun primitif.

      Hapus

Hubungi admin melalui Wa : +62-896-2414-6106

Respon komentar 7 x 24 jam, mohon bersabar jika komentar tidak langsung dipublikasi atau mendapatkan balasan secara langsung.

Bantu admin meningkatkan kualitas blog dengan melaporkan berbagai permasalahan seperti typo, link bermasalah, dan lain sebagainya melalui kolom komentar.

- Ikatlah Ilmu dengan Memostingkannya -
- Big things start from small things -