Forum: Mikrocontroller und Digitale Elektronik Padauk PFS154 und Rambelegung


von Ralph S. (jjflash)


Lesenswert?

Man möge mir die Anfrage verzeihen (weil ich noch absoluter Newbie im 
Umgang mit PADAUK in Verbindung mit SDCC bin).

Vllt. weiß ja Philipp Klaus K. einen Rat für mich oder kann mir etwas 
erläutern: bisher habe ich in Programmen, wenn es evtl. knapp mit dem 
Ram war (nicht Padauk) "einfach" den verfügbaren Speicherplatz 
abgefragt, das kann ich mit den (sehr) kleinen PFS154
nicht.

Also mache ich mich über das Map-File des SDCC her (schlicht weil ich 30 
oder 40 Byte mehr Ram benötige).

In meinem Programm habe ich eine Funktion:
1
// mir ist bewusst, dass das Registerarray 32 Byte Ram frisst, aber das geht leider nicht anderst
2
3
uint16_t rda5807_reg[16];
4
5
...
6
7
void rda5807_setvol(uint16_t volume)
8
{
9
  rda5807_reg[5]=(rda5807_reg[5] & 0xFFF0) |  volume;
10
  rda5807_writereg(5);
11
}

Laut map-file des SDCC benötigt die Funktion für das Argument 8 Byte 
(Speicher von 0x3F bis 0x46 (inklusive):

Listing map-File
----------------
1
Area                                    Addr        Size        Decimal Bytes (Attributes)
2
--------------------------------        ----        ----        ------- ----- ------------
3
DATA                                00000002    00000065 =         101. bytes (REL,CON)
4
5
      Value  Global                              Global Defined In Module
6
      -----  --------------------------------   ------------------------
7
     00000002  _aktfreq                           rda5807_test
8
     00000004  _aktvol                            rda5807_test
9
     00000005  _rda5807_reg                       rda5807_test
10
     00000025  _i2c_startaddr_b_PARM_1            rda5807_test
11
     00000026  _i2c_startaddr_b_PARM_2            rda5807_test
12
     00000027  _rda5807_writereg_PARM_1           rda5807_test
13
     00000039  _rda5807_setfreq_PARM_1            rda5807_test
14
     0000003F  _rda5807_setvol_PARM_1             rda5807_test
15
     00000047  _setnewtune_PARM_1                 rda5807_test

Warum ist das so?

Interpretiere ich hier etwas falsch ? Ich hätte im besten Fall 4 Bytes 
vermutet, 2 für den Parameter und 2 für die Rücksprungadresse (wobei ich 
eigentlich annehme, dass eine Rücksprungadresse auf dem Stack liegt und 
hierfür nicht extra Ram reserviert wird).

Interpretiere ich das falsch und es werden gar keine 8 Bytes reserviert 
und wenn ich das nicht falsch interpretiere wie kann ich Abhilfe 
schaffen?

--------------------------------------

Wenn ich mein Programm nur mit globalen Variablen schreibe funktioniert 
das Programm aber es ist natürlich höchst unschön (und ich will das 
eigentlich nicht mit mehr globalen Variablen machen als notwendig).

Gruß,
Ralph

von Ralph S. (jjflash)


Lesenswert?

Vergessen habe:

Compilerflags sind:

--std-sdcc11 --opt-code-size

Kann ich hier etwas ändern, Flashspeicher habe ich noch etwas

von MaWin (Gast)


Lesenswert?

Keine Möglichkeit, dir den erzeugten Assemblercode der Funktion 
anzusehen (du könntest erschrecken was er alles macht), schliesslich ist 
der Padauk fast ein PIC und genau so ungeeignet für C.

von Ralph S. (jjflash)


Lesenswert?

MaWin schrieb:
> Keine Möglichkeit, dir den erzeugten Assemblercode der Funktion
> anzusehen

ich habe mir ihn angesehen...

MaWin schrieb:
> der Padauk fast ein PIC und genau so ungeeignet für C.

Das würde ich so nicht unterschreiben. Allerdings hat auch niemand 
gesagt dass dieses ein "komfortabler" Controller ist und ich kenne deine 
Abneigung den Padauk mittels C programmieren zu wollen (genau so wie du 
abgeneigt bist, die kleinen PIC in C coden zu wollen).

Hier geht es mir auch nicht darum den in Assembler programmieren zu 
wollen (das Programm das mir vorschwebt funktioniert in Assembler 
schon), es geht mir darum, ein kleines Framework für den Padauk in C zu 
machen, egal ob das für jemanden Sinn macht oder nicht und für mich 
auszuloten, was in C machbar ist und was nicht.

Kleinere Dinge die in C machbar sind, werde ich hier dann sicher nicht 
in Assembler erledigen, schlicht deshalb, weil sie schneller erledigt 
sind.

Ich mag hier auch garantiert nicht eine Diskussion C vs. Assembler 
aufmachen wie sie hier schon einmal stattgefunden hat, sondern es ging 
mir schlichtweg darum, wie ich in C RAM-Speicher sparen kann, vor allem 
in Verbindung mit dem SDCC (den ich gut finde und ich froh bin, dass es 
diesen gibt).

Wenn ich in C keine Lösungen für mich finde, werde ich bestimmte Dinge 
mit dem Padauk in C eben nicht machen.

Hier ging es vor allem darum, warum für eine Parameterübergabe eines 
16-Bit Integers 8 Byte RAM benötigt werden, in einer anderen Funktion, 
die einem Int-Array einen Wert beschreibt sogar 32 Byte belegt werden 
(was für mich eben deshalb tragisch ist, weil der Controller nur 128 
Byte Ram hat).

Im Übrigen gilt für mich: erlaubt ist, was funktioniert (was heißt, dass 
ich in meinem Falle wohl mit globalen Variablen arbeiten werde und die 
Programmfunktionen in eine *.h *.c Kombination stecke in der die 
globalen Variable nicht "öffentlich" gemacht werden. Schön ist zwar 
anderst, aber so funktioniert es dann eben.

-----------------------------

By the way: das momentane "Projekt" erstellt aus dem Padauk ein kleines 
UKW-Radio mit RDA5807 Chip und Software I2C. Das Radio ist schon 
ansprechbar und ich kann einen Sender und eine Lautstärke schon fest 
einstellen. Das ganze soll mit 3 Tasten gesteuert werden und als Anzeige 
fungieren 20 LED's als Leuchtband, die mittels Charlieplexing 
angesprochen werden. Charlieplexing funktioniert auch, nur geht mir eben 
in Kombination von allem genau der RAM aus (und im konkreten Falle um 
genau 27 Byte).

Funktionsfähige Teile in C mittels Padauk sind:

- Nutzung 16-Bit Timer als Reload-Overflow
- einfacher Notenparser, gespeichert in einem String, der diese mittels 
Rechteckfrequenzen abspielen kann (im Stile einfacher Melodiegrußkarten)
- serielle Schnittstelle mit uart_putchar UND uart_getchar
- eigenem abgespecktem printf (logischerweise OHNE float-Unterstützung)
- I2C
- serielle Schieberegister (74HC595 / HEF 4094)
- generellen Abstraktionslayer für die GPIO Pins

Und das alles, damit man eben auf die Schnelle ein Progrämmchen bei 
Bedarf auf dem Padauk "hinrotzen" kann.

Ob das alles einen Sinn macht ist hier nicht die Frage (denn das ist es 
bei einem Hobby sicher nie), für mich ist das einfach faszinierend dass 
ein derart billiger Controller die Syntax von C verstehen kann, selbst 
dann, wenn der Code nicht sooooooo zwingend effizient ist.

So kann ich, zumindest bei Verwendung von Bitbanging, zwischen den 
einzelnen Controllern hin und her springen wie ich das mag.

von MaWin (Gast)


Lesenswert?

Ralph S. schrieb:
> ich habe mir ihn angesehen...

Na dann müsstest du doch jedes verwendete Datenbyte sehen.

Nein, ich programmiere gerne in C, finde aber schon den code den GCC für 
den AVR erzeugt grausam.

von W.S. (Gast)


Lesenswert?

Ralph S. schrieb:
> Ich mag hier auch garantiert nicht eine Diskussion C vs. Assembler
> aufmachen wie sie hier schon einmal stattgefunden hat, sondern es ging
> mir schlichtweg darum, wie ich in C RAM-Speicher sparen kann, vor allem
> in Verbindung mit dem SDCC (den ich gut finde und ich froh bin, dass es
> diesen gibt).
>
> Wenn ich in C keine Lösungen für mich finde, werde ich bestimmte Dinge
> mit dem Padauk in C eben nicht machen.

Ralph S. schrieb:
> Wenn ich mein Programm nur mit globalen Variablen schreibe funktioniert
> das Programm aber es ist natürlich höchst unschön (und ich will das
> eigentlich nicht mit mehr globalen Variablen machen als notwendig).

Ich kann deine Herangehensweise nicht wirklich verstehen. Diese Padauk's 
sin wirklich KLEINE Plattformen, da sollte man bereit sein, deren 
begrenzte Ressourcen sinnvoll zu verwenden und eben nicht hochtrabend 
irgendwelche C-Programmierer-Regeln als wichtiger zu erachten als die 
Plattform, die man zu programmieren gedenkt.

Also, es ist absolut NICHT "höchst unschön", auf dieser Plattform 
vornehmlich oder gar nur mit globalen Variablen zu arbeiten. Das ist 
die platzsparendste Version von allen. Und wenn es damit funktioniert, 
wie du ja schriebest, dann ist aus meiner Sicht die Sache final 
erledigt.

Bedenke mal, daß du auf diesen µC eben recht wenig RAM hast. Also 
überlege es dir gut, WAS du mit den Dingern anstellen willst - denn wenn 
du partout und NUR in C programmieren willst, dann kriegst du eben nicht 
anähernd soviel dort hinein, wie das in Assembler (und eigenem Können) 
möglich wäre. Dann bleibt dir nur eines: einen größeren Chip nehmen.

Ich für meinen Teil kenne das alles in- und auswendig, schließlich 
benutze ich schon fast 30 Jahre lang PIC's - die ich jedoch in Assembler 
programmiere. Muß man eben wollen und können.

Nun hat Padauk seine Chips zwar bei den PIC's abgeguckt, aber eben 
zwecks Kostenminimierung umgemodelt: Peripherie abgespeckt, das Meiste 
davon braucht man bei den angedachten Einsatzzwecken (Flackerkerzen, 
piepsende Grußpostkarten, billigster Schnickschnack aller Art) sowieso 
nicht, dafür die innere Struktur in Richtung C getrimmt (Stack in den 
RAM, ADD/SUB mit Carry und so weiter). Das hatte dann Konsequenzen für 
die Hardwareregister, die zwecks Freimachen von RAM in ein Extrasegment 
IO verlagert werden mußten, das wiederum machte spezielle 
Zugriffstbefehle notwendig und so weiter. Dazu dann eine Mini-IDE für 
das Programmieren in einem etwas abgespeckten C - das hatte triftige 
Gründe.

Diese Padauk-Chips sind in ihrer Art tatsächlich sehr konsequent auf das 
Billigst-Segment getrimmt: nicht nur der Chip und die Funktionalität 
darauf sind dafür optimiert, sondern auch die Programmierung: Leute, die 
nur etwas C können und sonst nix anderes, gibt es wie Sand am Meer - und 
sie sind billige Arbeitskräfte. Gute Assemblerprogrammierer sind 
hingegen eher rar. Wenn also eine Firma Billigs-Schnickschnack damit 
bauen will, dann dürfen die Programmierer auch nicht viel kosten.

Wenn man sich das alles mal durch den Kopf gehen läßt, dann kann man zu 
Padauk nur "Chapeau!" sagen. Sie haben das alles konsequent und richtig 
durchgezogen.

Und jetzt kommen Leute wie du und wollen mit dem SDCC dort hineinbrummen 
und dabei ihre gelernten Prämissen aufrecht erhalten wie z.B. deine 
Bemerkung über globale Variablen. Wenn das Boot und der Teich zum drauf 
schwimmen nicht zueinander passen - was ist dann daran als falsch zu 
bemängeln?

W.S.

von Kuddel (Gast)


Lesenswert?

W.S. schrieb:

Du hast den Deppen-Apostroph gut drauf. Dafür ist dein Beitrag 
ziemlicher Mist.

von Harald (Gast)


Lesenswert?

Kuddel schrieb:
> W.S. schrieb:
>
> Du hast den Deppen-Apostroph gut drauf. Dafür ist dein Beitrag
> ziemlicher Mist.

Weiß nicht, warum man da jetzt mit dem Deppen-Apostroph-Kram 
polemisieren muss, ich fand den Betrag von W.S. sehr gut und treffend. 
Solche Einschränkungen gab es bei den PIC12-Compilern von CSS vor 15 
Jahren auch. Man war doch froh, dass es überhaupt C für die Dinger gab, 
der Code sah ganz gut aus und konnte mit den Einschränkungen leben.

von Mw E. (Firma: fritzler-avr.de) (fritzler)


Lesenswert?

Der W.S. Betrag ließt sich wie moby "ASM über alles"

von MaWin (Gast)


Lesenswert?

Kuddel schrieb:
> Du hast den Deppen-Apostroph gut drauf. Dafür ist dein Beitrag
> ziemlicher Mist.

Zumindest beweist du, dass du nichts von ihm verstanden hast.

von Harald (Gast)


Lesenswert?

Mw E. schrieb:
> Der W.S. Betrag ließt sich wie moby "ASM über alles"

Lies es nochmal durch bitte.

von Mw E. (Firma: fritzler-avr.de) (fritzler)


Lesenswert?

Harald schrieb:
> Lies es nochmal durch bitte.

Hab ich genug.
Er hat ja schon im SDCC Padauk Thread sein Gift versprüht und es als 
"Hilfe" angeboten.

von Harald (Gast)


Lesenswert?

Aber wo liegt er denn falsch? Gut, den zweiten Teil mit den 
Programmierern hätte er weglassen können aber das hier ist ein Forum und 
kein Uploadportal für Dissertationen.

von Ralph S. (jjflash)


Lesenswert?

W.S. schrieb:
> Und jetzt kommen Leute wie du und wollen mit dem SDCC dort hineinbrummen
> und dabei ihre gelernten Prämissen aufrecht erhalten wie z.B. deine
> Bemerkung über globale Variablen.

... darum gehts doch gar nicht und gerlernt habe ich vor 40 Jahren auf 
einem 8080 in Maschinensprache, bei Controllern mit 8048 angefangen und 
wie viele dann auf MCS-51 ... natürlich alles in Assembler... und 
irgendwann einmal mußte ich dienstlich PIC16F84 verwenden (für einen 
Temperaturdatenlogger). Sogar Teile von PC Programmen hab ich in ASM 
gemacht (damals auch sogenannte TSR). Pascal, Delphi und C kamen erst 
sehr viel später. Von daher "denke" ich eher in Maschinensprache als in 
C, nur programmiere ich in Maschinensprache nur noch dann, wenn ich muß.

Summa summarum: es geht nicht darum, etwas partout in C machen zu wollen 
(beim Reload des 16-Bit Timers mußt du bspw. -noch- das Register mit 
Inline-ASM füttern weil SDCC momentan den Zugriff noch nicht für dieses 
einzige 16-Bit Register implementiert hat).

Es geht schlicht darum, etwas (für andere und mich) bereit zu stellen, 
mit dem schnelle Lösungen trotz dieser extrem dünnen Resourcen machbar 
sind. Das ganze bitte wieder verwendbar.

------------------------------------

Bei meinem ursprünglichen Problem hab ich mittlerweile 30 Byte RAM 
einsparen können (mit aus meiner Sicht der Dinge immer noch unschönem 
C), aber funktioniert, im Stile von (hinzuzulinkende C-Datei):
1
uint8_t aktvolume = 7;
2
uint8_t tmpvolume;
3
4
// überall im Programm kann die aktvolume geändert werden...
5
6
void setvolume(void)
7
{
8
  volume_register= aktvolume;
9
}
10
11
void scandown(void)
12
{
13
  tmpvolume= aktvolume;
14
  aktvolume= 0;          // Ton während Scan aus
15
  setvolume();
16
  // hier Sendersuchlauf
17
  aktvolume= tmpvolume;
18
  setvolume();
19
}

Das witzige hierbei ist, dass für einen solchigen Code Unmengen an 
Programmierer den Kopf schütteln werden, dass man das in C eben so nicht 
macht, sondern eben mit call by value oder call by reference. Beide 
Methoden verschlingen aber mehr Speicher, mit den globalen Variablen 
hier wurden in diesem Stile 12 Byte eingespart (normalerweise schüttelt 
man darüber den Kopf, weil 12 Byte nicht die Menge sind, aber wenn man 
insgesamt nur 128... ).

Das ganze kommt mir vom Stil dann auch eher in Richtung ASM vor, bei dem 
man vor einem Call ein Register oder eine Speicherstelle beschreibt und 
dann eben diese in der aufgerufenen Funktion auswertet.

Ich glaube, gerade W.S. ist der erste, wenn er solchen Code sieht, der 
als erster schreit, dass man das so nicht macht.

------------------------------------------------

Im Moment kämpfe ich jedoch mit anderen Dingen, bspw. warum ein 
read-modify-writeback auf die Register für die GPIO nicht so 
funktioniert wie ich das haben möchte.

Konfiguriere ich einen Portpin mittels:

PADIER |= 1 << bitnr;
PAC &= ~(1 << bitnr);

als Eingang, so wird mit dir Konifguration zerschossen, sobald ich auf 
Port A einen weiteren Pin als Ausgang verwenden möchte, so dass ich die 
Initialisierung vor dem Lesen eines Pins erneut durchführen muss.

Mir sind da einige Dinge eben noch suspekt (oder besser unklar) und 
suche hierfür eben den besten Weg.

von Ralph S. (jjflash)


Lesenswert?

... und an W.S. noch einmal:

Ja, ich habe in grauer Vorzeit einmal, mit PIC16F84 eine Berechnung mit 
natürlichem Logarithmus in Assembler machen müssen bei gleichzeitiger 
Aufaddierung der auf das Minigerätchen eingewirkten Wärmemenge...

Sowas will ich nie wieder machen müssen, in meiner Erinnerung war dieses 
die scheuslichste Programmierarbeit, die ich je gemacht habe.

von Olaf (Gast)


Lesenswert?

> Sowas will ich nie wieder machen müssen, in meiner Erinnerung war dieses
> die scheuslichste Programmierarbeit, die ich je gemacht habe.

Die Einstellung Teile ich zwar nicht so ganz, kann sie aber immerhin 
nachvollziehen. Was ich aber nicht verstehe warum man sich dann privat 
mit so einem Mickercontroller mit OTP abgibt. Als Firma die dann 
1Million davon kauft kann ich das verstehen, aber privat gibt man einmal 
1Euro mehr aus und hat danach eine sehr viel spassigeres leben.
Was WS geschrieben hat stimmt schon..

Olaf

von Ralph S. (jjflash)


Lesenswert?

Olaf schrieb:
> mit so einem Mickercontroller mit OTP abgibt.

Der PFS154 ist kein OTP!

von Peter D. (peda)


Lesenswert?

Ralph S. schrieb:
> (weil ich noch absoluter Newbie im
> Umgang mit PADAUK in Verbindung mit SDCC bin)

Dann ist es natürlich besonders "klug", einen MC zu nehmen, der nur 
wenige Ressourcen hat und den nur sehr wenige kennen.
Keiner, der bisher geantwortet hat (mich eingeschlossen), kennt diesen 
Chip.
Man kann sich das Leben auch künstlich schwer machen. Viel Spaß dabei.
Wie ja schon gesagt wurde, sollte aus dem Assemblerlisting hervorgehen, 
wofür der RAM genau benutzt wird.

Wenn ich Hilfe bräuchte, würde ich MCs nehmen, die weit verbreitet und 
gut in C programmierbar sind, z.B. AVR oder 8051.

: Bearbeitet durch User
von Harald (Gast)


Lesenswert?

Peter D. schrieb:
> Dann ist es natürlich besonders "klug", einen MC zu nehmen, der nur
> wenige Ressourcen hat und den nur sehr wenige kennen.

Er schreibt aber doch, dass er 40 Jahre Programmiererfahrung hat. Wenn 
er jetzt mal was mit Padauk machen will ist er ja automatisch am Anfang 
Newbie. Oder wie machst Du das?

von Chris (Gast)


Lesenswert?

Wenn dein Programm C8x conform ist, dann kann ich dies mal durch den 
smallC durchlaufen lassen und dir den Ressourcenverbrauch auf Padauk 
mitteilen, ist aber kein vollwertiger C wie sdcc.

von Peter D. (peda)


Lesenswert?

Harald schrieb:
> Oder wie machst Du das?

Ich habe ja noch nicht mal die MCs ausgeschöpft, die ich kenne. Daher 
habe ich keinerlei Bedarf nach weiteren 8-Bittern.
Man will sich ja nicht rückentwickeln, sondern weiter entwickeln. D.h. 
irgendwas machen, was die bisherigen Chips noch nicht oder nur sehr 
umständlich können.
Man kauft sich ja auch nicht das neue Auto schlechter als das alte.

von Peter D. (peda)


Lesenswert?

Ralph S. schrieb:
> Das witzige hierbei ist, dass für einen solchigen Code Unmengen an
> Programmierer den Kopf schütteln werden, dass man das in C eben so nicht
> macht

D.h. als abschreckendes Beispiel, diesen MC lieber nicht zu nehmen.
Gut zu wissen.

von Harald (Gast)


Lesenswert?

Peter D. schrieb:
> Ralph S. schrieb:
>> Das witzige hierbei ist, dass für einen solchigen Code Unmengen an
>> Programmierer den Kopf schütteln werden, dass man das in C eben so nicht
>> macht
>
> D.h. als abschreckendes Beispiel, diesen MC lieber nicht zu nehmen.
> Gut zu wissen.

Also ich finde die auch interessant (aber nur um zu sehen, was man auch 
einem 3ct Controller so rausholen kann). Du musst den ja nicht nehmen. 
Aber dürfen andere das dann auch nicht bzw. hier Fragen stellen?

von W.S. (Gast)


Lesenswert?

Ralph S. schrieb:
> Von daher "denke" ich eher in Maschinensprache als in
> C, nur programmiere ich in Maschinensprache nur noch dann, wenn ich muß.
>
> Summa summarum: es geht nicht darum, etwas partout in C machen zu wollen

Also erstens sind wir uns nach deinen Worten dann doch ähnlicher, als 
angenommen und zweitens frag ich mich, was dann deine Worte

Ralph S. schrieb:
> Wenn ich in C keine Lösungen für mich finde, werde ich bestimmte Dinge
> mit dem Padauk in C eben nicht machen.

bedeuten sollen. Ich lese das so: "entweder geht der Chip in C zu 
programmieren oder ich will ihn nicht benutzen."

Und obendrein hast du ja geschrieben, daß deine Firmware funktioniert 
und reinpaßt, wenn du die Variablen alle global machst. Da ist das 
Problem doch erledigt, also wozu dann all die Aufregung?

Ist es dir wichtiger, globale Variablen zu vermeiden und stattdessen mit 
einem Haufen an Funktionsargumenten zu arbeiten oder gar 'static' zu 
benutzen, als die Grenzen des vorliegenden Chips zu beachten? Siehe: 
"Wenn ich mein Programm nur mit globalen Variablen schreibe funktioniert 
das Programm aber es ist natürlich höchst unschön" Ich würde da aber 
ganz schnell meine Prioritäten neu ordnen. Und ich finde globale 
Variablen durchaus nicht höchst unschön. Wer lehrt die Leute denn sowas?


Nochwas:
Ich hab jetzt nicht all die HW-Register dieser Chips auswendig gelernt, 
aber wenn ich mal ganz kühn von den PIC auf die Padauk schließe, dann 
kommt mir deine Quelle etwas verschwenderisch vor. Ich mach da mal ein 
paar Anmerkungen:
1
uint8_t aktvolume = 7; // wozu überhaupt eine Variable erzeugen?
2
uint8_t tmpvolume;     // dito
3
4
// wozu diese Funktion überhaupt schreiben? 
5
// so wie es aussieht, hält 'volume_register' den Volumewert
6
// ja ohnehin. Man kann das (sehr wahrscheinlich) als normale
7
// Variable benutzen.
8
void setvolume(void)
9
{
10
  volume_register= aktvolume;
11
}
12
// wäre wohl eher als Inline machbar, etwa so:
13
inline void setvolume(unsigned char w)
14
{ volume_register=w; }
15
16
17
18
// ohne inneren Funktionsaufruf
19
// dafür aber mit einer Variablen auf dem Stack
20
void scandown(void)
21
{ unsigned char tmp;    // hier mal lokal
22
23
  tmp= volume_register;
24
  volume_register= 0;          // Ton während Scan aus
25
  // hier Sendersuchlauf
26
  volume_register= tmp;
27
}
28
29
// Alternativlösung mit einer Universal-Temporär-Variablen, die
30
// man an anderen Stellen eben auch benutzt. Das braucht Obacht, 
31
// daß man die nicht gedankenlos mehrfach geschachtelt benutzt
32
33
unsigned char temphudel;       // quasi Mädchen für alles
34
35
void scandown(void)
36
{ temphudel= volume_register;
37
  volume_register= 0;          // Ton während Scan aus
38
  // hier Sendersuchlauf
39
  volume_register= temphudel;
40
}

Ich sag's mal so: Die Gepflogenheiten auf dem PC sind das eine, das 
Bedenken der Eigenheiten solcher kleinen µC's sind etwas ganz anderes. 
Gepflogenheiten kann man ändern oder mal auslassen, eine vorliegende 
Plattform kann man hingegen nicht ändern.

W.S.

von Peter D. (peda)


Lesenswert?

Harald schrieb:
> Aber dürfen andere das dann auch nicht bzw. hier Fragen stellen?

Ich wollte nur darauf hinweisen, daß man sich dann nicht über das 
Ausbleiben von zielführenden Antworten wundern sollte.
Mehr nicht.

von W.S. (Gast)


Lesenswert?

Ralph S. schrieb:
> Ja, ich habe in grauer Vorzeit einmal, mit PIC16F84 eine Berechnung mit
> natürlichem Logarithmus in Assembler machen müssen bei gleichzeitiger
> Aufaddierung der auf das Minigerätchen eingewirkten Wärmemenge...
>
> Sowas will ich nie wieder machen müssen, in meiner Erinnerung war dieses
> die scheuslichste Programmierarbeit, die ich je gemacht habe.

Tja, da sind wir uns dann doch SEHR unähnlich:

Ich hatte damals (Anfang der 90er) von Microchip nur den PICALC als 
Assembler. OK, das war ein eher scheußliches Tool. Also hatte ich mir 
kurzerhand meinen Assembler für die PIC's selber geschrieben.

Und da ich auch für meßtechnische Zwecke Gleitkomma brauche, hab ich mir 
auch mein Gleitkommapaket für diese PIC selbe geschrieben. Später hab 
ich das auf 32 Bit Mantisse umgeschrieben, weil ich für meinen 
Taschen-Frequenzzähler mehr als nur 24 Bit Mantisse brauchte. Ich kann 
sowas und wenn ich es brauche, schreibe ich mir das eben selber, wenn 
mir das Vorhandene nicht gefällt.

Die ganze Architektur der PIC ist für Assembler gemacht und ich finde, 
sie hat in diesem Punkte eine Eleganz, die man bei stupiden 
Load-Modify-Store Architekturen eben nicht hat. Ich mag das und du hast 
dich offensichtlich innerlich dagegen gesträubt. Tja, kann man nix 
machen.

W.S.

von MaWin (Gast)


Lesenswert?

Peter D. schrieb:
> Man will sich ja nicht rückentwickeln, sondern weiter entwickeln. D.h.
> irgendwas machen, was die bisherigen Chips noch nicht oder nur sehr
> umständlich können.
> Man kauft sich ja auch nicht das neue Auto schlechter als das alte.

Bla Bla  natürlich.

Manche brauchen wenn sie älter werden keine Schwanzverlängerung mehr, 
sondern sind mit dem Kleinwagen zufrieden.

Und andere finden es interessant was man mit kleinen billigen uC machen 
kann während andere den rPi einsetzen.

Lass ihn also machen. Warum er sich aber verweigert, den 
compilererzeugten Assemblercode anzusehen, weiss ich auch nicht, 
ebensowenig wie ich wüsste was an einer handvoll globaler Variablen 
schlecht ist.

von W.S. (Gast)


Lesenswert?

Peter D. schrieb:
> Keiner, der bisher geantwortet hat (mich eingeschlossen), kennt diesen
> Chip.

Peter, sieh das mal etwas genereller. Wir hatten vor Jahren das große 
Plattform-Sterben, weil die Cortexe so ziemlich alles Andere 
plattgemacht hatten. Keine NEC, keine Fujitsu, keine Mitsubishi, keine 
Hitachi, keine Mips in ESS-Chips mehr.

Ich finde das überhaupt nicht gut, denn ich weiß, daß Monokulturen immer 
auf lange Sicht etwas übles sind. Und genau aus DIESEM Grunde finde ich 
im Prinzip das Auftauchen dieser kleinen billigen Chips durchaus 
begrüßenswert.

Das könnte eine Bereicherung des Marktes sein. Allerdings gibt es ernste 
Widerhaken dabei: der Hersteller hat zwar die Assembler-Mnemonics 
veröffentlicht, die jeweiligen Maschinencodes jedoch nicht. Er hat auch 
nicht die Programmieralgorithmen für die Chips veröffentlicht.

Das ist ein wirklich ERNSTER Grund, die Finger davon zu lassen.

Nun haben einige Enthusiasten auf eigene Faust dies herausbaldowert, was 
an sich lobenswert ist, aber es fehlt noch immer eine Dokumentation all 
dessen, was da herausgefunden wurde. Stattdessen gibt es einiges an über 
die Zeit angehäuften Unterlagen unterschiedlichen Erkenntnisstandes, 
dito Quellen, dito Fragmenten, was aber salopp gesagt alles nur 
dahingerotzt ist.

Es gibt auch einen Programmierdongle dafür, der in Serie produziert 
wird, als ich das letzte Mal dort reingeschaut hatte, war grad die 2. 
Charge in Produktion. Aber auch dort sind zwar Quellen und Schaltung per 
Git veröffentlicht (die Quellen durchaus professionell geschrieben), 
jedoch wiederum völlig kommentarlos und ohne Dokumentation. Ist fast wie 
bei einem obfuscated Java-Modul. Das ist dann ebenso wenig der 
Verbreitung förderlich wie das Benehmen des Herstellers.

Ich kann verstehen, daß die Jagd nach dem, was der Hersteller 
verschweigt, für interessierte Programmierer sehr reizvoll ist. Ich kann 
es auch verstehen, wenn Leute aus der Verschwiegenheit des Herstellers 
ein Geschäft machen und Programmiertools dafür verkaufen wollen und 
deshalb nicht interessiert sind, die Essentials dediziert zu 
dokumentieren.

Ja, es gibt da einiges außerhalb von Padauk, aber das heißt noch lange 
nicht, daß das ein Beitrag zur Beförderung der Popularität dieser Chips 
ist. Und wenn sich da im Verständnis der Beteiligten nichts ändert, dann 
bleibt das Ganze eben nur eine Rand-Episode.

Ich selbst hatte durchaus mit dem Gedanken gespielt, meine GK-Lib auf 
die Padauk's umzusetzen, damit man dort auch mal kleinere Meßgeräte etc. 
machen kann. Aber ich mache sowas nicht, ohne zuvor eine ordentliche 
Dokumentation des Pferdes zu haben, das da geritten werden soll.

W.S.

von Olaf (Gast)


Lesenswert?

> Also ich finde die auch interessant (aber nur um zu sehen, was man auch
> einem 3ct Controller so rausholen kann). Du musst den ja nicht nehmen.

Also so wie GO auf einem 6x6 Feld zu spielen? :-)

Ich kann ja verstehen das sich arme Schweine damit beschaeftigen muessen 
welche die blinkenen Weihnachtbaeume fuer die Grabbelkiste bei Aldi 
entwickeln muessen und wenn mich mein Chef mit Geld bewirft damit ich 
meine Zeit damit vertute auch okay. Aber wieso ich meine Freizeit mit so 
einem ollen Kram vertueddeln soll ist mir ein Raetzel.

Olaf

von H. (Gast)


Lesenswert?

Olaf schrieb:
> ist mir ein Raetzel.

Glaube ich gerne!

von MaWin (Gast)


Lesenswert?

Olaf schrieb:
> Ich kann ja verstehen das sich arme Schweine damit beschaeftigen muessen
> welche die blinkenen Weihnachtbaeume fuer die Grabbelkiste bei Aldi
> entwickeln muessen und wenn mich mein Chef mit Geld bewirft damit ich
> meine Zeit damit vertute auch okay. Aber wieso ich meine Freizeit mit so
> einem ollen Kram vertueddeln soll ist mir ein Raetzel

Tja, warum beschäftigen sich Leute überhaupt mit Mikrocontrollern, wo es 
doch so schöne Supercomputer gibt die in der Cloud alles viel besser und 
schneller berechnen, mit einfachster "1 Klick Homepage Generator" 
Programmierung.

Ich glaube, du verstehst eh eher wenig von der Welt.

von Tim  . (cpldcpu)


Lesenswert?

> Konfiguriere ich einen Portpin mittels:
>
> PADIER |= 1 << bitnr;
> PAC &= ~(1 << bitnr);
>
> als Eingang, so wird mit dir Konifguration zerschossen, sobald ich auf
> Port A einen weiteren Pin als Ausgang verwenden möchte, so dass ich die
> Initialisierung vor dem Lesen eines Pins erneut durchführen muss.

Daraus sollte SDCC eigentlich SET1 / SET0-Befehle generieren. Hast Du 
Dir das Listing schon einmal angschaut?

von W.S. (Gast)


Lesenswert?

Tim  . schrieb:
>> PADIER |= 1 << bitnr;
>> PAC &= ~(1 << bitnr);
>....
> Daraus sollte SDCC eigentlich SET1 / SET0-Befehle generieren.

Das ist ja eben eines der vielen traurigen Details bei solchen Chips: 
sowas wie C kann eben nicht den Möglichkeiten des Chips entsprechen.

Weitaus angenehmer wäre es, wenn man solche Bits tatsächlich als Boolean 
Variablen deklarieren könnte und dann

MeinPadier=false;

schreiben könnte. Im Maschinenbefehl sind ja beide Dinge drin: 
Byteadresse und Bitnummer, das macht zusammen ne Bitadresse.

W.S.

von Tim  . (cpldcpu)


Lesenswert?

W.S. schrieb:
> Weitaus angenehmer wäre es, wenn man solche Bits tatsächlich als Boolean
> Variablen deklarieren könnte und dann
>
> MeinPadier=false;
>
> schreiben könnte. Im Maschinenbefehl sind ja beide Dinge drin:
> Byteadresse und Bitnummer, das macht zusammen ne Bitadresse.

So etwas erlaubt C ja auch mit bitfield-structs. Funktioniert aktuell im 
SDCC mit dem Padauk aber noch nicht.

https://sourceforge.net/p/sdcc/bugs/3070/

von Ralph S. (jjflash)


Lesenswert?

MaWin schrieb:
> Warum er sich aber verweigert, den
> compilererzeugten Assemblercode anzusehen, weiss ich auch nicht,

Heeey, ich hatte oben schon geschrieben gehabt, dass ich das gemacht 
habe ... und auch die Stellen gefunden, wo optimiert werden konnte und 
auch Teile, wie W.S. das beschrieben hatte, Teile davon dann als Inline 
gemacht.

Insgesamt wurden 30 Byte eingespart.

By the way: Das Radio mit PFS150 und RDA5807 funktionert jetzt mit 
aktivierbarem Sendersuchlauf und einstellbare Lautstärke sehr gut.

Tim  . schrieb:
>> Konfiguriere ich einen Portpin mittels:
>>
>> PADIER |= 1 << bitnr;
>> PAC &= ~(1 << bitnr);
>>
>> als Eingang, so wird mit dir Konifguration zerschossen, sobald ich auf
>> Port A einen weiteren Pin als Ausgang verwenden möchte, so dass ich die
>> Initialisierung vor dem Lesen eines Pins erneut durchführen muss.
>
> Daraus sollte SDCC eigentlich SET1 / SET0-Befehle generieren. Hast Du
> Dir das Listing schon einmal angschaut?

Hab ich gemacht und er macht etwas anderes als "erwartet". Allerdings 
bin ich mit noch nicht ganz sicher ob ich nicht irgendwo einen Bug in 
meinen Macros eingebaut habe, als Abstraktionsschicht sind bei mir für 
PAC  PBC und PADIER  PBDIER diese zusammengefasst im Stile von
1
#define mask1   (1 << 1)
2
#define mask2   (1 << 2)
3
4
#define PA1_output_init()  (PAC |= mask1)
5
#define PA1_set()          (PA |= mask1)
6
#define PA1_clr()          (PA &= ~mask1)
7
8
// Input mit eingeschalteten Pull-Up Widerstaenden
9
#define PA2_input_init()   { PAC &= ~(mask2); PADIER |= mask2; PAPH |= maske; }       
10
#define is_PA2()            (PA & mask2)

Wie gesagt, ich schau es mir noch einmal genauer an und wenn das nicht 
klappt, werde ich einen Weg über Inline Assembler finden. Wenn der 
Fehler nicht bei mir liegt, werde ich diesbezüglich mich noch einmal 
melden.

---------------------------------------------

Olaf schrieb:
> Aber wieso ich meine Freizeit mit so
> einem ollen Kram vertueddeln soll ist mir ein Raetzel.

... einfach weil das Spaß macht (vllt. bin ich ja auch massochistisch 
veranlagt und weiß das noch nicht). Der Reiz hier ist dann tatsächlich: 
Geiz ist geil und "mal sehen mit wie wenig man auskommen kann".

Die Bauteile des Radios kosten (ohne PCB) im Moment (inkl. der 
Widerstände, Kondensatoren, LED's und Uhrenquarz) 42 Cent.

So etwas reizt mich einfach ohne einen großen Sinn zu machen.

von Harald (Gast)


Lesenswert?

Mich würde mal interessieren was dein RDA5807 Radio so kann. Magst Du 
das verraten? Danke!

von Ralph S. (jjflash)


Lesenswert?

... ich werde die Tage den Code einstellen und ein Foto vom Steckbrett, 
wenn es sauberer gesteckt ist.

Das Radio kann UKW Radioempfänger empfangen :-) :-) :-)

Grundsätzlich ist das Radio in der Qualität ja abhängig vom RDA5807, der 
ist hier auch schon hinlänglich besprochen worden.

Für mich ging es darum, das von meinen STM8 und AVR-Versionen auf den 
Padauk zu portieren.

Der RDA5807 ist eigentlich schon kein "Chip" mehr, er benötigt lediglich 
einen Uhrenquarz um zu funktionieren und die Steuersignale mittels I2C. 
Ursprünglich wollte ich dem Teil noch eine 20 Digit 
LED-Leuchtbandanzeige mittels Charlieplexing geben, aber das hatte im 
ursprünglichen Entwurf wegen des RAM-Mangels nicht geklappt gehabt 
(sollte jetzt zwar realisierbar sein, aber die Motivation ist jetzt 
nicht mehr so groß).

Das Radio hat 8 LED als Leuchtbandanzeige auf der am linken Rand das 
untere Ende des Empfangbereichs (88 MHz) und am rechten Rand das oberen 
Ende (107 MHz) angezeigt wird (oder je nach eingestelltem Sender dann 
dazwischen) und eine LED zur Anzeige, welcher Modus aktiv ist.

Das Radio hat 3 Tasten: "MODE" "<<" und ">>".

Mit MODE kann zwischen Sendersuchlauf und Lautstärkeeinstellung 
getoggelt werden (Modus-LED an = Lautstärkeeinstellung).

Taste auf "<<" verringert die Lautstärke, ">>" erhöht sie. Es gibt 16 
Lautstärkestufen und die eingestellte Lautstärke wird auf den LED's als 
Leuchtband angezeigt.

Im Modus Sendersuchlauf bewirkt ein Druck auf "<<" einen Suchlauf in 
Richtung unteres Frequenzband. Während der Suche blinkt die Modus-LED.
Ein Druck auf ">>" startet einen Suchlauf in Richtung oberes Ende des 
Frequenzbandes.

Am Ausgang des Empfängerchips (RDA5807) ist ein kleiner 
Brückenverstärker HXJ8002 / FM8002 mit Vdd= +5V angeschlossen der lt. 
Datenblatt eine Leistung von 1 W true rms haben soll (zumindest dürfte 
die Kühlung auf meinen Adapterplatinen nicht ausreichend genug sein).

Ein sehr einfaches, aber normales Radio eben.

Das Radio ist für mich als solches abgeschlossen, als nächstes steht die 
Fehlersuche bei evtl. Bugs der GPIO Anschlüsse an und parallel dazu 
werde ich mich ab morgen mit dem integrierten Komparator beschäftigen um 
damit einen "Software-ADC" wie das Atmel seiner Zeit für einen 
ATtiny2313 vorgeschlagen hatte (hmmm, sind diese alten App-Notes noch 
irgendwo verfügbar, ich finde diese nicht auf der microchip Seite).

Im Endeffekt wird dann daraus evtl. ein VU-Meter wie das hier im Forum 
mit einem ATtiny13 vorgestellt wurde:

Beitrag "VU-Meter mit Attiny13a statt LM3916"

von Harald (Gast)


Lesenswert?

Okay, vielen Dank für die ausführliche Beschreibung! Das mit der 
Leuchtbandanzeige ist ja ganz fein! Ich will Dir den Mut nicht nehmen, 
aber wusstest Du von der RDA5807FP Variante, da kann man Sender- und 
Lautstärketasten direkt anschließen, also komplett ohne uC. Dann 
natürlich auch keine Leuchtbandanzeige. FP gibt es meines Wissens nur im 
SO16 Package.

von Ralph S. (jjflash)


Lesenswert?

Harald schrieb:
> aber wusstest Du von der RDA5807FP Variante, da kann man Sender- und
> Lautstärketasten direkt anschließen

kenne ich, auch wenn ich noch keinen in den Fingern gehabt habe. 
Grundsätzlich finde ich den (für mich) aber eher uninteressant, weil da 
dann nur grob die Originalapplikation nachgebaut wird.

Mit I2C Schnittstelle und anderem Controller als Padauk, kannst du dann 
eben die Anzeige verbessern (als Lehrprojekt hatte ich mal was gemacht 
gehabt mit SPI-Display und STM8, der dann eben auch freie Senderspeicher 
hatte und beim Wiedereinschalten den zuletzt eingestellten Sender und 
die Lautstärke restauriert hatte, außerdem war da zwischen Empfängerchip 
und Verstärker noch ein über den Controller einstellbares 
Klangregelnetzwerk (Bass / Höhe) drin, dass das ganze als Radio 
komfortabler macht. Bauteilekosten hier waren dann eher am Display fest 
zu machen als an der Kombination µC - RDA5807

von MaWin (Gast)


Lesenswert?

Harald schrieb:
> Das mit der Leuchtbandanzeige ist ja ganz fein!

Ich hätt' jetzt gesagt: wenn's LCD wäre, könnte man wenigstens 
Batteriebetrieb vorsehen.
Und die Frequenz als Zahl darstellen...

https://www.pollin.de/p/lcd-modul-tian-ma-a2c00096100-121581

von Philipp Klaus K. (pkk)


Lesenswert?

Ralph S. schrieb:
>
> Laut map-file des SDCC benötigt die Funktion für das Argument 8 Byte
> (Speicher von 0x3F bis 0x46 (inklusive):
>
> Listing map-File
> ----------------
>
>
1
> Area                                    Addr        Size        Decimal 
2
> Bytes (Attributes)
3
> --------------------------------        ----        ----        ------- 
4
> ----- ------------
5
> DATA                                00000002    00000065 =         101. 
6
> bytes (REL,CON)
7
> 
8
>       Value  Global                              Global Defined In 
9
> Module
10
>       -----  --------------------------------   ------------------------
11
>      00000002  _aktfreq                           rda5807_test
12
>      00000004  _aktvol                            rda5807_test
13
>      00000005  _rda5807_reg                       rda5807_test
14
>      00000025  _i2c_startaddr_b_PARM_1            rda5807_test
15
>      00000026  _i2c_startaddr_b_PARM_2            rda5807_test
16
>      00000027  _rda5807_writereg_PARM_1           rda5807_test
17
>      00000039  _rda5807_setfreq_PARM_1            rda5807_test
18
>      0000003F  _rda5807_setvol_PARM_1             rda5807_test
19
>      00000047  _setnewtune_PARM_1                 rda5807_test
20
>
>
> Warum ist das so?
>
> Interpretiere ich hier etwas falsch ? Ich hätte im besten Fall 4 Bytes
> vermutet, 2 für den Parameter und 2 für die Rücksprungadresse (wobei ich
> eigentlich annehme, dass eine Rücksprungadresse auf dem Stack liegt und
> hierfür nicht extra Ram reserviert wird).
>
> Interpretiere ich das falsch und es werden gar keine 8 Bytes reserviert
> und wenn ich das nicht falsch interpretiere wie kann ich Abhilfe
> schaffen?

In .map sind nicht alle Variablen aufgelistet, sondern nur solche, die 
auch einen Namen haben. Namenlose temporäre Variablen sind dort nur aus 
dem Eintrag zur Größe ersichtlich.
Aus der Größe der Lücke von _rda5807_setvol_PARM_1 bis zum nächsten 
Eintrag kann man also nicht die Größe von _rda5807_setvol_PARM_1 
erkennen.

Wenn es allzu knapp wird mit dem Speicher, wäre es naheliegend, einen µC 
mit mehr Speicher zu nehmen, z.b. den PFS173.

Philipp

von Philipp Klaus K. (pkk)


Lesenswert?

Tim  . schrieb:
> W.S. schrieb:
>> Weitaus angenehmer wäre es, wenn man solche Bits tatsächlich als Boolean
>> Variablen deklarieren könnte und dann
>>
>> MeinPadier=false;
>>
>> schreiben könnte. Im Maschinenbefehl sind ja beide Dinge drin:
>> Byteadresse und Bitnummer, das macht zusammen ne Bitadresse.
>
> So etwas erlaubt C ja auch mit bitfield-structs. Funktioniert aktuell im
> SDCC mit dem Padauk aber noch nicht.
>
> https://sourceforge.net/p/sdcc/bugs/3070/

Gewöhnliche C bitfields (also im normalen Speicher) gehen. Und dort sind 
sie nützlich, um RAM zu sparen, was ja gerade bei den kleinen Padauk-µC 
nützlich ist.

Was aber in SDCC noch nicht geht (und außerhalb des C-Standard liegt), 
sind bit-fields an I/O-Adressen (außer natürlich bei Architekturen mit 
I/O im normalen Adressraum, wie stm8).

Philipp

von Philipp Klaus K. (pkk)


Lesenswert?

Ralph S. schrieb:
> uint16_t rda5807_reg[16];
>
> ...
>
> void rda5807_setvol(uint16_t volume)
> {
>   rda5807_reg[5]=(rda5807_reg[5] & 0xFFF0) |  volume;
>   rda5807_writereg(5);
> }
> [/code]

Wenn ich das mit aktuellem SDCC kompiliere (unter der Annahme, dass 
rda5807_writereg ein void rda5807_writereg(uint_least8_t) ist), werden 
für diese Funktion 4 Bytes an RAM verwendet: 2 Byte für den Parameter, 2 
Byte für die temporären Variablen, die nicht in Registern abgelegt 
werden.

Das sollte sich das aber durch kleine Verbesserungen an SDCC auf 2 Byte 
reduzieren lassen (wozu alle temporären Variablen in Register müssten, 
und dann nur noch der Parameter RAM bräuchte). Wenn ich Zeit finde, 
werde ich mir das genauer anschauen.

Philipp

von Philipp Klaus K. (pkk)


Lesenswert?

Ralph S. schrieb:
> Vergessen habe:
>
> Compilerflags sind:
>
> --std-sdcc11 --opt-code-size
>
> Kann ich hier etwas ändern, Flashspeicher habe ich noch etwas

Reentrante Funktionen sind deutlich größer und langsamer, sparen aber 
RAM.

Einzelne Funktionen lassen sich per __reentrant reentrant machen, aber 
es gibt auch --stack-auto, um das global zu machen (allerdings braucht 
man bei --stack-auto auch eine mit --stack-auto kompilierte 
Standardbibliothek, was bei SDCC nicht für alle Ports mitgeliefert wird 
- bei den Padauk bisher nur für pdk15).

Philipp

von W.S. (Gast)


Lesenswert?

Philipp Klaus K. schrieb:
> wozu alle temporären Variablen in Register müssten,
> und dann nur noch der Parameter RAM bräuchte

Um das mal deutlich zu sagen: auf diesen Chips gibt es keine Register 
außer dem W (PIC) bzw. A (Padauk). Bei Padauk kommt für Argumente und 
lokale Variablen ansonsten nur noch der Stack in Frage, aber der geht ja 
ohnehin vom spärlichen RAM ab.

Das Grundprinzip dieser Architektur ist, daß man Operationen an 
Variablen direkt in der Variablen vornimmt. Es sind eben keine 
Load-Modify-Store Architekturen.

W.S.

von P.S. (Gast)


Lesenswert?

W.S. = Will stänkern?

von Philipp Klaus K. (pkk)


Lesenswert?

W.S. schrieb:
> Philipp Klaus K. schrieb:
>> wozu alle temporären Variablen in Register müssten,
>> und dann nur noch der Parameter RAM bräuchte
>
> Um das mal deutlich zu sagen: auf diesen Chips gibt es keine Register
> außer dem W (PIC) bzw. A (Padauk). Bei Padauk kommt für Argumente und
> lokale Variablen ansonsten nur noch der Stack in Frage, aber der geht ja
> ohnehin vom spärlichen RAM ab.
>
> Das Grundprinzip dieser Architektur ist, daß man Operationen an
> Variablen direkt in der Variablen vornimmt. Es sind eben keine
> Load-Modify-Store Architekturen.
>
> W.S.

SDCC verwendet das Byte an Adresse 0 als Pseudoregister P. Aus Sicht des 
Registerallokators gibt es damit zwei Register zu je einem Byte. Und im 
Falle der obigen Funktion sollte es durch leichte Verbesserungen an SDCC 
möglich sein, dass auch noch die letzte zur Zeit im RAM liegende 
16-Bit-Variable je zur Hälfte in A und P abgelegt wird.

Beim Stack sind hier zwei Aspekte zu bedenken: 1) es fehlt an 
effizienten Instruktionen für den Zugriff darauf, wodurch bei Verwendung 
des Stacks für Variablen der Code groß und langsam wird. 2) Variablen 
auf dem Stack lassen sich effizienter speichern, da 2a) nur die der 
gerade aufgerufenen Funktionen wirklich dort liegen und 2b) SDCC dort 
einen besseren Allokator verwendet.

Ein kurzer Überblick über die Padauk-µC als Zielarchitektur für C, und 
eine ein paar Daten, wieviel besser die Padauk wären, wenn man 
effizienter auf den Stack zugreifen könnte: 
https://arxiv.org/abs/2010.04633

Philipp

von Ralph S. (jjflash)


Lesenswert?

Philipp Klaus K. schrieb:
> Aus der Größe der Lücke von _rda5807_setvol_PARM_1 bis zum nächsten
> Eintrag kann man also nicht die Größe von _rda5807_setvol_PARM_1
> erkennen.

Das wußte ich nicht, vielen Dank für die Info.

Philipp Klaus K. schrieb:
> Wenn es allzu knapp wird mit dem Speicher, wäre es naheliegend, einen µC
> mit mehr Speicher zu nehmen, z.b. den PFS173.

Es geht ja mittlerweile auch mit dem PFS154, mit dem PFS173 ging es 
früher :-)

Philipp Klaus K. schrieb:
> Das sollte sich das aber durch kleine Verbesserungen an SDCC auf 2 Byte
> reduzieren lassen (wozu alle temporären Variablen in Register müssten,
> und dann nur noch der Parameter RAM bräuchte). Wenn ich Zeit finde,
> werde ich mir das genauer anschauen.

... das finde ich das Sensationelle am Forum und am SDCC-Team, dass sie 
sich solche Dinge dann tatsächlich anschauen, vielen Dank

von Philipp Klaus K. (pkk)


Lesenswert?

Ralph S. schrieb:
> Philipp Klaus K. schrieb:
>> Das sollte sich das aber durch kleine Verbesserungen an SDCC auf 2 Byte
>> reduzieren lassen (wozu alle temporären Variablen in Register müssten,
>> und dann nur noch der Parameter RAM bräuchte). Wenn ich Zeit finde,
>> werde ich mir das genauer anschauen.
>
> ... das finde ich das Sensationelle am Forum und am SDCC-Team, dass sie
> sich solche Dinge dann tatsächlich anschauen, vielen Dank

In SDCC 4.0.4 #11926 wird die Funktion nun zumindest auf meinem Debian 
GNU/Linux testing System keine temporären Variablen im RAM mehr, so dass 
nur noch die 2 Byte für den Parameter benötigt werden.

Philipp

von Ralph S. (jjflash)


Lesenswert?

VERRÜCKT !!!
-----------------------------------

Ich konnte zwar SDCC 4.0.4 #11926 nicht ausprobieren, weil als Snapshot 
auf http://sdcc.sourceforge.net/snap.php "nur" #11925 zum download 
liegt, aaaaaaaber das Ergebnis ist schon "krass":

Ein und dasselbe Programm (hier das Radio) mit beiden Versionen (4.0.3 
#11879 und 4.0.4 #11925) übersetzt:

----------------------------------------------------------------

SDCC 4.0.3 #11879

Area                                    Addr        Size        Decimal 
Bytes (Attributes)
--------------------------------        ----        ----        ------- 
----- ------------
DATA                                00000002    00000048 =          72. 
bytes (REL,CON)

Area                                    Addr        Size        Decimal 
Bytes (Attributes)
--------------------------------        ----        ----        ------- 
----- ------------
CODE                                00000046    0000084A =        2122. 
bytes (REL,CON)

Zu flashende Words im Hexfile sind: 1110

----------------------------------------------------------------

SDCC 4.0.4 #11925

Area                                    Addr        Size        Decimal 
Bytes (Attributes)
--------------------------------        ----        ----        ------- 
----- ------------
DATA                                00000002    00000036 =          54. 
bytes (REL,CON)

Area                                    Addr        Size        Decimal 
Bytes (Attributes)
--------------------------------        ----        ----        ------- 
----- ------------
CODE                                00000046    000007F4 =        2036. 
bytes (REL,CON)

Zu flashende Words im Hexfile sind: 1067

---------------------------------------------------------------

Das Einsparen von RAM-Speicher finde ich schon klasse (18 Bytes 
angesichts der Tatsache, dass man insgesamt nur 128 hat), dass dabei der 
Code dann auch noch um 43 Words kleiner geworden ist... Respekt.

Natürlich funktioniert die Firmware des Radios mit beiden Versionen 
übersetzt identisch.

Vielen Dank

von Philipp Klaus K. (pkk)


Lesenswert?

Ralph S. schrieb:
> Ich konnte zwar SDCC 4.0.4 #11926 nicht ausprobieren, weil als Snapshot
> auf http://sdcc.sourceforge.net/snap.php "nur" #11925 zum download
> liegt, aaaaaaaber das Ergebnis ist schon "krass":
>
> Ein und dasselbe Programm (hier das Radio) mit beiden Versionen (4.0.3
> #11879 und 4.0.4 #11925) übersetzt:

In 4.0.4 #11925 sind auch schon die meisten Verbesserungen enthalten 
(insbesondere die für & und |). 4.0.4 #11926 bringt demgegenüber nur 
Verbesserungen für ^ und einen Bugfix.

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.