; ; hello.asm ; ; A "Hello, World!" which illustrates an Atari 2600 programming ; introduction talk (slides at http://slideshare.net/chesterbr). ; ; This is free software (see license below). Build it with DASM ; (http://dasm-dillon.sourceforge.net/), by running: ; ; dasm hello.asm -ohello.bin -f3 ; PROCESSOR 6502 INCLUDE "vcs.h" ORG $F000 ; Start of "cart area" (see Atari memory map) StartFrame: lda #%00000010 ; Vertical sync is signaled by VSYNC's bit 1... sta VSYNC REPEAT 3 ; ...and lasts 3 scanlines sta WSYNC ; (WSYNC write => wait for end of scanline) REPEND lda #0 sta VSYNC ; Signal vertical sync by clearing the bit PreparePlayfield: ; We'll use the first VBLANK scanline for setup lda #$00 ; (could have done it before, just once) sta ENABL ; Turn off ball, missiles and players sta ENAM0 sta ENAM1 sta GRP0 sta GRP1 sta COLUBK ; Background color (black) sta PF0 ; PF0 and PF2 will be "off" (we'll focus on PF1)... sta PF2 lda #$FF ; Playfield collor (yellow-ish) sta COLUPF lda #$00 ; Ensure we will duplicate (and not reflect) PF sta CTRLPF ldx #0 ; X will count visible scanlines, let's reset it REPEAT 37 ; Wait until this (and the other 36) vertical blank sta WSYNC ; scanlines are finished REPEND lda #0 ; Vertical blank is done, we can "turn on" the beam sta VBLANK Scanline: cpx #174 ; "HELLO WORLD" = (11 chars x 8 lines - 1) x 2 scanlines = bcs ScanlineEnd ; 174 (0 to 173). After that, skip drawing code txa ; We want each byte of the hello world phrase on 2 scanlines, lsr ; which means Y (bitmap counter) = X (scanline counter) / 2. tay ; For division by two we use (A-only) right-shift lda Phrase,y ; "Phrase,Y" = mem(Phrase+Y) (Y-th address after Phrase) sta PF1 ; Put the value on PF bits 4-11 (0-3 is PF0, 12-15 is PF2) ScanlineEnd: sta WSYNC ; Wait for scanline end inx ; Increase counter; repeat untill we got all kernel scanlines cpx #191 bne Scanline Overscan: lda #%01000010 ; "turn off" the beam again... sta VBLANK ; REPEAT 30 ; ...for 30 overscan scanlines... sta WSYNC REPEND jmp StartFrame ; ...and start it over! Phrase: .BYTE %00000000 ; H .BYTE %01000010 .BYTE %01111110 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %00000000 .BYTE %00000000 ; E .BYTE %01111110 .BYTE %01000000 .BYTE %01111100 .BYTE %01000000 .BYTE %01000000 .BYTE %01111110 .BYTE %00000000 .BYTE %00000000 ; L .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01111110 .BYTE %00000000 .BYTE %00000000 ; L .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01111110 .BYTE %00000000 ; O .BYTE %00000000 .BYTE %00111100 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %00111100 .BYTE %00000000 .BYTE %00000000 ; white space .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 .BYTE %00000000 ; W .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %01011010 .BYTE %00100100 .BYTE %00000000 .BYTE %00000000 ; O .BYTE %00111100 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %01000010 .BYTE %00111100 .BYTE %00000000 .BYTE %00000000 ; R .BYTE %01111100 .BYTE %01000010 .BYTE %01000010 .BYTE %01111100 .BYTE %01000100 .BYTE %01000010 .BYTE %00000000 .BYTE %00000000 ; L .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01000000 .BYTE %01111110 .BYTE %00000000 .BYTE %00000000 ; D .BYTE %01111000 .BYTE %01000100 .BYTE %01000010 .BYTE %01000010 .BYTE %01000100 .BYTE %01111000 .BYTE %00000000 ; Last byte written to PF1 (important, ensures lower tip ; of letter "D" won't "bleeed") ORG $FFFA ; Cart config (so 6502 can start it up) .WORD StartFrame ; NMI .WORD StartFrame ; RESET .WORD StartFrame ; IRQ END ; ; Copyright 2011-2013 Carlos Duarte do Nascimento (Chester). All rights reserved. ; ; Redistribution and use in source and binary forms, with or without modification, are ; permitted provided that the following conditions are met: ; ; 1. Redistributions of source code must retain the above copyright notice, this list of ; conditions and the following disclaimer. ; ; 2. Redistributions in binary form must reproduce the above copyright notice, this list ; of conditions and the following disclaimer in the documentation and/or other materials ; provided with the distribution. ; ; THIS SOFTWARE IS PROVIDED BY CHESTER ''AS IS'' AND ANY EXPRESS OR IMPLIED ; WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND ; FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL OR ; CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR ; CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR ; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ; ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING ; NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ; ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ; ; The views and conclusions contained in the software and documentation are those of the ; authors and should not be interpreted as representing official policies, either expressed ; or implied, of Chester. ;