0

The program must display letters from a to z (alternate uppercase and lowercase horizontally) using looping.

 Sample Output :

AaBb . . . . . . . . . . . . YyZz

This is the code I've used so far but it only outputs the uppercase letters. Please help me how to combine those lower case letters :(

Thank you :)

.model small
.code
.stack 100
org 100h 
start :
       mov  ah, 02h
       mov   cl, 41h 
skip :
       mov  dl, cl
       Int     21h   
       inc    cl
       cmp  cl, 5Ah
       jnz   skip
       Int    27h
end start
elixenide
  • 44,308
  • 16
  • 74
  • 100
Francoise
  • 3
  • 1
  • 4
  • 2
    Please do not deface your question. By posting it here, you licensed it to the community (see [this help center page](http://stackoverflow.com/help/editing)). You cannot destroy it for personal reasons. If you need help from a moderator, you can flag the message and explain what you need. – elixenide Aug 10 '16 at 03:59
  • okay. thanks anyway – Francoise Aug 10 '16 at 04:02

2 Answers2

1

You have to add 20 (hex) to show the lowercase ones. Like this:

 start :
     mov  ah, 02h
     mov  cl, 41h 
 skip :
     mov   dl, cl
     Int   21h   
     add   dl, 20h
     Int   21h
     inc   cl
     cmp   cl, 5Ah
     jnz   skip
     Int   27h
 end start

UPDATE

Another way to do it:

 start :
     mov  ah, 02h
     mov  cl, 41h 
 skip :
     mov   dl, cl
     Int   21h   
     xor   dl, 20h
     Int   21h
     inc   cl
     cmp   cl, 5Ah
     jnz   skip
     Int   27h
 end start
David BS
  • 1,822
  • 1
  • 19
  • 35
  • I don't see how this alternates. Doesn't it just increment an uppercase loop counter and lcase a copy of it every iteration? I like Paxdiablo's unroll-by-two suggestion that makes it easy to implement. The other option is to `xor cl, 0x20` every iteration to [toggle between upper and lower case](http://stackoverflow.com/a/35936844/224132). – Peter Cordes Aug 10 '16 at 01:48
  • If xor cl,20h you will have to move CL contents again to DL to provide the print using the INT 21h (which see character in DL). XOR is a good result also, but over DL and not CL. Anyway, I believe that XOR and ADD may consume the same clocks of CPU (I'm not sure about this). – David BS Aug 10 '16 at 01:56
  • Sir can I ask what is the use of "xor" ? I'm new in TASM so its not easy for me to understand some of the codes :( – Francoise Aug 10 '16 at 02:04
  • Oh, I misread what the OP wanted, and your code. I thought the OP wanted `AbCd...`, which would have been more interesting than printing every letter both ways. I was thinking of a loop like `int 21h` / `inc dl` / `xor dl,0x20` / `cmp dl, 'z' / jb` (keeping the loop counter in dl because `int 21h` doesn't clobber it). And yes, `xor` and `add` both have the same latency and throughput on all modern x86 CPUs. (See http://agner.org/optimize/, and also the [x86 tag wiki](http://stackoverflow.com/tags/x86/info) – Peter Cordes Aug 10 '16 at 02:05
  • Sure. XOR is equivalent to "eXclusive OR", I mean, it can invert the bits of a byte ONLY if ONLY they're different. XOR consumes only 1 clock of CPU. I don't remember how many clocks ADD consumes, but if it consumes 2 clocks, you will have (with XOR) a faster routine. In this case, XOR with 20h is THE SAME as add 20h. – David BS Aug 10 '16 at 02:07
  • 1
    @DavidBS: lol, performance is way more complicated than that on modern x86. For example Haswell can run 4 independent `add`s or `xor`s (or a mix) per clock, since all 4 of its integer ALU ports can handle either instruction. But if one depends on the result of another, you're limited (by latency) to one per clock. See Agner Fog's microarch guide and instruction tables, which I linked earlier. Also other answers on http://stackoverflow.com/questions/9957004/modern-x86-cost-model – Peter Cordes Aug 10 '16 at 02:11
  • 1
    Don't mess about with `xor`. At the educational level, you're probably going to be penalised for trying to be sneaky rather than writing readable code :-) – paxdiablo Aug 10 '16 at 02:14
  • Oh I see. thank you so much :D Guess I need to study very hard about assembly language. – Francoise Aug 10 '16 at 02:14
  • 1
    @L.Arona: or you could say: use `xor` when you want to toggle some bits. e.g. to flip between upper and lower case, like in the answer I linked earlier. Use `add` if it makes more sense to think about adding. (Fun fact: `xor` is an add without carry). – Peter Cordes Aug 10 '16 at 02:21
  • @Peter Cordes: That's way better. It's cleared now for me. Thank you :) – Francoise Aug 10 '16 at 02:25
  • @Francoise "study hard"... actually yes and no. Bit operations: `and, or, xor` (complementary `not` and arithmetic `neg` are bonus), shifts/rotate family (like `shl, rcr`), pure arithmetic `add, sub, mul, div`, `jmp` around (`call` it loud), copy group of bits (`mov`, because copying is moving in hw architect language), operate stack (`push, pop, enter, leave`), and some tools for branching `cmp, test`, and some classic helpers like `stos, lods, movs`... maybe a week or two to exercise work with bits, and understanding binary numbers well, another 1-2w for those instructions, and that's all. – Ped7g Aug 10 '16 at 09:40
  • @Francoise now to produce anything meaningful with that, or to learn further details (modern x86 CPU has many more specialized instructions, which can be "emulated" by those I wrote in previous comment, but if you want full performance, you should use the specialized ones), that may require few more weeks of practice.. like few years. But to get the basics a month or two is enough, just switch your brain into binary number processing (this has additional bonus, that you can't be afraid or worrying, as that doesn't make any sense in binary). – Ped7g Aug 10 '16 at 09:42
1

If you want them interspersed, the ASCII character set has an offset of 20h between the uppercase and lowercase letters:

enter image description here

You can see from that table that moving from A to a requires adding 20h (to go from 41h to 61h) and this is the same for all other letters as well.

So, instead of simply adding one at the end of the loop, you must first:

  • add 20h.
  • print that character.
  • subtract 1fh (i.e., subtract 20h then add one).

In other words, change:

mov  dl, cl
int  21h
inc  cl

into something like:

mov  dl, cl     ; load dl with character and print.
int  21h

add  cl, 20h    ; move to lowercase variant and print.
mov  dl, cl
int  21h

sub  cl, 1fh    ; move back to next uppercase variant.

The code can be made shorter if you know that the interrupt won't clobber the dl register you're using (and the excellent Ralf Brown interrupt list seems to indicate this is so, stating that only al is changed):

mov  dl, cl     ; load dl with character and print.
int  21h

add  dl, 20h    ; move dl to lowercase variant and print.
int  21h

inc  cl         ; move cl to next uppercase variant.
paxdiablo
  • 854,327
  • 234
  • 1,573
  • 1,953