Unterkapitel zur HTML-Seitenverkleinerung


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
pasc_init0:
ldi r19, 0x00
ldi r16, HIGH (pascal)
mov XH, r16
ldi r16, LOW (pascal)
mov XL, r16
ldi COL_COUNTER, 0x00
pasc_init0_loop01:
ldi ROW_COUNTER, 0x00
pasc_init1_loop02:
st X+, r19
inc ROW_COUNTER
cpi ROW_COUNTER, PASCAL_HEIGHT
brne pasc_init1_loop02
inc COL_COUNTER
cpi COL_COUNTER, PASCAL_WIDTH
brne pasc_init0_loop01
ldi r16, HIGH (pascal)
mov YH, r16
ldi r16, LOW (pascal)
mov YL, r16
ldi r19, 0x01
std Y+PASC_FRST, r19
ret

pasc_echo:
ldi COL_COUNTER, 0x00
ldi ROW_COUNTER, 0x00

ret

pasc_run:
ldi COL_COUNTER, 0x00
ldi ROW_COUNTER, 0x00

ret

.dseg

pascal: .byte  PASCAL_HEIGHT*PASCAL_WIDTH
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; mal gucken, raucherpause, 0en nicht ausgeben, ergaenzt
pasc_echo:
ldi r23, HIGH (pascal+PASCAL_WIDTH*PASCAL_HEIGHT)
ldi r22, LOW (pascal+PASCAL_WIDTH*PASCAL_HEIGHT)
ldi r16, HIGH (pascal)
mov XH, r16
ldi r16, LOW (pascal)
mov XL, r16
pasc_echo_loop01:
ld r16, X+
cpi r16, 0x00
breq pasc_echo_no_out
out PORTD, r16
rjmp sleep
pasc_echo_no_out:
mov r23, XH
mov r22, XL
cp r20, r22
brge pasc_echo_loop01_out
rjmp pasc_echo_loop01
pasc_echo_loop01_out:
cp r21, r23
brge pasc_echo_loop02_out
rjmp pasc_echo_loop01
pasc_echo_loop02_out:
ret

pasc_run:
ldi COL_COUNTER, 0x00
ldi ROW_COUNTER, 0x00

ret
das post auto inkrement von X, mit X+ versagt, habe ich festgestellt.

Gibt übrigens ne Möglichkeit Wörter zu vergleichen fällt mir auf ich hab ja jetzt das Problem bisher. Ich lass das jetzt erst mal so anschaulicher Weise, damit so funktioniert aber es geht anders.

Kann auch sein, dass er das sehr wohl will, sondern dass ich bei der warte schleife und Mist eingebaut hat. Ich probier's mal ein dass es nicht da rauskommt oder sonst was

Ja, da muss irgendein Fehler drin sein bei der bei dem Aufruf von der Warteschleife. Da seh ich ich versteh ich weiß was ich falsch gemacht hab. Ich weiß was ich falsch gemacht hab. Es ist ein Fehler bei der Warteschleife und zwar nicht in der Warteschleife selber ich sehe, was ich falsch gemacht hab. Warten Sie, das ist zum Glück nicht Z+

Ja, das war es


//jetzt gibt es raucherpause und - danach kommt das ganze auf den atmega8, zusammen mit sram - die struktur der tabelle ist nun generell bekannt, aber das ganze muss nach assembler transformiert werden, von C her.

// kleine verbesserung

// (C) David Vajda
// 2025-03-10
// Pascalsches Dreieck Out

#include <stdio.h>

#define PASCAL_HEIGHT 11
#define PASCAL_WIDTH 2*PASCAL_HEIGHT+1

void prog_head_echo (void);
void pasc_init0 (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_echo (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_out (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_run (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);

void prog_head_echo (void) {
    printf ("(C) David Vajda\n");
    printf ("2025-03-10\n");
    printf ("Pascalsches Dreieck Out\n\n");
return;
}

void pasc_init0 (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT;  i++)
        for (j = 0;  j < PASCAL_WIDTH;  j++)
            pascal [i][j] = 0;
    printf ("---  %i --- \n\n", (PASCAL_WIDTH >> 1)+1);
    pascal [0][(PASCAL_WIDTH>>1)+1] = 1;
return;
}

void pasc_echo (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    printf ("{");
    for (i = 0;  i < PASCAL_HEIGHT;  i++) {
        printf ("{");
        for (j = 0;  j < PASCAL_WIDTH;  j++) {
            if (pascal [i][j] != 0)
                printf ("%i", pascal [i][j]);
            if ((pascal [i][j] != 0) && (j < (PASCAL_WIDTH - 1)))
                printf (", ");
        }
        printf ("}");
        if (i < (PASCAL_HEIGHT - 1))
            printf (", ");
    }
    printf ("}\n\n");
return;
}

void pasc_out (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT;  i++) {
        for (j = 0;  j < PASCAL_WIDTH;  j++) {
            if (pascal [i][j] == 0)
                printf ("  ");
            else
                printf ("%2i", pascal [i][j]);
        }
        printf ("\n");
    }

return;
}

void pasc_run (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT -1;  i++)
        for (j = 1;  j < PASCAL_WIDTH -1;  j++)
            pascal [i+1][j] = pascal [i][j-1] + pascal [i][j+1];
return;
}

int main (void) {
    int pascal [PASCAL_HEIGHT][PASCAL_WIDTH];

    prog_head_echo ();

    pasc_init0 (pascal);

    pasc_run (pascal);

    pasc_echo (pascal);
    pasc_out (pascal);
return 0;
}


david@work:~$ ./pascal20250310
(C) David Vajda
2025-03-10
Pascalsches Dreieck Out

---  12 ---

{{, , , , , , , , , , , , 1, , , , , , , , , , }, {, , , , , , , , , , , 1, , 1, , , , , , , , , }, {, , , , , , , , , , 1, , 2, , 1, , , , , , , , }, {, , , , , , , , , 1, , 3, , 3, , 1, , , , , , , }, {, , , , , , , , 1, , 4, , 6, , 4, , 1, , , , , , }, {, , , , , , , 1, , 5, , 10, , 10, , 5, , 1, , , , , }, {, , , , , , 1, , 6, , 15, , 20, , 15, , 6, , 1, , , , }, {, , , , , 1, , 7, , 21, , 35, , 35, , 21, , 7, , 1, , , }, {, , , , 1, , 8, , 28, , 56, , 70, , 56, , 28, , 8, , 1, , }, {, , , 1, , 9, , 36, , 84, , 126, , 126, , 84, , 36, , 9, , 1, }, {, , 1, , 10, , 45, , 120, , 210, , 252, , 210, , 120, , 45, , 10, , }}

                         1
                       1   1
                     1   2   1
                   1   3   3   1
                 1   4   6   4   1
               1   5  10  10   5   1
             1   6  15  20  15   6   1
           1   7  21  35  35  21   7   1
         1   8  28  56  70  56  28   8   1
       1   9  36  84  126  126  84  36   9   1
     1  10  45  120  210  252  210  120  45  10
david@work:~$


// (C) David Vajda
// 2025-03-10
// Pascalsches Dreieck Out

#include <stdio.h>

#define PASCAL_HEIGHT 11
#define PASCAL_WIDTH 2*PASCAL_HEIGHT+1

void prog_head_echo (void);
void pasc_init0 (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_echo (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_out (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);
void pasc_run (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]);

void prog_head_echo (void) {
    printf ("(C) David Vajda\n");
    printf ("2025-03-10\n");
    printf ("Pascalsches Dreieck Out\n\n");
return;
}

void pasc_init0 (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT;  i++)
        for (j = 0;  j < PASCAL_WIDTH;  j++)
            pascal [i][j] = 0;
    printf ("---  %i --- \n\n", (PASCAL_WIDTH >> 1)+1);
    pascal [0][(PASCAL_WIDTH>>1)+1] = 1;
return;
}

void pasc_echo (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    printf ("{");
    for (i = 0;  i < PASCAL_HEIGHT;  i++) {
        printf ("{");
        for (j = 0;  j < PASCAL_WIDTH;  j++) {
            if (pascal [i][j] != 0)
                printf ("%i", pascal [i][j]);
            if (j < (PASCAL_WIDTH - 1))
                printf (", ");
        }
        printf ("}");
        if (i < (PASCAL_HEIGHT - 1))
            printf (", ");
    }
    printf ("}\n\n");
return;
}

void pasc_out (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT;  i++) {
        for (j = 0;  j < PASCAL_WIDTH;  j++) {
            if (pascal [i][j] == 0)
                printf ("  ");
            else
                printf ("%2i", pascal [i][j]);
        }
        printf ("\n");
    }

return;
}

void pasc_run (int pascal [PASCAL_HEIGHT][PASCAL_WIDTH]) {
    int i, j;

    for (i = 0;  i < PASCAL_HEIGHT -1;  i++)
        for (j = 1;  j < PASCAL_WIDTH -1;  j++)
            pascal [i+1][j] = pascal [i][j-1] + pascal [i][j+1];
return;
}

int main (void) {
    int pascal [PASCAL_HEIGHT][PASCAL_WIDTH];

    prog_head_echo ();

    pasc_init0 (pascal);

    pasc_run (pascal);

    pasc_echo (pascal);
    pasc_out (pascal);
return 0;
}
Jetzt noch paar schöne Zähl folgen wo die externe Unterbrechung wunderschön funktionieren

wie gehen die fibonnaci zahlen? google hilft, erst mal das pascalsche dreieck. das muesste man auswendig wissen und geht so


{{1},{1,1},{1,2,1},{1,3,3,1},{1,4,6,4,1},{1,5,10,5,1},{1,6,15,20,15,6,1}}
jetzt koennte man versuchen die irgendwie so darzustellen

1.) option: erst die spalten, dann innerhalb der spalten die zeilen, also erst 1,1,1,..., dann naechstes 2.) oder wie es hier da steht, das heisst, erst zeile, dann alle spalten innerhalb der zeile, dann naechste zeile, ...

1.) blos, wie berechnet man die, ohne tabelle? 2.) oder muessen wir in unserem atmega8 erst eine tabelle erstellen

beides geht.

benutzen wir (2.) dann brauchen wir einen speicher

problem

1.) von neumann: daten und code/text in einem 2.) harward: code und daten getrennt

das bedeutet:

atmega8 1.) Programmspeicher in unserem eeprom fest 2.) Feste daten - Variationen von Architektur zu architektur immer moeglich 3.) aber daten nicht manipulierbar - wir brauchen SRAM - heisst das beim atmega8 und das heisst -

wir brauchen die tabelle und die muss manipuliert werden, also SRAM

gut - jetzt erst mal tabelle erstellen.

1.) zugriff auf SRAM nicht sehr heftig 2.) Tabelle erstellen: algorithmus

Algorithmus:

Problem: keine quadratische oder viereckige speichermatrix, sondern schief

Loesung: Problem? nein - weil - 0 nicht vergessen: Darstellungsproblem in LaTeX - ueberall wo 'nichts' steht, also eine 1 am anfang und sonst nichts, steht in wirklichkeit eine 0

also: tabelle: wir beginnen - mit - 0001000 oder irgendso etwas. im naechsen schritt addieren wir immer i und i+1 der j zeile und schreiben es in das entsprechende element der j+1 zeile

gut, bevor wir mit dem avr anfangen, probieren wir es in c am pc

ausgabe: beim avr: wie beim "bildschirmßpaltenelement, spaltenelement... naechste zeile und: 0 wird nicht ausgegeben.

so, jetzt kommt erst mal die darstellung in C, die frage ist

Die Frage ist, sollen wir das jetzt so machen wenn wir oben sozusagen also in der Zeile drüber sagen wir lieber Norden eine eins haben und 1° drunter im Süden südlich eine also zweimal eins, dementsprechend sagen wir so nebeneinander sollen wir die so machen, dass wir sozusagen zwei Spalten verbrauchen oder sollen wir drei Spalten verbrauchen und weil es ist ja eigentlich sagen wir mal ne schräge Anordnung und ich bin dafür, dass wir drei 3 Spalten verbrauchen drei Längen Grade nämlich dass wir sozusagen mittig drunter schreiben 101 ist eigentlich besser und dass die eins genau über der Null steht. Dann fangen wir mal an und machen das so. Dann werden innerhalb der Spalten überall Nullen stehen dazwischen auffüllen und wenn wir das ausgeben, dürfen die Nullen nicht mit ausgegeben werden.

Tatsächlich heißt es mcucr hab ich gerade richtig gesagt aber hab nicht geglaubt, dass es richtig ist, weil d.h. Mcu Control Register das ist Punkt Nummer eins, das hab ich richtig. ISC steht für Intrup sence Control. Das hab ich richtig was ich immer verwechseln und das merke ich mir immer und mach dann eben deswegen falsch rum wie immer das kann man gibt allerdings hier wahrscheinlich keine Eselsbrücke. Wenn man's noch genauer macht dann vielleicht schon aber es gibt eben das GICR das ist das Global Interrupt Control Register und eben des mcu Control, register und da muss man bedenken die heißen int0 und int1 das ist das Problem das andere Problem jetzt haben wir das klassische Theater mit der Antennenleistung und die nicht in Prellgeräten Tasten weil das Problem ist. Wir brauchen jetzt mal wieder einen Pull down Widerstand am Eingang. Das ist Problem Nummer eins in diesem Fall, wo wir keine normalen Taster haben. Lohnt es sich sozusagen zur Abwechslung mal isc11 anzugucken, weil interrupt sence Control macht jetzt überhaupt keinen Sinn bei dem klassischen stk500 das sind ja die Taster schon drauf aber hier sind eben keine Taster d.h. wenn ich das Kabel aufmache„ dann ist der Kontakt sozusagen langfristig unterbrochen und dann zählt jetzt einfach immer weiter. Es funktioniert trotzdem aber es zählt schön weiter. Jetzt hab ich zwei Probleme einerseits es bleibt halt die Antennenleistung. Das ist nicht immer das Problem wie gut ihre Impedanz stimmt es kriegen sie selber hin glaube ich, sondern das Problem ist das hier einfach ne Antenne ist und da kommt egal wie irgendwas rein ganz einfach. Das brauchen wir also einen pull down Widerstand oder ein pull up Widerstand klassisches Problem und das zweite Problem eben nicht unbedingt die Entzugsprellung. Das würde ich jetzt nicht sagen das ist nicht das Problem weil wenn sie isc11 anders einstellen und sie ziehen das Kabel raus zählst zählt es trotzdem weiter. Das ist kein Problem von einer Entzugsprellung sondern dass da halt ne Antennenleistung drauf ist. Sonst wird's beim rausziehen ein paar mal zählen und dann aufhören das zählt aber weiter d.h. es ist jetzt ne Antenne wir brauchen jetzt im pull down Widerstand und wie gesagt das zweite Problem ist eben, dass am Ende die Interrupt sence Control falsch einstellen in dem Fall können wir das negativ beeinflussen, indem es nicht nur einmal beim rausziehen oder beinah positiven oder negativen Taktflanke zählt, sondern eben zum Beispiel überhaupt einfach weiter zählt. D.h. das können wir beeinflussen.


;; funktioniert wunderbar

;; (C) David Vajda
;; 2025-03-10
;; Extern Interrupt - LED Count

.include "m8def.inc"

.org 0x000
rjmp RESET
.org INT0addr
rjmp ExtInt0Handler
.org INT1addr
rjmp ExtInt1Handler

RESET:
ldi r16, HIGH (RAMEND)
out SPH, r16
ldi r16, LOW (RAMEND)
out SPL, r16

ldi r16, 0xff
out DDRB, r16

ldi r16, 0xff
out PORTB, r16

ldi r16, (1 << ISC11 | (1 << ISC10) | (1 << ISC01) | (1 << ISC00))
out MCUCR, r16
ldi r16, (1 << INT1) | (1 << INT0)
out GICR, r16

sei

end: rjmp end

ExtInt0Handler:
dec r16
out PORTB, r16
reti

ExtInt1Handler:
inc r16s
out PORTB, r16
reti

;; Kleiner Fehler drin im alten. Es können ja suchen, wo der steckt.

;; (C) David Vajda
;; 2025-03-10
;; Blink LED

.include "m8def.inc"

ldi r16, HIGH (RAMEND)
out SPH, r16
ldi r16, LOW (RAMEND)
out SPL, r16

ldi r16, 0xff
out DDRB, r16

ldi r16, 0x80
loop1:
out PORTB, r16
rcall sleep
lsr r16
cpi r16, 0x00
brne stepover
ldi r16, 0x80
stepover:
rjmp loop1

sleep:
push r16
push r17
ldi r16, 0xff
sleep_loop1:
ldi r17, 0xff
sleep_loop2:
dec r17
brne sleep_loop2
dec r16
brne sleep_loop1
pop r17
pop r16
ret

;; (C) David Vajda
;; 2025-03-10
;; Blink LED

.include "m8def.inc"

ldi r16, HIGH (RAMEND)
out SPH, r16
ldi r16, LOW (RAMEND)
out SPL, r16

ldi r16, 0xff
out DDRB, r16

ldi r16, 0x80
loop1:
out PORTB, r16
rcall sleep
lsr r16
cpi r16, 0x01
brne stepover
ldi r16, 0x80
stepover:
rjmp loop1

sleep:
push r16
push r17
ldi r16, 0xff
sleep_loop1:
ldi r17, 0xff
sleep_loop2:
dec r17
brne sleep_loop2
dec r16
brne sleep_loop1
pop r17
pop r16
ret
;; funktioniert auf anhieb, das wandern