;christmas chain ;(C)2005 by wek http://www.efton.sk ;use freely; please let me know to xmas-at-efton.sk if you use it or modify it ; ;LED chain is driven by 2x74LS164 in a cascade, ;LEDs connected directly (no resistors) anodes to 74LS164 outputs, ; cathodes to GND ;for "properly" connected LEDs to shift registers (cathodes to outputs, ; anodes through resistor to VCC), invert data in the shiftout routine (IntT0) ;for latched shift registers, drive latch after shifting out all data ; by end of IntT0 ;CLOCK of 74LS164 connected to P1.7, DATA to P1.5 ;XTAL=22.1184MHz, for cca 11MHz xtal reload 80h into th0 in IntT0 ;$SET(SPI) to use hardware SPI on P89V51RD2 ; ;for adding "effects": ;- insert jump to "effect" routine into AlgosTab ;- at the beginning of "effect" routine check IntTim1, return if nonzero ;- if IntTim1 is zero ; - set IntTim1 to constant timing one "step" of the "effect" ; - if effect initialisation is required, do it when AlgoTim=0FFh ; - perform the "effect" by modifying Data0 and Data1 ; - decrement AlgoTim ;- return $SET(SPI) T2CON EQU 0c8h T2MOD EQU 0c9h TH2 EQU 0CDh TL2 EQU 0CCh TR2 EQU 0CAh ;SFR bit (in T2CON) RCAP2L EQU 0CAh RCAP2H EQU 0CBh LED EQU P3.6 ;this LED flashes wildly indicating operation Data0 EQU 20h Data1 EQU 21h IntFlag EQU 22h.0 Rnd EQU 30h ;8 bytes IntTim1 EQU 38h AlgoNo EQU 39h AlgoTim EQU 3Ah ;2 bytes (?) ;counter for how many times an algo should be executed Stack EQU 40h USING 0 CSEG org 0 ljmp Start org 0Bh ljmp IntT0 ;------------------- INIT --------------------- org 30h Start: mov sp,#Stack-1 mov tmod,#20h ; Timer1 autoreload 8bit (baud generator), Timer0 in 13bit mode mov th1,#-1 ;#0feh ; 115200 at 22.1184MHz mov pcon,#80h mov scon,#72h ; 8 bit UART mode, but with the "no RI if no stop bit" feature activated mov tcon,#30h ; run timers mov t2con,#0 ;autoreload mode, osc/12 ; mov ie,#82h ; only timer0 interrupt enabled mov P1,#0F9h mov P3,#0DFh mov r3,#2*5 LampTX1: djnz r0,LampTX1 djnz r1,LampTX1 cpl LED djnz r3,LampTX1 mov AlgoNo,#0 mov AlgoTim,#0FFh mov Data0,#12h mov Data1,#45h ;--- init SPI $IF(SPI) mov 0D5h,#01110001b $ENDIF setb tr0 ;hmmmm... this was already enabled in tcon... setb tr1 setb et0 setb ea Loop: call Randomize jnb ri,RIW1 cpl LED mov Data0,sbuf clr ri RIW1: ; call Run1 call CallAlgos ; call LongDelay jmp Loop Stop: sjmp Stop CallAlgos: mov a,AlgoTim jnz CAX1 dec AlgoTim inc AlgoNo mov a,AlgoNo add a,#'0' jnb ti,$ clr ti mov sbuf,a CAX1: mov a,AlgoNo add a,AlgoNo add a,AlgoNo mov dptr,#AlgosTab jmp @a+dptr AlgosTab: ljmp Run1 ljmp Run2 ljmp Run3 ljmp Run4 ljmp Run4a ljmp Run5 Restart: ;the last in AlgosTab mov AlgoNo,0 ret ;---------- interrupt IntT0: ; mov th0,#128 ;this constant determines the overall speed - uncomment if xtal<22MHz push psw push acc setb IntFlag mov a,IntTim1 jz IntTX1 dec IntTim1 IntTX1: cpl LED $IF(SPI) mov a,Data0 ;cpl a ;if LEDs are connected "properly" mov 86h,a Wait1: mov a,0AAh jnb acc.7,Wait1 anl 0AAh,#01111111B mov a,Data1 ;cpl a ;if LEDs are connected "properly" mov 86h,a Wait2: mov a,0AAh jnb acc.7,Wait2 anl 0AAh,#01111111B $ELSE push b push ar2 mov a,Data0 ;cpl a ;if LEDs are connected "properly" mov b,#8 Loop1: clr P1.7 rrc a mov P1.5,c ; call Delay setb P1.7 ; call Delay djnz b,Loop1 mov a,Data1 ;cpl a ;if LEDs are connected "properly" mov b,#8 Loop2: clr P1.7 rrc a mov P1.5,c ; call Delay setb P1.7 ; call Delay djnz b,Loop2 pop ar2 pop b $ENDIF ;place triggering the latch here, if latched shiftregister used pop acc pop psw reti ;--------------- utils --------- Delay: ; jnb ri,Delay ; clr ri ; ret mov r2,#2 Delay1: djnz r2,Delay1 ret LongDelay: mov r2,#80 mov r4,#0 LDelay1: djnz r4,LDelay1 djnz r2,LDelay1 ret Randomize: mov a,RND+3 rr a rr a xrl a,RND+2 rr a rr a rr a rr a xrl a,RND rr a xrl a,RND xrl a,#1 rrc a mov a,RND rlc a mov RND,a mov a,RND+1 rlc a mov RND+1,a mov a,RND+2 rlc a mov RND+2,a mov a,RND+3 rlc a mov RND+3,a mov a,RND+7 anl a,#11101010b mov c,p rlc a xrl a,RND+4 rrc a mov a,RND+7 rrc a mov RND+7,a mov a,RND+6 rrc a mov RND+6,a mov a,RND+5 rrc a mov RND+5,a mov a,RND+4 rrc a mov RND+4,a ret ;----- Data modification algos Run1: ;random running from end to beginning ; jnb IntFlag,IWX1 ; clr IntFlag mov a,IntTim1 jnz Run1X1 mov IntTim1,#20 ;speed mov a,Rnd+7 anl a,#7 clr c jnz Run1X2 setb c Run1X2: mov a,Data0 orl a,Data1 jnz Run1X3 setb c Run1X3: mov a,Data0 jnb acc.0,Run1X4 clr c Run1X4: mov a,Data0 rlc a mov Data0,a mov a,Data1 rlc a mov Data1,a dec AlgoTim Run1X1: ret Run2: ;random running from beginning to end mov a,IntTim1 jnz Run2X1 mov IntTim1,#20 ;speed mov a,Rnd+7 anl a,#7 clr c jnz Run2X2 setb c Run2X2: mov a,Data0 orl a,Data1 jnz Run2X3 setb c Run2X3: mov a,Data1 jnb acc.7,Run2X4 clr c Run2X4: mov a,Data1 rrc a mov Data1,a mov a,Data0 rrc a mov Data0,a dec AlgoTim Run2X1: ret Run3: ;1:1 flash mov a,IntTim1 jnz Run3X1 mov IntTim1,#40 ;speed mov a,AlgoTim inc a jnz Run3X2 mov Data0,#55h mov Data1,#55h mov AlgoTim,#100 ;short down this mode - it's too long and boring Run3X2: xrl Data0,#0FFh xrl Data1,#0FFh dec AlgoTim Run3X1: ret Run4: mov a,IntTim1 ;KIT - KnightRider jnz Run4X1 mov IntTim1,#16 mov a,AlgoTim mov b,#14 div ab mov a,b mov r2,a add a,#Run4T1-Run4X2 movc a,@a+pc Run4X2: mov Data0,a mov a,r2 add a,#Run4T2-Run4X3 movc a,@a+pc Run4X3: mov Data1,a dec AlgoTim Run4X1: ret Run4T1: db 80h,40h,20h,10h,08h,04h,02h db 01h,02h,04h,08h,10h,20h,40h Run4T2: db 01h,02h,04h,08h,10h,20h,40h db 80h,40h,20h,10h,08h,04h,02h Run4a: mov a,IntTim1 ;KIT - KnightRider - 2 jnz Run4aX1 mov IntTim1,#16 mov a,AlgoTim mov b,#22 div ab mov a,b mov r2,a add a,#Run4aT1-Run4aX2 movc a,@a+pc Run4aX2: mov Data0,a mov a,r2 add a,#Run4aT2-Run4aX3 movc a,@a+pc Run4aX3: mov Data1,a dec AlgoTim Run4aX1: ret Run4aT2: db 80h,40h,20h,10h,08h,04h,02h db 01h,02h,04h,08h,10h,08h,04h,02h db 01h,02h,04h,08h,10h,20h,40h Run4aT1: db 01h,02h,04h,08h,10h,20h,40h db 80h,40h,20h,10h,08h,10h,20h,40h db 80h,40h,20h,10h,08h,04h,02h Run5: ;ping-pong mov a,IntTim1 jnz Run5X1 mov IntTim1,#15 ;speed mov a,AlgoTim inc a jnz Run5X2 mov Data0,#01h mov Data1,#00h sjmp Run5X3 Run5X2: mov a,AlgoTim jnb acc.4,Run5X4 ;determine the movement direction clr c mov a,Data0 rlc a mov Data0,a mov a,Data1 rlc a jc Run5X3 ;not to loose the "ball" if it would "fall over the edge" mov Data1,a sjmp Run5X3 Run5X4: clr c mov a,Data1 rrc a mov Data1,a mov a,Data0 rrc a jc Run5X3 ;not to loose the "ball" if it would "fall over the edge" mov Data0,a Run5X3: dec AlgoTim Run5X1: ret ;------------------ THAT'S ALL, FOLKS! ------------------- end