Sitze hier mal wieder am Notebook und programmiere MSPg2211, da taucht
dieser seltsame Fehler auf:
"../lnk_msp430g2211.cmd", line 60: error: placement fails for object
".text",
size 0x810 (page 0). Available ranges:
FLASH size: 0x7e0 unused: 0x7e0 max hole: 0x7e0
error: errors encountered during linking; "AlarmClock.out" not built
Klingt fast als wäre mein Code zu lang. Er enthält einige recht lange
Funktionen zur Ansteuerung eines Schieberegisters, das Hauptprogramm ist
eher kurz:
1
voidmain(void)
2
{
3
longcounter=0;
4
shortzaehler=0;
5
6
WDTCTL=WDTPW|WDTHOLD;//Watchdog stoppen
7
P1DIR=BIT0|BIT1|BIT2;//Outputs setzen
8
while(1)
9
{
10
for(counter=0;counter<20000;counter++){}
11
writevalue(zaehler);
12
zaehler++;
13
if(zaehler==10)zaehler=0;
14
}
15
}
Besonders seltsam:
Zuvor hatte ich in der Main einfach nur die while schleife mit
writevalu(99) stehen. Da hat der Compiler noch nicht aufgemuckt. Nun
wollte ich die Zahlen auf der Anzeige mal durchlaufen lassen und dann
das.
Noch erwähnenswert:
-ich programmiere den µC mit dem Launchpad
-es ist reiner C-Code
-schreibe den Code mit Code Composer Studio. Die kostenlose Version hat
eine beschränkte Länge für den Code, glaub 16 KB?! Meine Quelldatei
selbst hat 9354 bytes
-in dem Projektordner fliegt noch viel Schrott rum, wo ich kein Bock hab
zu löschen. Ist aber natürlich alles "excluded from built"
Wildkatz schrieb:> Die kostenlose Version hat eine beschränkte Länge für den Code, glaub 16 KB?!> Meine Quelldatei selbst hat 9354 bytes
Der Compiler erzeugt nicht mehr als 16 kB Binärcode, wie groß der
Quelltext ist, hat damit nur sehr wenig zu tun.
Das Problem aber ist ein anderes: Der aus Deinem Programm erzeugte
Binärcode ist größer als der im µC zur Verfügung stehende Platz - das
Flash-ROM ist voll.
Anhand Deines Codeschnipselchens lässt sich natürlich nicht beurteilen,
was hier so viel Code erzeugt.
Deine Zählvariable "counter" ist vom Typ long, also 32 Bit groß. Der
MSP430 kann 32-Bit-Werte nicht direkt verarbeiten, also ist für
32-Bit-Berechnungen etwas mehr Programmcode erforderlich als für
16-Bit-Variablen. Das sind zwar nur eine Handvoll Bytes, aber das
läppert sich.
Wenn Du aber eh' nur bis 20000 zählst, gibt es überhaupt keinen Grund,
einen long einzusetzen, das passt auch in einen (16 Bit großen) int.
Danke für die Einschätzung.
Dann lag ich mit meiner Einschätzung ja gar nicht so falsch. Aber was
kann ich tun?! Ich hab hier noch mehr MSPs rumliegen, aber mehr als 1 KB
Flash hat keiner. Und das Programm ist noch lange nicht fertig. Es kommt
mindestens nochmal die selbe Menge dazu. Enttäuschend - finde ich schon
en bisschen schwach, die Dinger haben alle Finessen ADUs, Oszillatoren
und Kram aber en gescheiter Speicher Fehlanzeige.
Wildkatz schrieb:> Enttäuschend - finde ich schon> en bisschen schwach, die Dinger haben alle Finessen ADUs, Oszillatoren> und Kram aber en gescheiter Speicher Fehlanzeige.
Na, na, du wilde Katze, kannst du mit einem Luftgewehr einen Elefanten
erlegen? Immer den passenden Controller für die Anwendung wählen. Wenn
du viel 32 Bit verarbeiten willst, nimm einen ARM. Bei kleinen
Applikationen im Low Power und Low Cost Bereich bist du bei MAPS430 und
kleinen AVR gut bedient.
Wildkatz schrieb:> Enttäuschend - finde ich schon> en bisschen schwach, die Dinger haben alle Finessen ADUs, Oszillatoren> und Kram aber en gescheiter Speicher Fehlanzeige.
Es gibt auch MSP430-Varianten mit ganz erheblich mehr Speicher; der
'F5834 beispielsweise hat 256 kB Flash-ROM und 16 kB RAM.
Davon abgesehen ist Dein Code etwas, äh, umständlich. Wie ich bereits
schrieb, solltest Du Dir mal Gedanken über die verwendeten Datentypen
machen. Welchen Sinn hat es, einen 32-Bit-Datentyp zu verwenden, um
damit nur bis 50 zu zählen?
Desweiteren solltest Du Dir mal ansehen, was eine Schleife ist; was um
alles in der Welt soll der Code in den segmentX-Funktionen?
Bist Du Dir dessen bewusst, daß es auch eine
Hardware-SPI-Schnittstelle gibt?
Die longs habe ich schon geändert. Dann ging es wieder ein paar Zeilen
mehr zu schreiben. Was ne Schleife ist ist mir bestens bekannt, ich
arbeite bloß mit einem Schieberegister das doppelt verzögert (wenn ich
ein Signal anlege steht es erst nacht 3 steigenden Flanken im Register).
Daher wollte ich erstmal den Code so schreiben dass er überhaupt läuft
bevor es an die Feinheiten geht. Werde das mit den Schleifen also noch
verbessern, ob der Speicher langt scheint mir trotzdem fraglich.
Nein, das ist nicht relevant. i ist eine Variable, die landet im RAM.
Und nicht das ist es, was bei Deinem, äh, Programmierstil knapp wird.
Und ob i nun global deklariert wird oder als automatische Variable auf
dem Stack landet, ändert nichts daran, daß sie im RAM bleibt.
Wildkatz schrieb:> Was ne Schleife ist ist mir bestens bekannt, ich> arbeite bloß mit einem Schieberegister das doppelt verzögert (wenn ich> ein Signal anlege steht es erst nacht 3 steigenden Flanken im Register).
Dann poste doch mal einen Schaltplan, damit man das nachvollziehen kann.
Ist es eigentlich notwendig, dass segmenta() nach der Null zwei weitere
Nullen sendet und die anderen segment Unterroutinen nach der Null nur
Einsen senden?
Wenn die letzten beiden Bits bei segmenta() auch Eins sein dürfen
könntest du die ganzen Unterprogramme segmenta() bis segmentg() durch
ein einziges Unterprogramm ersetzen, dem du die Stelle der Null als
Parameter übergibst:
segment(1), segment(2), ...
Der Übergabeparameter+1 bestimmt dann die Anzahl der nach der Null zu
übertragenen Einsen.