Ich arbeite in einer µC-Umgebung, aber ich denke für diese Thematik ist
dieser Thread besser geeignet.
Ich habe folgende Klasse, welche ich nach Bedarf auch beliebig verändern
kann:
1
classFontInfo
2
{
3
// This structure describes a single character's display information
4
public:
5
classCharacterInfo
6
{
7
public:
8
uint8_t*widthpixel;// width, in bits (or pixels), of the character
9
uint8_t*unused;// emWin creates here an unused value
10
uint8_t*datawidth;// width, in bytes of data bitmap
11
uint8_t*data;// offset of the character's bitmap, in bytes, into the FONT's data array
12
};
13
// Describes a single font
14
uint8_t*fontName;// Font name string
15
uint8_t*charHeight;// height in pixels
16
uint8_t*startChar;// the first character in the font (e.g. in charInfo and data)
17
uint8_t*endChar;// the last character in the font
18
uint8_t*spaceWidth;// width, in pixels, of space character
19
CharacterInfocharInfo[256];// pointer to array of char information
20
}
Die Daten um diese Klasse zu initialisieren liegen auf dem SDRAM und ich
möchte möglichst nur einen Pointer auf dem SRAM haben, der auf diese
Daten zeigt.
Ich mache also zb Folgendes:
1
FontInfo*blubb(uint8_t*data)
2
{
3
FontInfoft;
4
ft.fontName=&data[0]
5
...
6
usw.
7
...
8
return&ft;
9
}
10
11
intmain()
12
{
13
FontInfo*asdf=blubb(blablubbdata);
14
}
Erstmal eine Frage, bevor ich anfange weiter zu fragen:
Wenn ft aus dem scope geht, ist der Zeiger asdf nichts mehr wert, oder?
EDIT: Jetzt hab ich doch das tatsächlich was vergessen:
Vielen Dank schonmal und
Viele Grüße
Reggie
Reginald L. schrieb:> Wenn ft aus dem scope geht, ist der Zeiger asdf nichts mehr wert, oder?
Richtig, d.h. der Rückgabewert von blubb ist nutzlos.
Reginald L. schrieb:> FontInfo* blubb(uint8_t* data)> {> FontInfo ft;> ft.fontName = &data[0]> ...
Warum so kompliziert? Warum tust du nicht direkt eine FontInfo-Klasse in
den S(D??)RAM, warum ist deine Font ein uint8_t Array?
Dr. Sommer schrieb:> Warum so kompliziert? Warum tust du nicht direkt eine FontInfo-Klasse in> den S(D??)RAM
Ich kann nur statische Variablen im SDRAM zur Compilelaufzeit erstellen.
Und ich weiß erst während der Programmlaufzeit wieviele Fonts geladen
werden müssen.
Dr. Sommer schrieb:> warum ist deine Font ein uint8_t Array?
Weils eine AntiAliasing-Schriftart ist. Um die Speichereffizienz der
Schriftarten gehts hier auch nicht.
Dr. Sommer schrieb:> Richtig, d.h. der Rückgabewert von blubb ist nutzlos.
OK, danke. Demnach müsste der Rückgabewert also ein "Non-Pointer" sein.
Wie schaut es da mit dem Speicherverbrauch aus? Jeder Pointer
verbraucht, in meinem Fall, 4x8bit, also wäre es schonmal Quatsch
beispielsweise die charHeight und startChar als Pointer zu definieren?
Im Endeffekt zielt meine Frage darauf ab, ob es möglich ist, einen
FontInfo-Pointer auf dem SRAM zu erstellen, der auf eine Speicherstelle
auf dem SDRAM zeigt, in dem die Daten liegen. Dh die Werte von FontInfo
werden also nicht wirklich initialisiert.
Also im Prinzip so was:
Reginald L. schrieb:> Im Endeffekt zielt meine Frage darauf ab, ob es möglich ist, einen> FontInfo-Pointer auf dem SRAM zu erstellen, der auf eine Speicherstelle> auf dem SDRAM zeigt, in dem die Daten liegen.
Sofern SRAM und SDRAM im gleichen Adressraum liegen (also keine
Klimmzüge zum Ansprechen des einen oder anderen nötig sind), geht das
selbstverständlich.
Übrigens hat das Thema mit Pointerarithmetik nichts zu tun, darunter
versteht man gemeinhin was anderes.
Reginald L. schrieb:> Jeder Pointer verbraucht, in meinem Fall, 4x8bit
Gib in C/C++ keine Größen in Bit an; Bit sind nicht einzeln adressierbar
(außerhalb von Bitfeldern). Das kleinste adressierbare Objekt ist das
Byte.
Rufus Τ. F. schrieb:> Übrigens hat das Thema mit Pointerarithmetik nichts zu tun, darunter> versteht man gemeinhin was anderes.
Ich habe mal wieder ein paar Sachen von deinen Posts gelernt, das lässt
sich nicht abstreiten.
Aber zur Lösung hast du, sofern ich mich recht erinnere, nicht
beigetragen ;)
Vielleicht kannst du den Titel ja noch nachträglich ändern. Wäre blöd,
wenn so ein Mist hier im Forum stehen bleibt.
Rufus Τ. F. schrieb:> Sofern SRAM und SDRAM im gleichen Adressraum liegen (also keine> Klimmzüge zum Ansprechen des einen oder anderen nötig sind), geht das> selbstverständlich.
Wie wird der Adressraum hier definiert? Also der Compiler weiß
eigentlich nicht ob das jetzt der SDRAM oder der SRAM ist. Ich kann ganz
normal eine 32-bit Adresse angeben.
Und, wenn das selbstverständlich geht, verrätst du mir auch wie?
Rufus Τ. F. schrieb:> Gib in C/C++ keine Größen in Bit an; Bit sind nicht einzeln adressierbar> (außerhalb von Bitfeldern). Das kleinste adressierbare Objekt ist das> Byte.
Wie gesagt, gelernt.
Reginald L. schrieb:> Weils eine AntiAliasing-Schriftart ist.
Was ist das denn für ein Argument o.O
Reginald L. schrieb:> Und ich weiß erst während der Programmlaufzeit wieviele Fonts geladen> werden müssen.
Was heißt hier "Laden"? Wo kommen die Fonts überhaupt ursprünglich her?
Wie wird dein uint8_t Array angelegt & befüllt?
Dr. Sommer schrieb:> Was ist das denn für ein Argument o.O
In den Arrays sind die Farbinformationen in 4bits kodiert.
Dr. Sommer schrieb:> Was heißt hier "Laden"?
Da habe ich mich wirklich blöd ausgedrückt. Die Fonts liegen im
SPI-Flash und werden in den SDRAM kopiert. Der SPI-Flash hat dann seine
Aufgabe erfüllt.
Dr. Sommer schrieb:> Wo kommen die Fonts überhaupt ursprünglich her?
emWin.
EDIT: Um genau zu sein emWin FontCvt
Dr. Sommer schrieb:> Wie wird dein uint8_t Array angelegt & befüllt?
Bisher hatte ich eine ganz andere Methode, bin aber gerade am Code
überarbeiten. Da möchte ich nun eine gemütliche Methode haben um ganz
easy neue Objekte in das Projekt einzufügen. Einzige Problematik die ich
hier habe ist die Font-Klasse. Das liegt wahrscheinlich daran, dass ich
den Wald vor lauter Bäumen nicht sehe. Mit Bitmaps ist es beispielsweise
ganz einfach gelaufen, weil ich hier nur ein paar Variablen und die
Farbinformation in einem Array habe.
Kurz und bündig: Also noch gar nicht. Ich kann die Daten im SDRAM
natürlich so anordnen wie ich will. Ich versteh nur nicht, wie ich sie
anordnen könnte, damit ein FontInfo* ausreicht, also ohne
Initialisierung.
Hier ist so eine Font zu finden:
https://www.mikrocontroller.net/attachment/302236/font_aa_mssans12.cpp
Reginald L. schrieb:> Aber zur Lösung hast du, sofern ich mich recht erinnere, nicht> beigetragen ;)
Als Pointerarithmetik betrachtet man das Rechnen mit Pointern. Du hast
z.B. einen großen Puffer, in dem Text ist. Ein Pointer zeigt auf ein
darin gefundendes Wort, ein anderer Pointer auf ein anderes darin
gefundenes Wort. Mit der Subtraktion beider Pointer voneinander lässt
sich die Anzahl der Zeichen zwischen dem Anfang des einen und dem Anfang
des anderen Wortes bestimmen.
Das ist auch bei Pointern, die auf andere Dinge als Zeichen zeigen,
möglich.
Der Puffer kann auch lauter double-Werte enthalten, und die Pointer
seien vom Typ double*. Mit einer Subtraktion bestimmt man hier die
Anzahl double-Werte zwischen den beiden Pointern.
Es ist ebenso legitim, zu einem Pointer einen Ganzzahlen-Wert zu
addieren. Damit zeigt der Pointer (in einem Array o.ä.) auf das
entsprechend vielste nachfolgende Element.
Bei einem Array aus doubles und einem Pointer (vom Typ double*) führt
die Addition vom Wert 2 zum Pointer dazu, daß der Pointer auf den
übernächsten Wert im Array zeigt.
Das funktioniert mit beliebigen Datentypen, also auch mit
selbstdefinierten structs.
So etwas nennt man Pointerarithmetik.
> Wie wird der Adressraum hier definiert?
Das legt der verwendete nicht erwähnte Prozessor fest.
> Also der Compiler weiß> eigentlich nicht ob das jetzt der SDRAM oder der SRAM ist. Ich kann ganz> normal eine 32-bit Adresse angeben.
Und die gleiche Adresse (der numerische Wert) kann nicht sowohl RAM als
auch SDRAM ansprechen? D.h. Du kannst durch Betrachten des numerischen
Werts alleine erkennen, ob SRAM oder SDRAM gemeint sind?
Dann ist das ein gemeinsamer Adressraum,
> Und, wenn das selbstverständlich geht, verrätst du mir auch wie?
Na, einfach machen. Wo liegt da jetzt Dein Problem?
Rufus Τ. F. schrieb:> Als Pointerarithmetik betrachtet man das Rechnen mit Pointern.
Ja, ich habs mir schon angeschaut. Mal abgesehen davon, dass ich hier
Pointerarithmetik benutze (was natürlich nichts mit dem Thread-Thema zu
tun hat):
Wollte halt als Maschinenbauer auch mal hier mit IT-Fachbegriffen
rumschmeissen. Das war wohl ein Griff ins Klo, da hab ich mich vertan :)
Ernsthaft: Schande über mich! Gibt nichts schlimmeres als der falsche
Gebrauch von Fachbegriffen.
Rufus Τ. F. schrieb:> Und die gleiche Adresse (der numerische Wert) kann nicht sowohl RAM als> auch SDRAM ansprechen? D.h. Du kannst durch Betrachten des numerischen> Werts alleine erkennen, ob SRAM oder SDRAM gemeint sind?
Jawohl.
Rufus Τ. F. schrieb:> Das legt der verwendete nicht erwähnte Prozessor fest> ...> Dann ist das ein gemeinsamer Adressraum,
Ah, verstehe. Wie und wo er das festlegt zwar nicht, aber falscher
Thread. Und zur Lösung meines Problems jetzt nicht sinnvoll :>
Rufus Τ. F. schrieb:> Na, einfach machen. Wo liegt da jetzt Dein Problem?
Hast du den Threadtitel gelesen? Ach, wäre es möglich mir nach meinem
Namen, wie bei dir, eine zusätzliche Info einzublenden? So wie bei dir
"Moderator". Nur sollte da bei mir Maschinenbaustudent stehen. Dann
hätte sich die Antwort auf deine Frage ergeben :>
Nee, im ernst, ich glaub der Groschen ist gefallen, siehe meinen
vorherigen Beitrag.
Das blöde ist nur, dass ich die Größe der Arrays in den Klassen
bestimmen muss, wenn ich das richtig verstehe.
Bäh, wäre ja fast schon besser einen eigenen Converter zu kreieren, der
mir die von emWin ausgegebenen Font-Bitmaps in für mich passende Arrays
konvertiert.
Reginald L. schrieb:> Wie und wo er das festlegt zwar nicht,
Das ist eine Hardwareeigenschaft des Prozessors. Der anscheinend nach
wie vor ungenannt bleiben muss.
Es gibt Prozessorarchitekturen, die RAM und ROM voneinander trennen, die
hier beliebten AVRs von Atmel gehören dazu. Da wird von
"Harvard-Architektur" gesprochen. Der Gegensatz (der das nicht trennt)
wird"von-Neumann-Architektur" genannt.
Und es hätte ja sein können, daß Dein Prozessor das SDRAM per Software
(Bitbanging über I/O-Ports) anspricht, ist ja nicht so, daß so etwas
hier noch niemand gemacht hätte. Dann wären auch da die Adressräume
sehr deutlich getrennt.
Rufus Τ. F. schrieb:> a wird von "Harvard-Architektur" gesprochen. Der Gegensatz (der das> nicht trennt) wird"von-Neumann-Architektur" genannt.
Aaah, das hab ich schon mal iwo gelesen.
Reginald L. schrieb:> Das blöde ist nur, dass ich die Größe der Arrays in den Klassen> bestimmen muss, wenn ich das richtig verstehe.
Worauf genau bezieht sich das jetzt?
Eric B. schrieb:> Der Unterschied liegt da drinnen, dass beim Harvard die Addressräume für> Programm und Daten getrennt sind.
Und das unterscheidet sich von meiner Formulierung "RAM und ROM trennen"
jetzt wie?
Mein Problem ist das Array "data" der einzelnen characters. Wie hier zu
sehen ist
https://www.mikrocontroller.net/attachment/302236/font_aa_mssans12.cpp,
unterscheiden sich die Größen der characters. Ich weiß aber erst zur
Programmlaufzeit wie groß die einzelnen characters sind und ich möchte
den Heap nicht nutzen.
Hättest du da noch einen Denkanstoß?
https://www.mikrocontroller.net/attachment/302236/font_aa_mssans12.cpp
Nun, da hilft Dir möglicherweise tatsächlich die Pointeraritmethik.
Wenn Du Dir
Resource::FontInfo::CharacterInfo msSansSerif_12ptDescriptors[95]
ansiehst, da wird jedes einzelne Zeichen aufgeführt. Gehe das Array
durch, bestimme die Adresse des Zeichens, und ziehe davon die Adresse
des vorangehenden Zeichens ab, also z.B. von der Adresse von
acGUI_Fontff_0021 die von acGUI_Fontff_0020.
Die Differenz sollte die Größe von acGUI_Fontff_0020 sein.
Das ist insgesamt eine eher ziemlich ungünstige Vorgehensweise. Ist
diese Struktur so festgemeißelt?
Sonst würde ich CharacterInfo noch um ein Element namens "size" oder
"bytecount" erweitern, und statt
Rufus Τ. F. schrieb:> Nun, da hilft Dir möglicherweise tatsächlich die Pointeraritmethik.
Supi, dann braucht man den Threadtitel nicht mehr ändern :>
Rufus Τ. F. schrieb:> Resource::FontInfo::CharacterInfo msSansSerif_12ptDescriptors[95]>> ansiehst, da wird jedes einzelne Zeichen aufgeführt. Gehe das Array> durch, bestimme die Adresse des Zeichens, und ziehe davon die Adresse> des vorangehenden Zeichens ab, also z.B. von der Adresse von> acGUI_Fontff_0021 die von acGUI_Fontff_0020.>> Die Differenz sollte die Größe von acGUI_Fontff_0020 sein.
Das mache ich eigentlich schon so die ganze Zeit, auch mit meinem alten
Code. Mein Problem ist weniger das "wie bekomme ich die spezifischen
Stellen zu den characters wieder", sondern das "wie sollte ich die
Klassenmember deklarieren und wie weise ich die spezifischen Stellen im
SDRAM diesen Membern korrekt zu". Mit meiner oben geposteten Methode
gehts ja nicht, da ich "data" mit der Größe 256 deklariere und die
einzelnen characters mal 20, mal 40, mal 60 usw. groß sind. Ich müsste
so für diese Schriftart also die Größe von "data" auf die Größe des
größten characters setzen und die Daten dementsprechend im SDRAM
anordnen. Es sind allerdings noch andere Schriftarten vorhanden. Da kann
die Größe eines Character-Arrays dann auf zb. 1300 wachsen. Das erzeugt
dann einen doch zu großen overhead.
Also, wie kann ich sagen: "Weise ft->Name die Adresse 0xD000000 zu,
ft->charHeigth 0xD03000000, ft->charinfo[3]->data 0xD03000001". Am
liebsten wäre es mir, falls das überhaupt möglich ist, einen Pointer ft
definieren und komplett initialisieren (bis hier her kein Problem),
deren Member auf die von mir gewünschten Adressen zeigen. Das ganze am
besten ohne Arrays, die Größen kenne ich ja beim kopieren der Daten vom
SPI-Flash zum SDRAM.
Rufus Τ. F. schrieb:> Das ist insgesamt eine eher ziemlich ungünstige Vorgehensweise. Ist> diese Struktur so festgemeißelt?
Genau da liegt der Hund begraben. emWin erzeugt mir diese ganzen Arrays
genau so. Daran kann ich nicht drehen. Deshalb habe ich vorher erwähnt,
dass ich mir vielleicht einen Converter für Windows schreiben sollte,
der mir die Arrays günstiger legt, weitere Gedanken hierzu habe ich mir
allerdings nicht gemacht.
Ich habe versucht mich möglichst verständlich auszudrücken :>
Vielleicht noch etwas, ab 0xD0000000 liegt ein string im SDRAM:
1
classFontInfo
2
{
3
uint8_t*Name;
4
}
5
6
voidblubb()
7
{
8
FontInfoft;
9
ft.Name=(uint8_t*)0xD0000000;
10
}
ft.Name liefert mir dann natürlich die Adresse an der "0xD0000000"im
µC-Flash liegt. Das versteh ich nicht, da Name ja als Zeiger deklariert
wurde. Bei ft.Name = *(uint8_t*)0xD0000000 bekomme ich einen
Compiler-Error.
Vielleicht macht das die ganze Sache auch etwas klarer.
EDIT:
Deklariere ich in der FontInfo-Klasse Name als non-Pointer, also
"uint8_t Name", funktioniert das ganze. Aber hier habe ich ja das
Problem, dass ich klare Angaben zur Array-Größe von "data" und
"charInfo" machen muss (siehe weiter oben im Thread).
Rufus Τ. F. schrieb:> Eric B. schrieb:>> Der Unterschied liegt da drinnen, dass beim Harvard die Addressräume für>> Programm und Daten getrennt sind.>> Und das unterscheidet sich von meiner Formulierung "RAM und ROM trennen"> jetzt wie?
Wie meinst du? Du wirst doch wissen, was der Unterschied zwischen "RAM"
und "Datenspeicher" ist. Das sind doch Bezeichnungen auf ganz
unterschiedlicher Ebene. RAM ist doch nicht automatisch Datenspeicher
und ROM nicht automatisch Programmspeicher. Gerade dem AVR merkt man
diesen Unterschied an. Bei ihm ist es als Trennung zwischen RAM und ROM
ausgefürt. Da man aber auch den ROM als Datenspeicher nutzen kann, hat
man keine saubere Trennung zwischen Programm- und Datenspeicher. Das ist
ja auch gerade das, was bei der Programmierung des AVR in C immer zu
Schwierigkeiten führt. Meist heißt es dann, das läge an der
Harvard-Architektur und daren, dass C eigentlich nicht gut damit
harmoniere.
Tatsächlich resultiert das Problem aber gerade daraus, dass der AVR eben
keine reine Harvard-Architektur ist, weil man auch auf Daten im ROM
zugreifen kann. Mit einer echten Harvard-Architektur hätte C überhaupt
keine Probleme. Die ist sogar extra berücksichtigt.
Das erzeugt mir einen overhead (für die Klasse selber und deren Member
nehme ich mal an?) von knapp 600Byte. Ich verstehe nur nicht, warum ich
ft in blubb() nicht als Pointer deklarieren bzw. definieren kann.
Reginald L. schrieb:> Das erzeugt mir einen overhead (für die Klasse selber und deren Member> nehme ich mal an?) von knapp 600Byte. Ich verstehe nur nicht, warum ich> ft in blubb() nicht als Pointer deklarieren bzw. definieren kann.
Warum sollte das nicht gehen?
So liegt das Ganze auf dem Stack:
Ich gehe jetzt mal davon aus, dass Deine geheime Plattform das Anlegen
von Objekten im Freispeicher ("auf dem Heap") unterstützt. Auf dem PC
jedenfalls kompiliert dies tadellos.
Mark B. schrieb:> Ich gehe jetzt mal davon aus, dass Deine geheime Plattform das Anlegen> von Objekten im Freispeicher ("auf dem Heap") unterstützt.
Ja natürlich, allerdings war das nur ein Beispielcode. Es ist ein STM32,
Heap soll nicht benutzt werden. Im Stack wird ft lustigerweise nacher
auch nicht liegen :>
Ich habe offensichtlich eine Denkblockade gehabt: Ich muss ja irgendwo
Speicher für ft oder *ft festlegen und zwar für die Member. Es wäre wohl
durchaus möglich, nur mit FontInfo* ft, ohne zusätzliche
Initialisierungen zu arbeiten, allerdings müssten dann die Größen des
der Fonts und Characters alle gleich sein und diese müsste ich schon in
der FontInfo Klasse festlegen. Da das hier nicht möglich ist, muss ich
Speicherplatz für die Member zuweisen.
Auf jeden Fall habe ich mein Problem jetzt gelöst, zwar anders als
gedacht, aber ich blicks jetzt wohl, warum es anders nicht geht.
Reginald L. schrieb:> Auf jeden Fall habe ich mein Problem jetzt gelöst, zwar anders als> gedacht, aber ich blicks jetzt wohl, warum es anders nicht geht.
Ich blicke nicht warum du dir das Leben schwer machst.
"Der Heap ist verboten und der Stack auch". Der Heap löst dein Problem
des "ft" der am Anfang nicht aufrufbar war.
Prinzipiell kannst du doch mit einem packed struct arbeiten.
Beispiel (Ich hab die C-Syntax nicht mehr so im Blut):
1
structblah{
2
uint32_ta;
3
uint32_tb;
4
}
Wenn du jetzt zB hast: struct blah* ptr = 0xD70000; und rufst ptr->b
auf, so wird von 0xD70004 gelesen. Damit sparst du dir irgendwelches
unübersichtliches Gefrickel und alles liegt tatsächlich im ROM.
Der Vorteil hier ist auch, dass du nichts lädst sondern direkt darauf
zugreifst. Der Overhead sind hier also uintptr_t Byte (4 Byte) an RAM.
Dein nächstes Problem mit der Größe und einem fixen Array ist wirklich
ungeschickt. Da gibt es zum einen malloc/Heap (Der DAFÜR da ist und auch
den Toten Speicher (256 - Größe Array) effizient weiterbenutzt) oder man
greift in die Trickkiste:
Erweitern wir das struct. Nehmen wir an im Speicher liegt noch die Größe
des Arrays (Die aber eigentlich nicht nötig ist), dann kann man
folgendes tun:
1
structblah{
2
uint32_ta;
3
uint32_tb;
4
uint32_tsize;
5
uint8_tbyteArray;
6
}
Jetzt musst du nur noch C weiß machen, dass an Adresse byteArray ein
Array läge:
1
structblah*ptr=0xD70000;
2
((uint8_t*)(&ptr->byteArray))[30]=0x0;
Das ist natürlich hacky und vielleicht geht auch ein
(uint8_t[ptr->size]), weiß ich nicht.
Wenn die Daten nun aber nicht jedes Mal aus dem ROM gelesen werden
sollen, dann solltest du wirklich den Heap nutzen.
Einfach uint8_t* byteArray = (uint8_t*)malloc(size);
Student schrieb:> Ich blicke nicht warum du dir das Leben schwer machst.
Sicher, es ginge auch einfacher. Aber ich möchte mir später nicht das
Leben schwer machen, beim Einfügen neuer Objekte (in meinem Fall sind
das ja Fonts, etc). Das funktioniert jetzt indem ich das Font als cpp
ins Projekt einfüge und dann nur noch eine Klassenmethode aufrufe. Das
beinhaltet halt, dass zur Compilelaufzeit die Größen der Objekte
unbekannt sind.
Student schrieb:> "Der Heap ist verboten und der Stack auch". Der Heap löst dein Problem> des "ft" der am Anfang nicht aufrufbar war.
Du hast natürlich absolut recht, ich programmiere auch am PC, natürlich
auch viel mit Heap. Aber hier ist es ein wenig komplizierter, schau mal
hier:
Beitrag "STM32F4 GCC Linker section nur global?"Student schrieb:> Wenn du jetzt zB hast: struct blah* ptr = 0xD70000; und rufst ptr->b> auf, so wird von 0xD70004 gelesen. Damit sparst du dir irgendwelches> unübersichtliches Gefrickel und alles liegt tatsächlich im ROM.
Wie gesagt, die Größen der Arrays werden erst beim auslesen des
SPI-Flashs bekannt.
Student schrieb:> Jetzt musst du nur noch C weiß machen, dass an Adresse byteArray ein> Array läge:> struct blah* ptr = 0xD70000;> ((uint8_t*)(&ptr->byteArray))[30] = 0x0;>> Das ist natürlich hacky und vielleicht geht auch ein> (uint8_t[ptr->size]), weiß ich nicht.
Das die Größe des Arrays 30 beträgt, weiß ich ja nicht. Siehe oben.
Student schrieb:> Wenn die Daten nun aber nicht jedes Mal aus dem ROM gelesen werden> sollen, dann solltest du wirklich den Heap nutzen.
Ja, der Heap wäre hier die Lösung aller Probleme, da hast du recht :)
Aber ich möchte mir, vor allem als Anfänger, keine weiteren Probleme
dadurch einholen. Desweiteren funktioniert malloc() bzw. new in meinem
Fall nicht im SDRAM. Da habe ich noch ein Problem mit den C-Libs und dem
Provide-End im Linker.
Vielen Dank @all für eure Hilfestellungen!
Rufus Τ. F. schrieb:> Eric B. schrieb:>> Der Unterschied liegt da drinnen, dass beim Harvard die Addressräume für>> Programm und Daten getrennt sind.>> Und das unterscheidet sich von meiner Formulierung "RAM und ROM trennen"> jetzt wie?
RAM und ROM bezieht sich auf Speichertyp, nicht auf der Adressraum. Ich
könnte die Addressräume für Programm und Daten jeweils noch in ROM und
RAM unterteilen.
Programm / ROM --> für normale Programmcode
Programm / RAM --> für sich zur laufzet ändernde Code (Hui!)
Daten / ROM --> Constanten
Daten / RAM --> Stack, Heap, BSS etc.
Wenn ich aber nur separate Adressräume für ROM und RAM habe, aber dann
in beide Code und Daten abspeichern kann, habe ich kein
Harvard-architektur mehr.
Eric B. schrieb:> RAM und ROM bezieht sich auf Speichertyp, nicht auf der Adressraum.
Das ist zwar technisch korrekt, nützt aber bei der Betrachtung des
vorliegenden Problems nichts.
Betrachtet man verbreitete µC-Systeme wie die 8-Bit-AVRs, dann sind
"zufälligerweise" RAM und ROM deckungsgleich auf die für Daten und
Programm separierten Adressräume abgebildet.
Rufus Τ. F. schrieb:> Betrachtet man verbreitete µC-Systeme wie die 8-Bit-AVRs, dann sind> "zufälligerweise" RAM und ROM deckungsgleich auf die für Daten und> Programm separierten Adressräume abgebildet.
Bein AVR ist das eben nicht ganz sauber den Fall, wie Rolf Magnus oben
erwähnte:
Beitrag "Re: Anfänger C / C++ Pointerarithmetik"