EET 2261 Unit 5 Tables Decision Trees Logic
EET 2261 Unit 5 Tables; Decision Trees & Logic Instructions ¡ ¡ ¡ Read Almy, Chapters 9 and 10. Homework #5 and Lab #5 due in two weeks. Exam #1 next week.
Review: Addressing Modes • The HCS 12’s six addressing modes are: • Inherent • Immediate • Direct • Extended • Indexed (which has several variations) • Relative • We briefly looked at indexed addressing mode two weeks ago. Let’s return to it now.
Review: Indexed Addressing Mode • Indexed addressing mode comes in at least five variations: • Constant offset indexed addressing • Auto pre/post decrement/increment indexed addressing • Accumulator offset indexed addressing • Constant indirect indexed addressing • Accumulator D indirect indexed addressing • Of these five variations, we’ll use only the three in bold above. For the others, see pages 5054 in the textbook or the section starting on p. 34 of the HCS 12 CPU Reference Manual.
Review: Variation #1: Constant Offset Indexed Addressing Mode • In constant offset indexed addressing mode, the operand’s address is found by adding a constant offset to the contents of an index register (usually IX or IY, but possibly also SP or PC). • Example: The instruction LDAA 3, X uses Index Register X, with 3 as the constant offset. • If Index Register X contains $1500, then this instruction loads Accumulator A with the contents of memory location $1503.
Review: Simple Example of Indexed Addressing LDX #$1500 LDY #$1600 LDAA 2, X INCA STAA 7, Y • In which memory location does the final instruction store a value?
An Application of Indexed Addressing: Copying a Block of Data • A typical use of indexed addressing mode is to copy a block of data (many bytes) from one place in memory to another. • Example: Suppose we have some data in memory locations $1200 through $128 F, and we want to copy it to memory locations $1300 through $138 F.
Copying a Block of Data: The Brute-Force Way • Without indexed addressing mode, we’d have to do something like the following: LDAA STAA $1200 $1300 $1201 $1301 $1202 $1302 ; copy first byte ; copy second byte ; copy third byte . . . LDAA $128 F STAA $138 F ; copy last byte
Copying a Block of Data: The Smart Way • With indexed addressing (and a loop!), the code is much shorter: LDX #$1200 LDY #$1300 LDAB #$90 L 1: LDAA 0, X INX STAA 0, Y INY DECB BNE L 1 ; pointer to source bytes ; pointer to destination bytes ; number of bytes
Variation #2: Auto Pre/post Decrement/ increment Indexed Addressing Mode • In the previous program, we incremented IX and IY each time through the loop. Since this is such a common thing to do, the HCS 12 gives us a quicker way to do it. • In place of these two instructions: LDAA 0, X INX We can use this one instruction: LDAA 1, X+
Copying a Block of Data With Auto Post -Increment Indexed Addressing • Once more, our earlier program made shorter: LDX #$1200 LDY #$1300 LDAB #$90 L 1: LDAA 1, X+ STAA 1, Y+ DECB BNE L 1 ; pointer to source bytes ; pointer to destination bytes ; number of bytes • As in this example, indexed addressing mode is often used in loops. You’ll write three similar programs in Lab #5.
Variation #3: Accumulator Offset Indexed Addressing Mode • In accumulator offset indexed addressing, the operand’s address is found by adding the contents of Accumulator A or B or D to the contents of an index register. • Example: The instruction LDAA B, X uses Index Register X, with the contents of Accumulator B as the offset. • If Index Register X holds $1500 and Accumulator B holds $07, then this instruction loads Accumulator A with the contents of memory location $1507.
An Application: Look-Up Tables • Accumulator offset indexed addressing mode is useful for implementing look-up tables. • Look-up tables can save us time in a program by storing the results of frequently used computations in memory so that we can look up the results when we need them instead of having to perform the calculation.
Look-Up Tables: Example • Example: Suppose your program frequently needs to raise numbers to the 2 nd power. Instead of including instructions in your program to do the math, you can store a table of squares in memory, and then look up the values when you need them. x x 2 0 0 1 1 2 4 3 9 4 16 5 25
Implementing Our Look-Up Table Example: Part 1 • First, we need to store the square values in consecutive bytes of memory. Typically you’ll store them in EEPROM so that the values are retained when power is lost. • Let’s say we want our look-up table to start at address $0500. Then here’s what we need to store in memory: Address Value $0500 0 $0501 1 $0502 4 $0503 9 $0504 16 $0505 25 … …
The DC Assembler Directive • The DC (Define Constant) directive lets us set up constant values in memory bytes. • To define our look-up table, we’d do the following: ORG $0500 DC 0, 1, 4, 9, 16, 25, 36
Three Ways to Load Values into Memory: First Way • You now know at least three ways to place a specific value into a memory location. • Example: Suppose we want to place the value $A 1 into memory location $0600. • The first way is to do it manually, using Code. Warrior’s Memory window.
Three Ways to Load Values into Memory: Second Way • The second way is to use HCS 12 instructions in your program, which will execute when the program runs. LDAA #$A 1 STAA $0600
Three Ways to Load Values into Memory: Third Way • The third way is to use the DC assembler directive, which places the value into memory when the program is downloaded to the chip, before the program runs. ORG $0600 DC $A 1
Implementing Our Look-Up Table Example: Part 2 • Now that we’ve defined our look-up table in memory starting at address $0500, how do we use the table? Here’s where accumulator offset indexed addressing is handy. • Suppose we have a number in Accumulator B and we want to load that number’s square into Accumulator A. Here’s how to do it: This will “reach” the correct distance into our look-up table to get the square of whatever value is in B. LDX #$0500 ; point to the table LDAA B, X ; load table’s Bth value
Putting It All Together • Combining the two pieces, we have: ABSENTRY Entry ; Define the look-up table. ORG $0500 DC 0, 1, 4, 9, 16, 25, 36 ; Use the look-up table. ORG $2000 Entry: LDX #$0500 ; point to the table LDAA B, X ; load table’s Bth value
Using a Label for the Table • Instead of using the table’s address, we’d do better to use a label: ABSENTRY Entry ; Define the look-up table. ORG $0500 Table: DC 0, 1, 4, 9, 16, 25, 36 ; Use the look-up table. ORG $2000 Entry: LDX #Table ; Point to the table. LDAA B, X ; Load table’s Bth value.
Review: Variations of Indexed Addressing Mode • Variation #1: Constant offset indexed addressing • • Variation #2: Auto post-increment indexed addressing • • Example: LDAA 3, X Example: LDAA 1, X+ Variation #3: Accumulator offset indexed addressing • Example: LDAA B, X
Review: Using Branch Instructions for Iteration (Loops) • • In Unit 4 we saw two uses for branch instructions: • We used BRA instruction to create “forever” loops. • We used BNE instruction to create counted loops. (See next two slides for review. ) After reviewing those two uses, we’ll move on to other uses of branch instructions.
Review: A “Forever” Loop Example Flowchart Program Start ABSENTRY Entry ORG $2000 Load A from $1000 Entry: Increment A LDAA $1000 Go. Here: INCA BRA Go. Here END
Review: A Counted Loop Example Start Load A from $1000 Counter=5 ABSENTRY Entry ORG $2000 Entry: LDAA $1000 LDAB #5 ; Init. Counter Increment A Decrement Counter No Counter = 0? Yes Store A to $1001 End Again: INCA ; Do action DECB ; Dec. Counter BNE Again ; Counter=0? STAA $1001 END
Conditional Structure • Often we want to check some condition and then either perform an action or skip the action, depending on whether the condition is true or false. . Yes Condition? No Action . . .
Conditional Structure: Example Flowchart Program Start ABSENTRY Entry Load A from $1000 A = 0? No Increment A ORG $2000 Yes Entry: LDAA $1000 BEQ Go. Here INCA Go. Here: STAA $1001 Store A in $1001 End END
A Second Conditional Structure • This is similar to the previous one, but this time there are several actions that we we’ll either do or skip, depending on whether the condition is true or false. . Yes Condition? No Action 1. . . Action n . . .
A Second Conditional Structure: Example Flowchart Program Start ABSENTRY Entry ORG $2000 Load A from $1000 Yes A = 0? No Load B from $1001 Increment B Add B to A Entry: LDAA $1000 BEQ Go. Here LDAB $1001 INCB ABA Go. Here: STAA $1001 Store A in $1001 End END
A Third Conditional Structure • This time, instead of either doing an action or skipping it, we’re doing one of two different actions depending on whether the condition is true or false. . Yes No Condition ? Action a Action b . . .
A Third Conditional Structure: Example Flowchart Program Start ABSENTRY Entry ORG $2000 Load A from $1000 Yes A = 0? Increment A No Entry: LDAA $1000 BEQ Go. Here Decrement A DECA BRA Go. There Store A in $1001 End Go. Here: INCA Go. There: STAA $1001 END
Comparing Numbers • Most of the previous branch examples checked to see whether a number was equal to 0. They did this by using BEQ or BNE. • Often, we want to compare two numbers to see whether one is greater than or less than the other. To do this we need other branch instructions. Read Temperature Temp > 70? No Turn on LED 1 Yes Turn on LED 0
How to Compare Numbers • The general procedure for comparing two numbers is to execute a subtract instruction (such as SUBA or SUBB) or a compare instruction (such as CMPA or CMPB), followed by one of the branch instructions shown on the next slide. • So it’s a two-step process: 1. Subtract or Compare 2. Branch
Branches for Comparing Numbers • Note 1: Most of these branches check more than one bit in the CCR. • Note 2: We have two sets of branches: one for comparing unsigned numbers and one for comparing signed (two’s-complement) numbers. • Remember: These branches are meant to be used immediately after a subtract or compare instruction.
Comparing Numbers : Example • Let’s assume we’re dealing with unsigned numbers. Flowchart Program Start ABSENTRY Entry Load A from $1000 A > 70? No Increment A ORG $2000 Yes Entry: LDAA $1000 CMPA #70 BHI Go. Here INCA Store A in $1001 End Go. Here: STAA $1001 END
Why Do We Need Unsigned Branches and Signed Branches? • Consider this question: Is %1111 greater than %0000 0001? • Answer: It depends! • If these are unsigned numbers, then %1111 = 255 and %0000 0001 = 1. So the answer is YES. • But if these are signed numbers, then %1111 = -1 and %0000 0001 = 1. So the answer is NO.
Lots of Branches • At this point you should be able to use any of the short branch instructions. (Table from p. 74 of the HCS 12 CPU Reference Manual. )
Boolean Logic Instructions (Table from p. 63 of the HCS 12 CPU Reference Manual. )
Examples of Boolean Operations • Suppose x and y are byte variables, with x = 6 and y = 12. • Then x AND y = 4, because 0000 0110 AND 0000 1100 0000 0100 • Also, x OR y = 14, because 0000 0110 OR 0000 1100 0000 1110 • Also, x EOR y = 10, because 0000 0110 EOR 0000 1100 0000 1010
Bitwise AND as a Masking Operation • Of these logical operations, bitwise AND is the most widely used. It’s often used to “mask” some of the bits in a number. • Example: suppose the user enters a value, but we only want to use the four lowest-order bits of that value, ignoring the four higher-order bits. We do this by applying a “mask” of 0000 1111. u 7 u 6 u 5 u 4 u 3 u 2 u 1 u 0 AND 0 0 1 1 0 0 u 3 u 2 u 1 u 0 Bits entered by the user. Our mask. Result of masking operation.
Complement Instructions (Table from p. 63 of the HCS 12 CPU Reference Manual. )
Boolean Operations in the Windows Calculator The Windows calculator can perform Boolean NOT, OR, XOR, and AND. • To complement a value, enter the value and then press the NOT button. • To OR, XOR, or AND two values, enter the first value, then press the appropriate Boolean button, then enter the second value, and then press the = button.
Review: STAA Stores an Entire Byte • Using instructions that we’ve studied, you can change the value of an entire byte in memory. • Example: If you want memory location $2500 to hold the value %0011 0100, here’s one way to do it: LDAA #$34 STAA $2500 • What if you want to change a single bit of the byte held in a memory location? Can you do that? Yes, by using two new instructions.
Bit Manipulation Instructions • Two instructions, BCLR and BSET, let us clear or set single bits in memory. (Table from p. 65 of the HCS 12 CPU Reference Manual. ) We’ll discuss BITA and BITB in future weeks. • BCLR and BSET operate on individual bits, in contrast to STAA, which operates on an entire byte.
“Set” and “Clear” • • As we’re using the words here: • “Set” means “force to 1. ” • “Clear” means “force to 0. ” So you’ll use BSET when you want to force a bit to be 1, and you’ll use BCLR when you want to force a bit to be 0.
Byte Masks • BCLR and BSET, as well as some other instructions we’ll study, use a byte mask. This is a byte that identifies which bit(s) in a byte we want to work with. • Example: Suppose we want to use BCLR or BSET to change the values of bits 2, 3, and 5 of a byte in memory. • Then the byte mask we would use is %00101100 (or, equivalently, $2 C).
BCLR: Example • Example: Suppose we want to clear bit 2 of the byte stored at memory location $1500. • Here’s how to do it: BCLR $1500, %00000100 (or you could do BCLR $1500, $04) • This instruction will clear bit 2 of the byte stored at memory location $1500, and will leave the other bits in that byte unchanged. • Note the comma between the address and the byte mask. • Note: the bit we call bit 2 is actually the 3 rd bit from the right, because the rightmost bit is bit 0.
BSET: Example • Example: Suppose we want to set bits 2, 3, and 5 of the byte stored at memory location $1500. • Here’s how to do it: BSET $1500, %00101100 (or you could do BSET $1500, $2 C) • This instruction will set bits 2, 3, and 5 of the byte stored at memory location $1500, and will leave the other bits in that byte unchanged.
Details: BSET Actually Does an OR • From the Instruction Set Summary, we can see that BSET actually ORs the memory byte with our mask: (From p. 383 of the CPU Reference Manual. ) • So BSET $1500, %00101100 does the same thing as the following sequence: LDAA $1500 ORAA #%00101100 STAA $1500
Details: BCLR Actually Does an AND • From the Instruction Set Summary, we can see that BCLR actually ANDs the memory byte with the complement of our mask: (From p. 382 of the CPU Reference Manual. ) • So BCLR $1500, %00000100 does the same thing as the following sequence: LDAA $1500 ANDA #%11111011 STAA $1500
Review: Most Branch Instructions Look at Bits in the CCR • Recall that most branch instructions let you make decisions based on the values of bits in the Condition Code Register. • Example: The following code loads a byte into accumulator A and then branches if the LDAA instruction resulted in the Z bit being set: LDAA $1000 BEQ Go. Here • What if you want to branch based on bits in a memory location? Can you do that? Yes, by using two new instructions.
Bit Condition Branch Instructions • Two instructions, BRCLR and BRSET, let us branch based on one or more bits in a memory location. (Table from p. 76 of the HCS 12 CPU Reference Manual. )
BRCLR: Example • Here’s an example that will branch if bits 2, 3, and 5 of the byte stored at memory location $1500 are all 0 s (cleared). Otherwise it won’t branch: LDAA #5 BRCLR $1500, %00101100, Go. Here DECA BRA * Go. Here: INCA BRA *
BRSET: Example • Here’s an example that will branch if bit 7 of the byte stored at memory location $3400 is a 1 (set). Otherwise it won’t branch: LDAA #5 BRSET $3400, %10000000, Go. Here DECA Go. Here: BRA *
- Slides: 54