Forum: Mikrocontroller und Digitale Elektronik MPLAB, PIC, Konstanten aus Speicher


von Michael B. (auchduliebergott)


Lesenswert?

PIC16F1512, MPLAB, Assembler
Die folgende Zeile definiert die Konstante d'24':
[#define   nnn   d'24']

;Dann folgen Berechnungen mit nnn:
[#define  anztone  d'32']
[#define  hnn  nnn+anztone-d'1']

Die Zeile "#define   nnn  d'24'" habe ich bislang per Hand ins Programm 
eingegeben.

Jetzt aber wird der Wert "nnn" über DIP-Schalter eingelesen und der Wert 
für "nnn" liegt nach dem Einlesen der DIP-Schalter in der  Speicherzelle 
"uNote".

Frage:
Wie kann ich den Inhalt der Speicherzelle "uNote" dem Wert "nnn" 
zuweisen, damit die obigen Berechnungen mit "nnn" weiterhin korrekt 
funktionieren?

von Stephan S. (uxdx)


Lesenswert?

1.
#define nnn d'24' ersetzen durch
1
movlw d'24'
2
movwf nnn

und später wenn uNote feststeht wird uNote nach nnn kopiert durch
1
movfw unote
2
movwf nnn

von Michael B. (auchduliebergott)


Lesenswert?

Hallo Stephan,

vielen Dank für Deine Mühe und für die schnelle Hilfe.
Ich werde es einmal ausprobieren, aber dennoch habe ich noch folgende 
Frage:

Bislang hatte "nnn" noch keine Speicherzelle.
Nach Deiner Anleitung muss ich zuerst eine Speicherzelle für "nnn" 
belegen.
Wenn ich später "uNote" nach "nnn" speichere, funktioniert dann die 
Berechnung
[#define  hnn  nnn+anztone-d'1'] immer noch, denn?
In der Vergangenheit war "nnn" eine Konstante, die ich durch "#define" 
festgelegt hatte. Mit Deiner Lösung wäre "nnn" der Inhalt der 
Speicherzelle "nnn" (und hoffentlich nicht die Adresse von "nnn").
Wie kann der Compiler dies eigentlich unterscheiden?

von Stephan S. (uxdx)


Lesenswert?

Michael B. schrieb:
> Bislang hatte "nnn" noch keine Speicherzelle.
> Nach Deiner Anleitung muss ich zuerst eine Speicherzelle für "nnn"
> belegen.
ok, da habe ich etwas missverstanden. Die 1. define-Zeile wird gar nicht 
mehr benötigt, denn Du liest ja den Wert jetzt über schalter ein.

> Wenn ich später "uNote" nach "nnn" speichere, funktioniert dann die
> Berechnung
> [#define  hnn  nnn+anztone-d'1'] immer noch, denn?
> In der Vergangenheit war "nnn" eine Konstante, die ich durch "#define"
> festgelegt hatte. Mit Deiner Lösung wäre "nnn" der Inhalt der
> Speicherzelle "nnn" (und hoffentlich nicht die Adresse von "nnn").
Da hast Du was missverstanden
[# define ...] bedeutet, dass der Compiler immer dann, wenn hnn im 
Source steht, statt dessen nnn+anztone-d'1' genommen wird. Das kann man 
als Konstante benutzen oder dazu einem Speicherplatz oder einem Bit 
einen aussagekräftigen Namen zuzuweisen, z.B. #define porta,7 LED wenn 
am Bit 7 des Port A eine LED hängt.

Ich kann das z.Zt. leider nicht selbst ausprobieren, da ich mit dem 
Laptop unterwegs bin. Schau doch mit dem Debugger (früher hiess der 
MPLAB SIM) im Einzelschritt, was die Register und die Speicherplätze 
machen.

von Dieter W. (dds5)


Lesenswert?

Michael B. schrieb:
> Wenn ich später "uNote" nach "nnn" speichere, funktioniert dann die
> Berechnung
> [#define  hnn  nnn+anztone-d'1'] immer noch, denn?

Nein, denn die Berechnung wird schon bei der Assemblierung des Programms 
ausgeführt. Da aber nnn erst zur Laufzeit bekannt ist, funktioniert das 
nicht.

Alles was mit #define festgelegt wird, ergibt nur eine Textersetzung an 
der Stelle im Quelltext, an der es steht.
An Stelle von hnn wird der dafür vom Assembler berechnete Wert als 
Konstante im Programm benutzt. Wenn der zur Laufzeit geändert werden 
soll, muss er in einer Speicherzelle abgelegt und die Rechenoperation im 
Programm ausgeführt werden.

von Michael B. (auchduliebergott)


Lesenswert?

Herzlichen Dank noch einmal für Deine ausführlichen Erklärungen.
Somit muss ich für alle Berechnungen dafür sorgen, dass sie während des 
Laufes des Programmes möglich sind und dies bedeutet, dass ich jeder 
Konstanten einen Speicherplatz spendieren muss.
Deine Erklärung, dass das Programm laufen muss, um diese Berechnungen 
auszuführen ist sofort einleuchtend.
Dann kann ich mit dem Simulator testen, was im Einzelnen passiert. Dabei 
dürfte auch die Frage beantwortet werden, ob der Compiler den Inhalt der 
Speicherzelle "nnn" benutzt, oder nicht.
Um solche Tests zu machen, muss ich zuerst das (funktionierende) 
Alt-Programm sichern damit ich immer zurück kann.
Damit beginne ich morgen und gebe gerne Bescheid, wie die Sache gelaufen 
ist.
Ich hoffe, dass meine Erfahrungen mit MPLAB ausreichen, aussagefähige 
Tests zu machen...

von Michael B. (auchduliebergott)


Lesenswert?

Ich habe jetzt alles geändert und es funktioniert.

Bisher funktionierte z.B.:
#define noon  0x90+kanal-0x1

Ich habe dies wie folgt geändert:
  movlw  0x90
  addwf  kanal,0    ;w = w + kanal
  movwf  noon
  decf  noon,1    ;noon = noon - 1

Dies funktioniert erwartungsgemäß!

Außerdem habe ich noch folgendes probiert:
  movlw  0x90 + kanal - 0x1
  movwf  noon
Dies funktioniert nicht, weil der hier mit der Adresse von "kanal" und 
nicht mit dem Inhalt der Zelle "kanal" gerechnet wird. Eigentlich 
schade, denn man könnte damit einige Programmzeilen einsparen, oder geht 
das irgendwie doch?

Letztendlich ist das Problem aber gelöst und ich bedanke mich noch 
einmal für Deine Hilfe, die mir den richtigen Anstoß gegeben hat.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.