Pages

Kamis, 18 Oktober 2012

Pemrograman dengan Bahasa Assembler 8051

BAB 2

Sasaran
Setelah anda menamatkan bab ini , diharapkan anda dapat :
ð          Menerangkan register-register dalam 8051.
ð          Memanipulasi data menggunakan register dan interuksi MOV.
ð          Membuat kode sederhana dengan menggunakan bahasa Asssembly 8051.

ð          Menjelaskan urutan kejadian saat 8051 baru saja dihidupkan.
ð          Menerangkan program dalam ROM kode dari 8051.
ð          Merinci kerja dari setiap instruksi dalam bahasa assembly 8051.
ð          Menjelaskan type data dalam 8051.
ð          Menjelaskan kegunaan register PSW (Program Status Word).
ð          Menjelaskan alokasi ruang untuk memory RAM dalam 8051.
ð          Menerangkan penggunaan stack dalam 8051
ð          Memanipulasi Bank register dari 8051.

Pada SubBAB 2.1 kita akan melihat bagian dalam pada 8051. Kita akan mendemonstrasikan beberapa register yang paling banyak digunakan dalam 8051 dengan instruksi sederhana misalnya adalah MOV dan ADD. Pada SubBAB 2.2 kita akan mempelajari pemrograman dengan bahasa Assembly dan bahasa mesin serta mengupas tentang beberapa hal penting misalnya mnumonic, opcode, operand, dll. Proses dari perakitan kode dan pembuatan program yang siap pakai untuk 8051 akan dibahas pada SubBAB 2.3. Dan dibagian 2.4 kita akan mempelajari langkah demi langkah dalam eksekusi program 8051 dan aturan tentang Program Counter. Di bagian 2.5 kita akan melihat beberapa Directive (petunjuk) bahasa Assembly yang banyak digunakan, pseudo-code, dan tipe data yang berhubungan dengan 8051. SubBAB 2.6 kita akan mendiskusikan bit-bit bendera dan bagaimana mereka berpengaruh pada instruksi-instruksi aritmatika. Pengalokasian memory RAM dalam 8051 termasuk stack dan bank register dalam 8051 akan kita bahas pada subBAB 2.7.





SubBAB 2.1 Bagian dalam 8051

Pada bagian ini kita akan mejelaskan register dari 8051 dan menggambarkan kegunaan mereka dalam instruksi-instruksi MOV dan ADD.

Register-register

Dalam CPU, register-register digunakan untuk menyimpan data secara sementara. Informasi dapat berupa data byte yang hendak diproses atau sebuah data alamat yang menunjuk pada data yang lain. Register-register dari 8051 pada umumnya adalah berupa register 8-bit. Dalam 8051 hanya ada satu jenis data yakni data 8-bit (sama dengan namanya yakni komputer 8-bit). Register 8-bit tersebut ditunjukkan dalam diagram mulai dari MSB (Most Significant Bit) / D7 sampai pada LSB (Least Significant bit) / D0. Dengan type data 8-bit tersebut, setiap data yang lebih besar dari 8-bit harus dipecah menjadi beberapa bagian data 8-bit sebelum dapat diproses. Mengingat banyak register dalam 8051, kita akan berkonsentrasi pada beberapa register yang paling sering digunakan.


Register yang paling banyak digunakan adalah A (Accumulator), B, R0, R1, R2, R3, R4, R5, R6, R7, DPTR (DataPointer), dan PC (Program Counter). Semua register tersebut adalah register 8-bit kecuali DPTR dan PC. Akumulator atau register A, digunakan dalam semua instruksi aritmatika dan logika. Untuk mengerti penggunaan dari register tersebut, kita dapat melihat mereka dalam konteks dari dua buah instruksi sederhana, MOV dan ADD.

gambar 2-1 Register 8-bit dan 2 buah register 16-bit pada 8051

Instruksi MOV

Singkatnya instruksi MOV adalah menyalin isi data dari register yang satu ke register yang lain, dengan format sebagai berikut :

MOV dest, source ;salin data source ke dest

Instruksi ini memerintahkan pada CPU untuk memindahkan (sebenarnya adalah menyalin) operand source menuju operand destination.Seperti contohnya, "MOV A,R0" adalah menyalin isi R0 ke register A. Setelah instruksi ini dijalankan isi dari kedua register tersebut adalah sama. Instruksi MOV tidak mengubah isi dari operand Source. Program berikut ini adalah contoh untuk mengubah Akumulator menjadi 55h (h adalah hex), lalu kemudian memindahkan nilainya kedalam beberapa register dalam CPU. Perhatikan tanda "#" dalam instruksi tersebut. Hal itu mengindikasikan bahwa simbol dibelakangnya adalah sebuah nilai. Hal tersebut akan kita bahas segera.

      MOV A,#55         ;Mengisi A dengan nilai 55h
      MOV R0,A          ;Salin isi A ke dalam R0
                        ;Sekarang R0 = 55h
      MOV R1,A          ;Salin isi A ke dalam R1
                        ;Sekarang R1 = 55h
      MOV R2,A          ;Salin isi A ke dalam R2
                        ;Sekarang R2 = 55h
      MOV R3,#95h       ;Mengisi R3 dengan nilai 95h
                        ;Sekarang R3 = 95h
      MOV A,R3          ;Salin isi R3 ke dalam A
                        ;Sekarang A = 95h

Saat menulis program untuk mikrokontroller 8051, hal-hal berikut ini harus diperhatikan.

1. Bahwa sebuah nilai dapat langsung diberikan pada register-register misalnya A, B, R0 s/d R7. Namun bagaimanapun juga untuk mengindikasikan bahwa sebuah simbol adalah sebagai sebuah nilai, dan bukan sebagai alamat atau yang lain, sebelumnya harus diberi simbol pound atau pagar atau "#".

      MOV A,#23h        ;Mengisi A dengan nilai 23h
      MOV R0,#12h       ;Mengisi R0 dengan nilai 12h
      MOV R1,#1Fh       ;Mengisi R1 dengan nilai 1Fh
      MOV R2,#2Bh       ;Mengisi R2 dengan nilai 2Bh
      MOV B,#3Ch        ;Mengisi R3 dengan nilai 3Ch
      MOV R7,#9Dh       ;Mengisi R3 denga nilai 9Dh
      MOV R6,#0F9h      ;Mengisi R3 denga nilai F9h
      MOV R5,#12        ;Mengisi R3 denga nilai 12 desimal

Perhatikan pada instruksi "MOV R5,#0F9h" sebelum simbol F nampak di sana diimbuhi oleh simbol "0" sehingga menjadi "0F9h". Hal ini penting bagi assembler untuk membedakan apakah sebuah symbol yang dituliskan itu sebagai sebuah angka bilangan atau sebuah identifier. Sedang identifier harus selalu dimulai dari karakter alphabeth.

2. Jika nilai 0 s/d F kita isikan pada sebuah register 8-bit, maka akan mengubah 4-bit paling kecil dari register tersebut. Dan kita akan mendapatkan 4-bit teratas darinya akan dibuat menjadi 0. Misalnya dengan instruksi "MOV A,#5", maka sejatinya instruksi tersebut adalah sama dengan "MOV A,#05h", dan menghasilkan A = 05h. Dan dalam bilangan biner adalah A = 00000101 biner.

3. Mengisikan sebuah nilai yang terlalu besar dari nilai yang sanggup ditampung sebuah register akan menghasilkan error.
      MOV A,#7F2h       ; 7F2h > (8-bit atau FFh atau 255 desimal)
      MOV R2,#456       ; 456d > (8-bit atau FFh atau 255 dec)

4. Untuk mengisikan nilai ke dalam  register, kita harus mengimbuhkan symbol pound (#). Jika tidak ada simbol tersebut, maka assembler akan menganggapnya sebagai sebuah lokasi memory. Ambil contoh "MOV A,17h" yang berarti pindahkan isi nilai dari memory 17h ke dalam A. Sedang saat kita menginginkan untuk mengisi A dengan nilai 17h, maka kita harus menuliskan dengan "MOV A,#17h". Tidak adanya symbol pagar tersebut tidak akan membuat assembler menghasilkan error. Namun Assembler akan membuatkan kode yang bukan seperti kemauan kita, hanya karena kesalahan kecil kita dalam menulis program. Biasanya hal ini biasa terjadi bagi para pemula.

Instruksi ADD

Instruksi ADD adalah berdasar pada format :

      ADD  A,Source     ;Tambahakan source ke Akumulator

Instruksi ini menambahkan sembarang tipe data ke dalam A dan A pula bertindak sebagai penerima hasil dari operasi. Sehingga dapat dikata operand tujuan (Dest) selalu adalah Akumulator (A). Di bawah ini contohnya…

      MOV  A,#25h       ;Isi A dengan nilai 25h
      MOV  R2,#34h      ;Isi R2 dengan nilai 34h
      ADD  A,R2         ;Tambahakan keduanya
;Jadi A = A + R2

Menjalankan program di atas akan menghasilkan A = 59h (25h + 34h = 59h) dan nilai pada R2 tidak berubah setelah instruksi ADD, yakni 34h. Sekali lagi operand source tidak akan berubah. Program di bawah ini adalah contoh program yang lebih kompleks.

      MOV  R5,#25h      ;Isi R7 dengan nilai 25h
      MOV  R7,#34h      ;Isi R5 dengan nilai 34h
      MOV  A,#0         ;Clear isi A menjadi 0
      ADD  A,R5         ;Tambahakan A dengan isi R5
;Jadi A = A + R5
      ADD  A,R7         ;Tambahakan A dengan isi R7
;Jadi A = A + R7

Program di atas menghasilkan nilai 59h yang terdapat pada A. Ada banyak jalan menuju Roma, namun sedapat mungkin cari jalan yang paling singkat dan cepat. Ini adalah cara lebih cepat.

      MOV  A,#25h       ;Isi A dengan nilai 25h
      ADD  A,#34h       ;Tambahakan A dengan 34h
     
Sekali lagi dapat kita lihat dari berbagai contoh di atas operand tujuan selalu adalah A. Jika kita memaksa menuliskan kode seperti "ADD R2,A" tentu akan menghasilkan error. 8051 memang hanya mendukung operasi arimatika dan logika yang hanya menggunakan A sebagai akumulator, dan dengan kata lain operasi tersebut dibatasi selebar 8-bit. Namun walaupun demikian hal itu sudah lebih dari cukup untuk membuat program untuk berbagai aplikasi canggih, misalnya robot.

Kita tahu bahwa 8051 juga memiliki 2 buah register 16-bit, walaupun dirancang bukan untuk keperluan manipulasi data. Namun jika anda bertanya apakah CPU 8051 dapat memanipulasi data yang lebih besar dari 8-bit?? Tentu saja, tidak ada hal yang tidak mungkin. Seperti yang sudah kita ketahui sebelumnya bahwa komputer 8-bit, idealnya hanya memproses data sampai selebar 8-bit. Dalam kasus tertentu beberapa perintah dalam 8051 dapat diurutkan untuk dapat menangani data yang lebih besar, seperti data 16-bit, 24-bit, maupun 32-bit. Semua bisa dilakukan. Tentu dengan memecah data tersebut dalam beberapa data 8-bit,dan kemudian memprosesnya satu-persatu kemudian menyatukan kembali data sehingga seperti hasil yang kita inginkan. Dalam prakteknya hal itu bisa dilakukan dengan membuat kode-kode yang rumit dan teliti. Dan nantinya akan dibahas pada Bab lain.






SubBab 2.2 Mengenal Pemrograman Assembly 8051

Pada bagian ini kita akan membahas format dari bahasa assembly dan mengupas terminologi yang berkaitan hal yang paling sering digunakan dalam pemrograman bahasa assembly.
Mengingat CPU bekerja hanya dalam biner, dan dilakukan dengan kecepatan yang sangat tinggi. Biner adalah serupa dengan dua buah keadaan, kalau tidak 0s maka itu mestinya adalah 1s, begitu pula sebaliknya. Maka kita harus familiar dengan 010010110, itulah biner. Bilangan biner yang berupa kode perintah dinamakan bahasa mesin. Pada computer terdahulu, programer menulis kode dalam bahasa mesin seperti itu. Namun agar lebih mudah dari menulis kode dengan biner, dibuatkah format bilangan yang dapat merepresentasikan biner dengan baik, yakni menggunakan bilangan Heksadesimal. Dan hasilnya, programer merasa jauh lebih mudah dari pada mengingat kombinasi "0" dan "1". Namun menulis kode dalam bahasa mesin Heksadesimal masih juga terlalu rumit bagi kebanyakan programer. Akhirnya, pada masa sekarang, dibuatlah sebuah bahasa assembler yang berisi mnumonic (symbol bahasa mesin dalam bahasa manusia yang mudah diingat), untuk setiap instruksi kode mesin, dan didukung juga beberapa kelebihan lain untuk mempermudah pembuatan program, termasuk pengujian atas kemungkinan adanya error dalam penulisan. Sekarang mnumonic digunakan secara luas dalam bidang ilmu pengetahuan, buku-buku tehnik yang merujuk pada kode dengan tujuan semuanya agar lebih mudah untuk diingat. Kode bahasa assembly diterjemahkan ke dalam bahasa mesin oleh sebuah program lain, yang kemudian disebut sebagai Assembler. Bahasa assembly juga dikenal sebagai bahasa tingkat rendah (low-level-languages) karena bahasa ini adalah yang paling berhubungan langsung dengan struktur CPU. Dalam memprogram bahasa ini, programer harus benar-benar mengenal semua register dalam CPU, ukuran masing-masingnya, termasuk berbagai detil dari instruksi serta efeknya terhadap register.
Namun sekarang, seseorang dapat menggunakan berbagai bahasa yang jauh lebih memudahkan, misalnya seperti BASIC, Pascal, C, C++, Java , dan banyak lagi lainnya.
Java bukan HoNoCoRoKo-nya jawa !!! Pesan penterjemah, kita harus bangga salah satu bahasa daerah kita digunakan sebagai nama bahasa program, walaupun mereka tanpa hak paten menggunakan nama "Java". Bagaimana nich DepKomInfo ??? Seharusnya yang namanya "Java Script" artinya "Tulisan Jawa" adalah hak-patennya negara kita, bukan ?!?!
Bahasa-bahasa di atas kemudian disebut dengan bahasa tingkat tinggi (high-level languages) karena kita tidak perlu mengenal lebih jauh tentang isi dari struktur CPU target. Bahasa ini kemudian diterjemahkan ke dalam bahasa assembler, baru kemudian ke bahasa mesin, atau beberapa program dapat langsung mengubah dari bahasa tingkat tinggi itu langsung menjadi bahasa mesin. Program yang dapat melakukan itu kemudian disebut dengan Compiler. Misalnya kita menulis program dalam bahasa C, maka kita harus menggunakan C-Compiler untuk kemudian mengubah kode program kita menjadi bahasa mesin. Namun untuk sekarang, kita berkonsentrasi pada bahasa assembly yang khusus untuk 8051, dan membuat program yang dapat bekerja dengan baik hanya dengan menggunakan bahasa itu. Assembler yang kita gunakan ini adalah sebuah program yang dibuat bersama-sama begitu diperkenalkannya Chip 8051 oleh Intel, yakni program "ASM51.EXE" dengan nama resmi "MCS-51 MACRO ASSEMBLER V2.3" buatan Intel Corporation 1976, 1986. Kita dapat meng-unduh (download) dari Internet secara gratis.

Struktur dari bahasa assembly

Program bahasa assembly terdiri dari beberapa bagian. Setiap instruksi diungkapkan dalam satu baris kode. Setiap instruksi terdiri dari mnumonic, dan kadang ditambahkan 1 atau 2 operand. Operand adalah data yang hendak dimanipulasi. Dan mnumonic itulah yang meninstruksi-kan CPU untuk melakukan sesuatu terhadap operand.

Program 2.1 Contoh program dalam bahasa Assembly

      ORG 0               ;Mulai program dari alamat 0000
      MOV R5,#25h         ;Isikan 25h pada R5
      MOV R7,#34h         ;Isikan 34h pada R7
      MOV A,#0            ;buat A = 0
      ADD A,R5            ;Tambahkan isi R5 ke dalam A
                          ;sehingga A = A + R5
      ADD A,R7            ;Tambahkan isi R7 ke dalam A
                          ;sehingga A = A + R5
      ADD A,#12h          ;Tambahkan 12h ke dalam A

TUNGGU: SJMP TUNGGU       ;program selesai dan berputar di sini
      END



Program dalam bahasa assembly yang dicontohkan di atas adalah statement yang berurutan, di mana terdiri dari instruksi misalnya ADD dan MOV, dan beberapa statement lain, yang disebut dengan Directive. Setiap instruksi, adalah memerintahkan CPU untuk melakukan sesuatu hal, sedang directive ( juga disebut dengan psuedo-instruction) memberikan arahan bagi assembler cara menterjemahkan kode di belakang ungkapan directive tersebut. Ambil contoh, intstruksi MOV dan ADD adalah sebuah perintah, sedang ORG dan END adalah directive (petunjuk arahan) bagi assembler. ORG dalam contoh diatas meminta kepada Assembler bahwa opcode selanjutnya agar ditempat dalam memory lokasi 0, sementara END adalah untuk memberitahukan assembler akhir dari program, dan mengabaikan setiap text di bahwa END.

Pada prinsipnya instruksi bahasa assembly terdiri dari 4 bagian :

[label] mnumonic [operand] [;komentar]

tanda kurung diatas (bracket) adalah menunjukkan bagiannnya, agar anda bisa lebih jelas, dan bukan dimasukkan dalam kode yang sebenarnya. Adapun penjelasannya adalah sebagai berikut ini :
1.    Bagian Label adalah sebuah identifier yang merujuk padaa lokasi opcode. Dengan kata lain nilai dari Label ini adalah relatif, dan ditentukan saat proses kompilasi. Berbeda dengan identifier lain yang nilainya harus ditentukan dengan expresi EQU, DATA, dll dengan diberikan nilai yang tetap (Konstanta). Karena sifat dinamisnya Instruksi JUMP yang merujuk pada Label, lokasi jump akan dihitung kembali agar menghasilkan lokasi Jump yang tepat, pada lokasi milik Label. Deklarasi Label adalah mirip dengan deklarasi identifier lain dan diakhiri dengan karakter titik-dua. Identifier hanya bisa dibentuk dengan karakter pertama adalah karakter Alphabet, dan karakter selanjutnya boleh juga numerik, dan karakter "_" serta "?".  Panjang Label ini juga tidak boleh melebihi 255 karakter.
2.    Bagian menumonic dan bagian operand dalam bahasa assembly adalah bagian utama dari kode program. Dan operand adalah spesifik atas mnumonic, yang mengisyaratkan tugas tertentu (Seperti yang sudah diatur oleh pabrik pembuat Chip dalam datasheet-nya). Ungkapan (statement) dalam bahasa assembly misalnya adalah :

            ADD A,B
            MOV A,#67

   ADD dan MOV adalah mnumonic dimana akan menghasilkan opcode. Sedang "A,B" dan A,#67" adalah operand. Di luar kedua bagian ini, yakni mnumonic dan operand adalah disebut sebagai instruksi-psuedo, atau directive. Ingat bahwa sebuah directive tidak akan menghasilkan kode mesin (opcode), dan mereka digunakan oleh assembler saat memutuskan bagaimana caranya untuk menterjemahkan mnumonic dan operand yang ada di belakang directive tersebut ke dalam kode mesin yang benar sesuai dengan kemauan kita. Dalam program 2.1 perintah ORG (original) dan END adalah contoh dari directive (beberapa assembler menggunakan syntax .ORG dan .END). Periksa assembler anda untuk penjelasan lebih jauh. Lebih jauh tentang pseudo akan kita bahas pada bagian 2.5
3.    Bagian komentar dimulai dengan karakter semi-colon (titik-koma) yang berarti karakter-karakter setelahnya adalah sebuah komentar. Assembler akan segera mengabaikan karakter-karakter sesudah karakter semi-colon tersebut. Mengingat assembler adalah menterjemahkan baris demi baris dalam program, maka setiap komentar harus dimulai dari karakter semi-colon itu, walaupun dalam baris tersebut tidak terdapat instruksi apapun.
4.    Perhatikan label "HERE" dalam program 2.1 adalah bagian Label. Setiap label harus diakhiri dengan simbol colon (titik-dua). Dalam instruksi SJMP (Short Jump), 8051 diberitahu untuk berhenti disitu, atau dengan kata lain berputar-putar terus ditempat yang sama.





SubBAB 2.3 Meng-Assembling dan Menjalankan program untuk 8051

Sekarang dasar-dasar dari program bahasa assembly telah diberikan. Dan pertanyaan berikutnya adalah, Bagaimana itu semua bisa dibuat, dirangkai (assembling), dan siap untuk dijalankan? Inilah langkah-langkah untuk membuat program berbahasa assembly.
1.    Pertama adalah dengan menggunakan editor yang umum, ketikkan program seperti pada Program 2.1. Berbagai Editor dapat digunakan untuk membuatnya, misalnya notepad atau bahkan MS-DOS EDIT, yang kesemuanya disertakan oleh Microsoft Windows. Ingat bahwa editor yang kita gunakan harus dapat menghasilkan file ASCII. Beberapa assembler meminta kita untuk menamakan file program kita dengan nama berformat DOS 8+3 yang diberi ekstensi ".asm" atau ".src", tergantung dari Assembler anda. Namun kita berkonsentrasi pada ektensi ".asm".
2.    File ".asm" yang telah kita buat  seperti langkah 1 di atas, sekarang diminta oleh Assembler 8051. Assembler ini akan mengubah setiap instruksi dalam file tersebut menjadi kode mesin. Assembler ini menghasilkan file Object dan file List. Object file berekstensi ".obj", sedang file List berekstensi ".lst". Program yang dapat melakukannya misalnya program "ASM51.EXE" dengan nama "MCS-51 MACRO ASSEMBLER V2.3" buatan Intel Corporation 1976, 1986. Yang dapat diunduh (download) dari Internet.
3.    Jika kita membuat sebuah program yang sangat besar dan menghasikan beberapa file object. Maka dibutuhkan langkah ke 3 ini yang disebut sebagai linking. Dengan file ini beberapa file object dapat dijadikan satu file besar absolute yang berekstensi ".abs". Umumnya file abs ini digunakan untuk latihan, jika kita memiliki program monitor.
4.    Selanjutnya file ".abs" ini akhirnya diubah sebagai bahasa mesin yang sebenarnya, yakni satu file kode mesin dengan ekstensi ".hex". Program "OH.EXE" dengan caption "V1.0 Intel Corporation 1986" yang dapat melakukan hal itu. Namun hebatnya program OH ini dapat langsung mengubah satu file ".obj" menjadi satu file kode mesin. Akhirnya muncul beberapa assembler canggih belakangan ini sudah merangkum semua proses menjadi satu program saja, bahkan termasuk dengan simulasinya segala.


Lebih jauh tentang file "asm" dan "obj"

File "asm" dapat disebut pula sebagai file source (sumber), dan untuk alasan inilah beberapa assembler juga mendukung extensi ".src".

File Lst
File Lst (List), adalah tambahan, namun bagaimanapun juga file tersebut adalah sangat penting karena file tersebut adalah mendaftar setiap opcode yang telah dibuat oleh assembler, termasuk alamat-alamatnya, dan termasuk pemberitahuan jika ada error atau kesalahan dalam penulisan program. Beberapa Assembler tidak otomatis mebuatkan file Lst tersebut untuk kita, dan membutuhkan perintah tambahan dalam DOS Command Promt saat menjalankan Assembler yang bersangkutan. (Namun untuk program Assembler ASM51.EXE buatan Intel sudah otomatis membuatkan file Lst). File tersebut sangat penting bagi programer untuk melihat setiap baris syntax yang dituliskan apa sudah benar atau tidak. Termasuk dapat melihat alamat setiap opcode dengan jelas.

Program 2.1 List File-nya

LOC  OBJ    LINE  SOURCE

0000           1  ORG 0        ;Mulai program dr 0000
0000 7D25      2  MOV R5,#25h  ;Isikan 25h pada R5
0002 7F34      3  MOV R7,#34h  ;Isikan 34h pada R7
0004 7400      4  MOV A,#0     ;buat A = 0
0006 2D        5  ADD A,R5     ;Tambahkan isi R5 ke dlm A
               6               ;sehingga A = A + R5
0007 2F        7  ADD A,R7     ;Tambahkan isi R7 ke dlm A
               8               ;sehingga A = A + R5
0008 2412      9  ADD A,#12h   ;Tambahkan 12h ke dalam A
               10    
000A 80FE      11 TUNGGU: SJMP TUNGGU  ;program selesai dan
               12 END






SubBAB 2.4 Ruang ROM dan Program Counter dalam 8051

Di bagian ini kita akan menjelaskan tentang register Program Counter (PC) dalam proses menjalankan perintah pada program 8051. Kita juga akan mebahas ruang (space) ROM untuk berbagai variant dari keluarga 8051.

Program Counter dalam 8051

Regsiter penting lainnya dalam 8051 adalah PC (Program Counter). Program Couter adalah menunjuk lokasi dari alamat selanjutnya yang hendak dijalanakan. Setelah CPU membaca program dari ROM program, program Counter kemudian di-INCrement (ditambah satu bilangan) yang berarti menunjuk pada alamat byte selanjutnya dalam ROM Porgram. Program Counter dalam 8051 adalah termasuk register 16-bit. Artinya 8051 dapat mengakses program mulai dari alamata 0000 s/d FFFFh, sehingga total adalah 64 Kbytes. Namun tidak semua variant keluarga 8051 memiliki ROM program sebanyak itu di dalam chip-nya. Beberapa diantaranya hanya memiliki 2 Kbytes atau bahkan tidak sama sekali sehingga membutuhkan ROM program tambahan secara external. Bagaimana 8051 dan Program Counter-nya saat pertama listrik daya-nya dihidupkan ?? Hal tersebut akan kita bahasa pada kesempatan yang lain

Mulai dari bagian mana dari Program saat 8051 pertama dinyalakan

Pertanyan yang harus kita tanyakan mengenai setiap microcontroller (microprocessor). Pada lokasi mana dari ROM program, sebuah CPU memulai tugas-tugasnya saat kita mulai menyalakan dengan menghubungkannya dengan Listrik PLN misalnya. Setiap Micro proscessor adalah berbeda-beda. Namun dalam keluarga 8051 apapun pabrik pembuatnya atau penjualnya lokasi pertama yang dijalankan oleh 8051 saat pertama dihidupkan adalah lokasi 0000. Menghidupkan atau menyalakan maksudnya dalah memeberikan daya sebesar Vcc yang dibutuhkan untuk pin Vcc. Atau menggunaan pin Reset,yang akan dibahasa lebih jauhpada BAB 4. Dengan kata lain saat 8051 pertama dihidupkan PC selalu bernilai 0000. Yang berarti bahwa pada loikasi ini opcode pertama yang akan dijalankan. Untuk alasan ini lah setiap program dalam 8051  harus dimulai dari lokasi 0000 dan dituliskan ke dalam ROM program juga dimuklai dari alamayt 0000. Kita dpat memastika agar assembler memulai penyusuan kode program dari alamat tersebut dengan memberikan direvtive ORG dalam program kita. Nantinya kita akan membahas bagaiaman melihat setia aksi dari Program Counter dalam proses pembacaan ROM program.

Menempatkan kode dalam ROM program

Untuk dapat lebih mengerti, aturan dari bagaimana Program Counter mengambil data dan dieksekusi oleh CPU, kita akan menjelaskan aksi dari Program Counter ini. Pertama, adalah menjelsakan sekali lagi file List dari program contoh dan bagaiaman kode ditempatkan dalam ROM yang terdapat dalam chip 8051. Seperti yang kita lihat bahwa opcode dan operand untuk setiap instruksi ditampilkan dalam file tersebut pada bagian sebelah kiri file list tersebut.

Program 2.1 List File-nya

LOC  OBJ    LINE  SOURCE

0000           1  ORG 0        ;Mulai program dr 0000
0000 7D25      2  MOV R5,#25h  ;Isikan 25h pada R5
0002 7F34      3  MOV R7,#34h  ;Isikan 34h pada R7
0004 7400      4  MOV A,#0     ;buat A = 0
0006 2D        5  ADD A,R5     ;Tambahkan isi R5 ke dlm A
               6               ;sehingga A = A + R5
0007 2F        7  ADD A,R7     ;Tambahkan isi R7 ke dlm A
               8               ;sehingga A = A + R5
0008 2412      9  ADD A,#12h   ;Tambahkan 12h ke dalam A
               10    
000A 80FE      11 TUNGGU: SJMP TUNGGU  ;program selesai dan
               12 END


Hasilnya adalah …
Setelah program ditulis (burned) ke dalam ROM internal dalam chip 8051 (misalnya AT89C51 atau DS5000). Opcode dan operand ditempatkan pada ROM program dimulai dari alamat 0000 seperti yang ditunjukkan dalan daftar dibawah ini.

Alamat ROM        Kode mesin        Kode Assembly
0000              7D25              MOV R5,#25h
0002              7F34              MOV R7,#34h
0004              7400              MOV A,#0
0006              2D                ADD A,R5
0007              2F                ADD A,R7    
0008              2412              ADD A,#12h
000A              80FE              TUNGGU: SJMP TUNGGU

Daftar tersebut menunjukkan alamat 0000 berisi 7D dimana adalah opcode untuk mengisikan nilai ke register R5, dan alamat 0001 adalah berisi operand (dalam daftar, terlihat 25h) yang diisikan dalam R5. Sehingga instruksi "MOV R5,#25h" adalah memiliki kode mesin "7D25" dimana 7D adalah opcode dan 25 adalah operand. Hal yang sama juga pada kode mesin 7F34 yang berlokasi dalam 0002 dan 0003 yang merupakan representasi dari instruksi "MOV R7,#34h". Termasuk juga untuk kode mesin 7400 yang berada dalam lokasi 0004 dan 0005 adalah representasi dari instruksi "MOV A,#0". Lokasi memory 0006 memiliki opcode 2D dimana itu adalah opcode untuk instruksi  "ADD  A,R5" dan lokasi memory 0007 adalah berisi 2F, dimana opcode untuk instruksi "ADD A,R7". Opcode dari intstruksi "ADD A,#12h" berlokasi pada alamat 0009. memory lokasi 000A berisi opcode dari instruksi SJMP. Sedang alamat target dari opcode SJMP tadi adalah isi dari lokasi 000B. Arti dari alamat target yang berisi FE akan dijelaskan pada bab selanjutnya.

Sedang dibawah ini adalah isi ROM menurut alamatnya.

Program 2-1 Isi ROM
Alamat     Code
0000       7D
0001       25
0002       7F
0003       34
0004       74
0005       00
0006       2D
0007       2F
0008       24
0009       12
000A       80
000B       FE


Menjalankan Program byte demi byte

Anggaplah program di atas sudah ditulis di dalam ROM dari Chip 8051 (atau 8751, AT89C51, atau DS5000), berikut ini adalah penjelasan langkah-langkah dari kejadian dalam 8051 ,setelah catu daya diberikan.
1.    Saat 8051 dinyalakan, PC (Program Counter) memiliki nilai 0000 dan mulai membaca opcode pertama, yakni 7D, yang mana kode tersebut berarti mengisikan operand ke dalam R5. Setelah menjalankan opcode tersebut CPU melalui bantuan PC kembali membaca lokasi ROM program berikutnya yakni  25, dan selanjutnya menjalankan tugasnya yakni memindahkan nilai 25 pada R5. Sekarang 1 instruksi sudah selesai. Selanjutnya Program Counter sudah di-INC-rement ke lokasi untuk opcode berikutnya, yakni ke alamat 0002. (PC==0002) dimana berisi opcode 7F, yang berarti opcode untuk instruksi "MOV R7,…".
2.    Setelah menjalankan opcode 7F, nilai 34h lalu dipindahkan pada R7. Kemudian Program Counter lagi dengan meng-inc-rement dirinya sendiri hingga kemudian menunjuk alamat 0004.
3.    ROM lokasi 0004 berisi opcode untuk instruksi "MOV A,#0". Instruksi ini adalah instruksi 2-byte, yang berarti masing-masing opcode dan operan menggunakan 1-byte.
4.    Sekarang PC = 0006 yang menunjuk alamat opcode dari instruksi "MOV ADD A,R5". Ini adalah instruksi 1-byte. Setelah instruksi ini, PC akan menjadi 0007h
5.    Sedang lokasi 0007 adalah berisi opcode 2F, yang menjadi milik instruksi "ADD A,R7". Ini juga termasuk dalam instruksi 1-byte. Setelah CPU menjalankan instruksi tersebut maka PC akan di-inc-rement dan menjadi 0008h. Hal ini terus terjadi sampai semua isi program dilaksanakan. Hal yang sebenarnya adalah, bahwa PC adalah berisi lokasi alamat dari instruksi yang hendak dieksekusi. Prosesor kelas X86 pun memiliki serupa dengan program counter yang dinamakan Instruction Pointer.


Peta Memory ROM untuk keluarga 8051

Seperti yang kita lihat dalam bab sebelumnya, beberapa keluarga 8051 memiliki jumlah ROM program  internal sebanyak hanya 4 K Bytes, seperti 8751, AT89C51. Beberapa di antaranya bahkan punya yang lebih besar, misalnya AT89C52 yang memiliki ROM program sebanyak 8 K Bytes. Dallas Semiconductor’s DS5000-32 memiliki ROM program internal sebanyak 32 K Bytes, ada pula yang memiliki 64 K Bytes. Ingat!! karena PC dalam keluarga 8051 adalah 16-bit maka jumlah memory Program ataupun data yang bisa dialamati hanya sampai 64 KB. Alamat kode yang paling pertama dijalankan adalah alamat 0000h.
Misalnya untuk AT89C51, dia memiliki alamat ROM program mulai dari 0000h s/d 0FFFh. Lihat contoh 2-1 untuk bagaimana cara menghitungnya.

Contoh 2-1

Cari dari alamat ROM internal dari contoh chip di bawah ini.
(a) AT89C51 (87C51) dengan 4 Kbytes, (b) DS-5000-32 dengan 32 KB.

Jawaban:

(a)  4K artinya adalah 4096 bytes, atau 1000 dalam heksa desimal. Dengan memasukkan 0 sebagai alamat pertama maka , jawabanyya adalah 0000 s/d 0FFFh dalam heksa desimal.

(b)  32K artinya adalah 32.768 bytes, atau dapat kita ubah menjadi heksadesimal menjadi 8000h. Dengan memasukkan 0 sebagai alamat pertama, maka jawabanyya adalah 0000 s/d 7FFFh dalam heksa desimal.



Gambar 2-3 Jangkauan alamat ROM dalam Chip 8051





SubBAB 2.5 Type-type Data dan Directive pada 8051

Pada bagian ini kita akan melihat Type-type dan directive mana saja yang didukung oleh Assembler 8051.

Type-type Data dan Directive pada 8051

Secara prinsip 8051 hanya memiliki 1 jenis type data, yakni data 8-bit. Ukuran setiap register juga 8-bit. Nah jika ternyata data yang hendak diproses ternyata lebih besar dari 8–bit maka programer harus memecah data mencadi beberapa data 8-bit agar dapat diproses oleh PCU, lihat BAB 6. Type data ini bisa beripa bilangan positif atau negatif, yang lebih lengkap akan dibahas pada bab6.

DB (define byte)

Directive DB ini digunakan secara luas dalam proses assembly oleh assembler. Yakni digunakan untuk mendefinisikan data 8-bit pada memory program. Saat data sudah didefinisikan maka date tersebut dapat berupa desimal, biner, hex, ataupun karakter-karakter ASCII. Untuk desimal, simbol "D" atau "d" setelah bilangan angka desimal boleh ditambahkan atau tidak. Walaupun demikian data desimal tersebut akan dikonversikan menjadi bilangan hex oleh assembler. Untuk mendefinisikan karakter ASCII, maka cukup mudah, yakni dengan menempatkan symbol tanda petik satu / quotation mark, misalnya (‘seperti ini’). Kemudian assembler akan mengubah setiap karakter tersebut menjadi kode-kode hex seperti yang sudah diatur dalam format ASCII.
Beberapa contoh adalah

            ORG 500h
DATA1:      DB 28             ;desimal (atau 1C hex)
DATA2:      DB 00110101b      ;biner (atau 35 hex)
DATA3:      DB 39h            ;hex
            ORG 510h
DATA4:      DB ‘2591′   ;bilangan dlm 4-bytes karakter ASCII
            ORG 518h
DATA6:      DB ‘As”ad’ ;Karakter ASCII

Di atas kita dapat melihat adanya 2 tanda petik-satu yang behimpitan. Dalam bahasa assembly 8051, 2 tanda petik-satu tersebut akan diartikan oleh assembler sebagai sebuah karakter ASCII #44 atau data 2Ch, yakni karakter tanda petik-satu ("’"). Sehingga Label DATA6 adalah lokasi untuk 5 bytes karakter "A", "s", "’", "a", dan "d".

DW (define Word)

Define Word masih dimungkinkan oleh 8051 mengingat dia juga menggunakan ukuran data 16-bit untuk DPTR dan PC. Directive ini mendifinisakan setiap masukkan ke dalam word jadi misalnya adalah

DATA1:      DW 0

Hasilnya Label DATA1 akan dibuat kode 2 byte berisi "00" dan "00". Lainnya, perhatikan kode di bawah ini..

DATA2:      DW 0FFFFh
DATA3:      DW ‘a’
DATA4:      DW ‘ab’
DATA5:      DW ‘abc’

Hasilnya DATA3 berisi "0061", yang high bytenya dibiarkan kosong. Sedang DATA5 adalah error, karena untuk DW hanya dibolehkan string maksimum 2 karakter.

Assembler directives

Berikut ini adalah beberapa directive yang umum digunakan dalam 8051.

ORG (origin)

Directive ORG digunakan untuk mengindikasikan awal dari alamat. Artinya adalah kode berikutnya akan ditempatkan oleh assembler dimulai dari alamat seperti yang ada dibelakang simbol ORG. Bilangan dibelakang symbol ORG ini boleh berbentuk desimal maupun hex. Jika bilangan ternyata tidak diikuti oleh symbol "h", maka Assembler akan merubahnya nanti menjadi hex.

EQU (equate)

Directive ini digunakan untuk mendefinisikan (define) sebuah konstan tanpa menuntut disediakannya sebuah lokasi memory. Biasanya symbol-symbol EQU ini digunakan sebagai data-data masukan langsung (immediate) yang nanti akan dibahas pada bab Addressing. Namun dalam prakteknya EQU adalah simbol define yang paling tinggi. Karena hasilnya bisa digunakan sebagai data langsung, lokasi memory data, maupun lokasi memory program.
Dalam proses Assembly, directive EQU ini tidak akan menghasilkan kode, namun nama simbol yang di-EQU akan ditambahkan pada daftar simbol, yang dengan daftar simbol inilah assembler dapat menentukan nilai sebuah konstan. Directive yang sejenis dengan jangkauan lebih kecil adalah "DATA" dan "BIT".

      NILAI       EQU 25
                  …
            MOV  R4,#NILAI
                  …

END directive

Directive penting lainnya adalah END. Dimana directive ini akan memberitahukan kepada assembler bahwa disitu adalah akhir dari program. Maka Assembler berhenti untuk membuat kode baru dan segera menyelesaikan tugasnya, tanpa lagi menghiraukan text dibelakang simbol END.
Dalam program Assembler, directive ini harus ada.

Aturan untuk Label dalam bahasa Assembly

Dalam memilih sebuah label idealnya adalah nama yang sangat singkat namun penuh arti. Sehingga programmer dapat membuat program menjadi sangat mudah dan cepat. Ada beberapa aturan yang harus kita ikuti. Pertama adalah Setiap Label (atau simbol) haruslah unik (tidak sama). Karakter yang boleh digunakan untuk Label bisa terdiri dari semua alphabeth, digit 0 s/d 9, tanda tanya (?), at (@), dan tanda dollar ($). Namun karakter pertama dari nama Label haruslah Alphabeth. Hal ini berbeda untuk angka yang karakter pertamanya haruslah angka, baik itu desimal, heksa, ataupun biner.
Dalam penamaan label tidak boleh menggunakan reserved word, misalnya MOV, ADD, ACC, SBUF, CY, RESET, dll yang sudah didefinisikan sendiri oleh assembler. Untuk lebih mengetahui reserved word apa saja yang ada dalam assembler, kita dapat kembali membaca manual dari assembler yang kita gunakan.






SubBAB 2.6 Bit-bit bendera dan register PSW pada 8051

Seperti kebanyakna prosesor, 8051 meiliki register bendera yang diguakan untuk mengindikasikan kondisi aritmatika seperti misalnya Sisa, atau Carry. Register bendera dalam 8051 disebut sebagai register Program Status Word (PSW). Pada subBAB ini kita akan membahas yang satu itu.

Register PSW (program status word)

Register Program Status Word (PSW) adalah register 8-bit. Dia juga disebut sebagai register bendera (sunda = flag register). Walaupun PSW adalah register 8-bit, namun hanya 6-bit diantaranya yang digunakan oleh 8051. 2 diantaranya adalah tidak digunakan itu dapat kita gunakan oleh user untuk mendukung program. 4 bit dari 6 yang digunakan disebut sebagi bendera kondisi, yang berarti bahwa mereka mengindikasikan sebuah kondisi yang dihasilkan dari sebuah proses matematika. Masing-masing adalah CY (C / Carry / Sisa), AC (Auxiliary Carry / Sisa tambahan / Sisa desimal), P (Parity / paritas / kegenapan), OV (Over Flow / kelebihan ).

Dari gambar 2-4 kita dapat melihat PSW4 dan PSW3 yang ditandakan sebagai RS1 dan RS0, dan digunakan untuk mengubah bank registers. Hal itu akan kita jelaskan pada bab yang lain. Sedang PSW1 dan PSW5 adalah bit bendera bebas yang dapat kita gunakan untuk berbagai hal.



CY  PSW.7  Bendera Carry
AC  PSW.6  Bendera Carry Tambahan
F0  PSW.5  Boleh digunakan secara bebas
RS1 PSW.4  Bit pemilih bank register
RS0 PSW.3  Bit pemilih bank register
OV  PSW.2  Bendera Overflow
— PSW.1  Boleh digunakan secara bebas
P   PSW.0  Bendera Paritas

RS1    RS0     Register Bank             Alamat
0      0          0                   00h – 07h
0      1          1                   08h – 0Fh
1      0          2                   10h – 17h
1      1          3                   18h – 1Fh


Gambar 2-4 Bit-bit dala register PSW

Berikut ini akan dibahas dengan lebih teliti penerapan dari ke 4 bendera  dari register PSW ini. Termasuk akibat dari sebuah instruksi terhadap register ini akan dibahas kemudian.

CY, bendera Carry

Bendera ini akan di-set saat adanya sisa / kelebihan dari D7. Bendera ini digunakan oleh instruksi penambahan (ADD) dan pengurangan (SUB), dan termasuk oleh perkalian (MUL) dan Pembagian (DIV). Namun secara manual kita dapat mengubah bit ini dengan instruksi "SetB C" atau "Clr C". Pelajari nanti juga ada bab 8.

AC, bendera Auxiliary Carry

AC prinsipnya mirip dengan Carry biasa, namun berbeda dengan sisa. Bendera ini akan di-set hanya saat adanya sisa / kelebihan dari D3 ke D4. Instruksi yang mempengaruhi bit adalah sama dengan Carry. Bit ini khusus dirancang untuk memudahkan programer dalam membuat program yang menggunakan BCD (Binary Coded Decimals). Lihat nanti bab 6.

P, bendera Parity

Bendera paritas adalah merefleksikan jumlah bit "1" dalam akumulator. Jika jumlahnya adalah genap, maka P = 1, namun jika jumlahnya ganjil maka P = 0.

OV, bendera Overflow

Bendera kelebihan ini dirancang untuk keperluan program yang menggunakan bilangan bertanda ( plus atau minus ). Bendera ini di-set saat mengindikasikan bahwa instruksi yang dijalankan menghasilkan bilangan yang diluar jangkauan yakni -128 s/d +127. Lebih lengkap akan dibahas pada bab 6.

Instruksi ADD dan PSW

Selanjutnya kita melihat dampak yang dihasilkan oleh instruksi ADD, pada bendera CY, AC dan P milik register PSW tersebut. Sedang dampaknya pada bit OV akan dibahas kemudian pada bab 6). Beberapa contoh akan diberikan utnuk memperjelas pembahasan.

Tabel 2-1 Instruksi-instruksi yang mempengaruhi Bit bendera
 Instruksi    CY   OV   AC
 ADD          x    x    x
 ADDC         x    x    x
 SUBB         x    x    x
 MUL          0    x    
 DIV          0    x    
 DA           x         
 RRC          x         
 RLC          x         
 SetB C       1         
 Clr C        0         
 CPL C        x         
 ANL C,bit    x         
 ANL C,/bit   x         
 ORL C,bit    x         
 ORL C,/bit   x         
 MOV C,bit    x         
 CJNE         x         
 Catatan : x dapat berarti 0 ataupun 1.


Contoh 2-2

Tunjukkan status dari CY, AC dan P setelah terjadi penambahan 38h dan 2Fh seperti instruksi-instruksi berikut ini
   MOV  A,#38h
   ADD  A,#2Fh  ; setelah penambahan A=67h, CY=0.

Jawaban:

        38  00111000
      + 2F  00101111
        67  01100111
CY = 0 karena memang tidak ada carry dari bit D7.
AC = 1 karena ternyata ada carry dari bit D3 ke D4.
P = 1 hasilnya A memiliki 1s yang ganjil.



Contoh 2-3

Tunjukkan status dari CY, AC dan P setelah terjadi penambahan 9Ch dan 64h seperti instruksi-instruksi berikut ini
   MOV  A,#9Ch
   ADD  A,#64h  ; setelah penambahan A=00 , CY=1.

Jawaban:

        9C  10011100
      + 64  01100100
       100  00000000
CY = 1 karena ada carry dari bit D7 keluar.
AC = 1 karena ternyata ada carry dari bit D3 ke D4.
P = 0 karena tidak ada bilangan 1s pada ACC.



Contoh 2-4

Tunjukkan status dari CY, AC dan P setelah terjadi penambahan 88h dan 93h seperti instruksi-instruksi berikut ini
   MOV  A,#88h
   ADD  A,#93h  ; setelah penambahan A=1Bh, CY=1.

Jawaban:

        88  10001000
      + 93  10010011
       11B  00011011
CY = 0 karena ada carry dari bit D7 keluar.
AC = 0 karena tidak ada carry dari bit D3 ke D4.
P = 0 hasilnya A memiliki 1s sebanyak 4 buah.







SubBAB 2.7 Bank-bank register dan Stack 8051

Kita tahu bahwa 8051 memiliki RAM internal sebanyak 128 bytes. Pada subBAB ini kita akan membahas alokasi RAM ini untuk register-register dan untuk Stack.

Ruang Alokasi memory RAM dalam 8051

Ada 128 bytes memory dalam 8051 ( 256 bytes untuk 8052). Memory ini dialamatkan pada 00h s/d 7Fh. Pada bab 5 nanti kita akan melihat memory ini dapat diakses secara langsung dengan hanya menyebutkan lokasinya. Ke 128 bytes memory ini dibagi menjadi beberapa bagian sebagai berikut ini :
1.    Total 32 bytes pertama 00h s/d 1Fh digunakan sebagai bank-bank register dan Stack.
2.    Total 16 bytes berikutnya 20h s/d 2Fh digunakan sebagai memory yang bisa dialamati setiap bit-bit-nya secara langsung. Yang lebih lengkap akan dibahas pada bab 8.
3.    Sedang total 80 bytes sisanya 30h s/d 7Fh dapat digunakan sebagai berbagai macam hal oleh kita, misalnya untuk menyimpan data, buffer, counter dll. Ini adalah memory bebas, dan penggunaannya diserahkan pada programmer.

Gambar 2-5 Alokasi RAM pada 8051

Bank-bank register dalam 8051

Seperti yang sudah disebut sebelumnya, totdal ada 32 bytes memory yang digunakan untuk regfister dan bank. Ke 32 bytes ii dibagi menjadi 4 bagian / bank, sehingga setiap bagian / bank memiliki jumlah 8 bytes. Setiap bank secara berurutan adalah milik regsiter R0 s/d R7. Dimana pada bank-0 (00h-07h) kita dapat mengetahu R0 akan menunjuk alamat 00h, dan R7 akan menunjuk 07h. Sedang jika pada bank-1 (08h-0Fh), R0 akan menunjuk 08h dan R7 akan menunjuk 0Fh. Demikian seterusnya.
Hanya ada 1 bank yang bisa digunakan. Lalu Bank mana yang sedang digunakan ? Itu tergantung dari RS1 dan RS0 atau PSW.4 dan PSW.3 pada register PSW. Seperti yang sudah sedikit dijelaskan diatas. Berikut ini adalah alokasi dari setiap bank untuk masing-masing register.


Gambar 2-6. Bank-bank register dan alamat RAM mereka dalam 8051

Seperti yang dapat kita lihat pada gambar 2-5, Saat pertama reset, Bank-0 adalah bank yang pertama dipilih, sedang Bank-1 ternyata untuk sementara digunakan untuk Stack. Inilah yang menjadi persoalan kebanyakan dalam pengorganisasian bank, terutama bagi pemula. Saat kita menggunakan Bank 1,2, atau 3 sebagai bagian dalam program, maka hal pertama yang harus dilakukan adalah memastikan bahwa bank-bank tersebut tidak sedang digunakan oleh Stack. Bagaimana caranya? tentu saja Stack harus dipindah untuk menduduki memory yang kosong.

Contoh 2-5

Tunjukkan status dari lokasi RAM setelah program berikut ini.
       MOV  R0,#99h  ; Isikan nilai 99h pada R0
       MOV  R1,#85h  ; Isikan nilai 85h pada R1
       MOV  R2,#3Fh  ; Isikan nilai 3Fh pada R2
       MOV  R7,#63h  ; Isikan nilai 3Fh pada R7
       MOV  R5,#12h  ; Isikan nilai 12h pada R5

Jawaban:

Setelah melaksanakan instruksi di atas maka..
RAM lokasi 0 memiliki nilai 99h
RAM lokasi 1 memiliki nilai 85h
RAM lokasi 2 memiliki nilai 3Fh
RAM lokasi 7 memiliki nilai 63h
RAM lokasi 4 memiliki nilai 12h


Bank register Default

Seperti yang kita tahu bahwa ada 4 bank register. Lokasi mana yan diakses R0 s/d R7 setelah CPU dihidupkan. Seperti yang sudah sedikit dijelaskan diatas, kita mendapati bahwa PSW adalah bernilai 00. Yang dalam arti RS1 = 0 dan RS0 = 0 yang berarti bank yang saat reset itu dipilih adalah bank-0. Sehingga lokasi 00 s/d 07h masing-masing untuk R0 s/d R7.
Begitulah kondisi setelah reset atau pertama dihidupkan, yakni bank yang dipilih adalah Bank-0 dan register seperti R0 mennujuk lokasi 00h sampai pada R7 yang berlokasi pada 07h.
Begitu saat bank dipindah, maka lokasi-loaski register tersebut akan ditinggalkan begitu saja, dan R0 s/d R7 akan berlokasi di tempat yang baru pada bank yang sedang dipilih.

Contoh 2-6

Ulangi contoh 2-5 namun dengan menyebutkan nama lokasi dari register-register tersebut.

Jawaban :

       MOV  00,#99h  ; Isikan nilai 99h pada lokasi 00
       MOV  01,#85h  ; Isikan nilai 85h pada lokasi 01
       MOV  02,#3Fh  ; Isikan nilai 3Fh pada lokasi 02
       MOV  07,#63h  ; Isikan nilai 3Fh pada lokasi 07
       MOV  05,#12h  ; Isikan nilai 12h pada lokasi 05




Bagaimana cara untuk mengubah bank register

Seperti diterangkan di atas bahwa Bank 0 adalah default, yakni saat 8051 baru dinyalakan. Kita dapat mengubah pemilihan bank tersebut dengan menggunakan register PSW (program status word). Bit D4 dan D3 dari PSW digunakan untuk melakukannya seperti yang ditampilkan pada
tabel 2-2.
Bit D4 dan D3 dari PSW juga dikenal dengan sebutan PSW.4 dan PSW.3 karena memang sebenarnya register PSW dapat dialamati secara bit. Sehingga masing-masing bit dalam register tersebut dapat dimanipulasi dengan instruksi CLR dan SETB. Misalnya "SETB PSW.3" akan membuat PSW.3 = 1, dan bank akan dipilih menjadi bank 1. Seperti yang dicontohkan dalam Contoh 2-7.

Tabel 2.2 Bit Pemilih Bank pada PSW        .
           RS1(PSW.4)  RS0(PSW.3)  .
Bank 0        0        0           .
Bank 1        0        1           .
Bank 2        1        0           .
Bank 3        1        1           .


Contoh 2-7

Jelaskan isi RAM setelah instruksi-instruksi berikut ini.

       MOV  00,#99h  ; Isikan nilai 99h pada lokasi 00
       MOV  01,#85h  ; Isikan nilai 85h pada lokasi 01
       MOV  02,#3Fh  ; Isikan nilai 3Fh pada lokasi 02
       MOV  07,#63h  ; Isikan nilai 3Fh pada lokasi 07
       MOV  05,#12h  ; Isikan nilai 12h pada lokasi 05

Jawaban :
Secara default PSW.3 = 0 dan PSW.4 juga 0. Atau dengan kata lain secara default bank yang dipilih adalah bank register 0. Sehingga dalam instruksi "SetB PSW.4", CPU kemudian menggunakan bank register 2. bank register 2 mengunakan RAM lokasi 10h – 17h. Sehingga setelah isntruksi-instruksi di atas RAM tersebut akan berisi sbb.

RAM lokasi 10h berisi 99h
RAM lokasi 11h berisi 85h
RAM lokasi 12h berisi 3Fh
RAM lokasi 17h berisi 63h
RAM lokasi 15h berisi 12h




Stack dalam 8051

Stack (dalam bahasa kita adalah "tumpukan") adalah bagian dari RAM, dan dugunakan bagi CPU untuk menyimpan informasi secara sementara. Informasi tersebut dapat berupa data maupun alamat. CPU sangat memerlukan mengaksesan memory RAM sebagai Stack karena memang Stack harus menempati memory yang berurutan.

Bagaimana caranya stack diakses dalam 8051

Jika Stack mengambil bagian dari RAM, maka tentu saja harus ada sebuah register dalam CPU yang dapat menunjuk Stack tersebut. Register tersebut digunakan untuk mengakses stack ini diberi nama register SP (Stack Pointer). Stack dalam 8051 adalah termasuk register 8-bit, yang mana hanya menunjuk alamat dari 00 s/d FFh. Saat CPU pertama dinyalakan register SP ini selalu bernilai 07h. Hal ini berarti lokasi RAM 08h adalah lokasi pertama stack dalam 8051. Saat CPU menyimpan nilai dari sebuah register ke dalam stack, itu disebut dengan PUSH (yakni mendorong data ke dalam stack). Sedang data yang di diambil dai tumpukan stack dikirim ke regsiter disebut dengan POP. Singkatnya adalah data didorong ke stack untuk menyimpannya, sedang data diambil dari stack untuk menggunakannya. Modifikasi stack sungguh menarik, namun Jika tidak hati-hati CPU akan menganggap salah satu bagian stack yang kita isi dengan data, justru dianggap sebagai sebuah alamat. Jika itu terjadi maka komputer akan bekerja tidak beraturan, dan tidak bisa mengerti lagi yang mana opcode dan yang mana operan. Untuk lebihmengerti dengan modifikasi Stack maka lihat kembali penjelsan tentang instruksai PUSH dan POP.

Mem-Push data ke dalam Stack

Dalam 8051 SP (Stack Pointer) adalah menunjuk pada alamat ujung dari stack tersebut. Data baru untuk stack akan ditempatkan pada lokasi sesudah. Dengan kata lain, saat mem-push stack, SP akan oromatis di-INCrement dan menuliskan data pada lokasi yang baru itu. Push = Increment lalu Save. Sekali lagi ingat bahwa setiap byte data yang disimpan dalam Stack, SP di-INC sekali saja, begitu pula dengan POP, setiap byte yang diambil dari Stack, SP akan didecrement 1 kali.

Metode transfer dalam Stack adalah seperti pengalamatan regsiter tidak langsung. Hanya saja register yang digunakan bukan Register serba guna, namun adalah register khusus, seperti yang sudah dibahas. Mekanisme mesin yang sama dalam proses Push dapat dimisalkan seperti ini.

      INC R0
      MOV @R0,Direct

Ilustrasi di atas hanya menunjukan mekanisme teknis dari PUSH. Selain berbeda Registernya, syntax yang digunakan adalah jauh lebih sederhana

      PUSH Direct


Contoh 2-8

Tunjukkan Stack dan Pointer-nya dari instruksi dobawah ini. Anggaplah bahwa stack pada area aslinya.

       MOV   R6,#25h
       MOV   R1,#12h
       MOV   R4,#0F3h
       PUSH  6
       PUSH  1
       PUSH  4

Jawaban :




Mem-Pop data dari Stack

Sedang POP = Load lalu Decrement. Jadi saat mem-POP stack data lokasi terakhir dari stack akan di load pada register yang bersangkutan. Selanjutnya SP akan di-Decrement dan 1 alamat sebelm alamat yang tadi diload, sekarang dianggap sebagai ujung dari stack. Proses Push dan POP pada 8051 berbeda dengan microprocessor seperti X86. Proesor ini akan men-DEC SP saat instruksi PUSH, dan akan men-INC SP setelah instruksi POP.
Proses dalam POP, juga memiliki mekanisme mesin yang sama dengan rangkaian instruksi dibawah ini

      MOV Direct,@R0
      DEC R0

Ilustrasi di atas hanya menunjukan mekanisme teknis dari POP. Selain berbeda Registernya, syntax yang digunakan adalah jauh lebih sederhana

      POP Direct

Sekali lagi mode pengalamatan stcak adalah mode pengalamatan tidak langusng untuk stacknya, sehingga range data 0 s/d 7Fh dapat digunakan sebagai stack. Bahkan untuk keluarga 8052 yang memiliki blok memory khusus pengalamat tidak langsung, memungkinkan stack memiliki jangkauan 0 s/d FFh. Sementara operand untuk PUSH dan POP harus mode pengalamatn Direct.

Batas atas dalam Stack

Sekali lagi Stack ada batasan. Secara teori Stack dapat menjangkau seluruh lokasi RAM yang berada dalam CPU. 00 s/d 7F untuk keluarga 8051, dan 00 s/d FF untuk keluarga 8052. Namun Intel sudah merancang dengan setelah awal(walaupun dapat kita ubah), Stack dimulai dari lokasi RAM 07h. Hal ini agar lokasi RAM 00 s/d 07h milik register serba guna Bank 0 aman dari gangguan Stack. Walau dalam beberapa aplikasi ukuran stack tidak terlalu besar memakan memory, namun tetap harus dipertimbangkan hal-hal semacam ini. Sedapat mungkin stack tidak menggangu daerah RAM yang kita gunakan. Misalnya kita menggunakan memory 25h sebagai memory sebuah data. Sedapat mungkin Stack tidak menggangu lokasi 25h ini. Jika Stack diperkirakan akan melewati lokasi 25h ini, maka ada 2 solusi untuk itu. Yakni memindahkan lokasi RAM 25h tadi ke alamat yang lebih tinggi, atau memindahkan lokasi Stacknya.

Contoh 2-9

Periksa stack. Dan tunjukkan Stack dan Pointer-nya setelah instruksi dibawah ini. Semua dalam bilangan hex. SP dimulai dari lokasi 0Bh.

       POP  3
       POP  5
       POP  2

Jawaban :




Hubungan instruksi CALL dengan Stack

Selain Stack ini digunakan untuk menyimpan register, maka kegunaan lain dari stack adalah untuk alamat saat dijalankannya instruksi CALL dan ACALL. Sebagaimana yang kita tahu bahwa instruksi tersebut adalah memanggil sebuah rutin lain yang lokasinya jauh. Namun sebelum melakukan lompatan CPU akan menyimpan lokasi alamat kode dari instruksi persis dibawah CALL. Agar saat CPU telah selesai menjalankan rutin yang dipanggil tadi, CPU akan kembali mengeksekusi yang urung dikerjakan karena adanya Instruksi Call sebelumnya. Pada Bab 3 akan dibahas mengenai hal ini secara lebih lengkap.

Contoh 2-10
Contoh 2-8

Tunjukkan Stack dan Pointer-nya dari instruksi dibawah ini.

       MOV   SP,#5Fh     ;Buat lokasi baru untuk Stack
       MOV   R2,#25h
       MOV   R1,#12h
       MOV   R4,#0F3h
       PUSH  2
       PUSH  1
       PUSH  4

Jawaban :




Konflik antara Stack dan Bank 1

Mengulang dari bahasan kita sebelumnya bahwa Stack Pointer pada llokasi yang tersedia dalam RAM untuk kegunaan Stack. Data di-PUSH ke dalam stack setelah SP di-increment terlebih dahulu. Sebaliknya SP akan di-decrement setelah di-POP. Kita juga mengingat bahwa Stack Default adalah berlokasi pada alamat 07h, yang berarti data pertama yang di-PUSH akan ditempatkan pada alamat 08h, dan seterusnya. Kita juga tahu bahwa blok alamat 00h s/d 1Fh adalah dimiliki oleh register yang dibagi menjadi 4 bank. Dan Bank 1 menduduki alamat 08 s/d 0Fh. Bank 2 mendudukui alamat sesudahnya. Dan lokasi 18h s/d 1Fh dimiliki oleh Bank 3.
Ada kesamaan lokasi memory antara Bank 1 dengan awal stack. Tentu saja hal ini membingungkan kita bukan ? Jangan bingung. Secara defaultnya juga bank yang digunakan adalah bank 0, sengan lokasi 00h s/d 07h. Dimana itu diluar jangkauan Stack.
Namun bagaimana saat kita menginginkan untuk menggunakan Bank 1 ,2 atau 3 tanpa terjadi masalah dengan Stack. Solusinya adalah memindah lokasi awal dari Stack. Misalnay memidah kan ke alamat 50h ke atas. Itu dapat dilakukan dengan mudah menggunakan instruksi "MOV SP,#4Fh". Hasilnya stack akan mengambil lokasi mulai dari 50h s/d 7Fh. Dan Bank 1, 2, dan 3 dapat segera kita gunakan. Hal tersebutdiconto dalam Contoh 2-10.







RINGKASAN

Pada Bab ini dimulai dari penjelasan tentang register utama dari 8051 termasuk A, B, R0, R1, R2, R3, R4, R5, R6, R7, DPTR, dan PC. Dalam penggunaan register-register tersebut, didemonstrasikan dengan contoh pemrograman. Proses dalam membuat aplikasi dengan bahasa Asembly telah diterangkan, yakni dengan menulis file sumber, kemudian meng-kompilasinya, link-ing, dan kemudian menjalankannya. Register PC (Program Counter) adalah selalu menunjuk pada lokasi kode yang hendak dikerjakan CPU. Bagaimana cara 8051 pengunakan ruang ROM program telah dijelaskan, namun nampaknya kita harus sedikit mengerti, dimana program kode akan ditempatkan dalam ROM, dan berapa daya tampung Chip.

Bahasa Assembly adalah sekumpulan directive yang terdiri dari instruksi, maupun psuedo-instruction yang juga disebut directive. Instruksi kemudian di terjemahkan ke dalam bahasa mesin. Sedang directive adalah petunjuk bagaimana cara men-terjemahkannya. Beberapa psuedo-instrucition tersebut digunakan hanya untuk mendefinisikan sebuah simbol data. Data dalam hal ini dapat berupa biner, hex, maupun desimal, bahkan string sekalipun, semuanya terorganisasi beberapa bagian memory 8-bit.

Bendera-bendera sangat berguna bagi paraprogrammer untuk dapat menilai kondisi dari sebuah operasi matematika misalnya apakah ada sisa atau kelebihan. Stack digunakan untuk menyimpan alamat yang ditinggalkan saat terjadinya Call. Namun stack juga dapat digunakan untuk menyimpan sebuah data. Stack menghuni di dalam RAM, di mana sudah digambarkan dan diterangkan. Termasuk juga manipulasi stack lewat PUSH dan POP juga sudah digali.





0 komentar:

Poskan Komentar