Fehler beim Zugriff auf Kerneltreiberdaten vom FIQ-Interrupt-Handler

Bei ARM-FIQ-Interrupts sind einige Register nur für die FIQ-Verwendung reserviert, und dies ist eine praktische Möglichkeit, den Status beispielsweise für die Datenübertragung zwischen FIQ-Aufrufen zu speichern.

Momentan löse ich welche ausGPIO Stifte von der FIQ, und es funktioniert wie erwartet. Beim Einrichten des FIQ-Handlers übergebe ich die Zeiger an die Datenregister, die mit ioremap zugeordnet wurden. Der Arbeitscode sieht folgendermaßen aus:

//Driver initialization:
static char* dout0;
static char* din0;
...
static int driver_probe(struct platform_device *pdev) 
{
struct pt_regs regs;
...
dout0 = ioremap(HW_PINCTRL_DOUT0, 0xffff);
din0  = ioremap(HW_PINCTRL_DIN0, 0xffff);
...
regs.ARM_r8 = (long) dout0;
regs.ARM_r9 = (long) din0;
set_fiq_regs(&regs);
...

//In the FIQ handler:
LDR r12, [r8]
ORR r12, r12, #0x20 /* set pin 5 high in dout0 register */
STR r12, [r8]

Der obige Code verhält sich wie erwartetpin 5 wird hoch gesetzt, nachdem der FIQ-Handler ausgeführt wurde.

Für eine kompliziertere Operation möchte ich eine Struktur vorbereiten, die Datenzeiger und andere verarbeitungsbezogene Daten enthält, einschließlich weiterer Zuordnungen zu verschiedenen Registern - und diese an den FIQ-Handler übergeben. Aber da läuft schon etwas schief, wenn der obige Code auf diesen migriert wird.

Ich habe den obigen Code so geändert, dass er so aussieht

//In Driver:
struct fiq_processing {
    char* din0;
    char* dout0;
};

static fiq_processing * pdata; //Pointer to our processing data structure

...
static int driver_probe(struct platform_device *pdev) 
{
struct pt_regs regs;
pdata = kmalloc(sizeof(*pdata), GFP_KERNEL); //Allocate memory for struct
printk("Size of the data struct %d \n", sizeof(*pdata)); //I get "8" as the size
...
pdata->din0  = ioremap(HW_PINCTRL_DIN0, 0xffff);
pdata->dout0 = ioremap(HW_PINCTRL_DOUT0, 0xffff);
...
regs.ARM_r8 = (long) pdata;
set_fiq_regs(&regs);
...

//In the FIQ handler:
#define OFFSET_DIN0 0x0 
#define OFFSET_DOUT0 0x4 //We know size is 8, so offset for dout is half from that
...
LDR r12, [r8, #OFFSET_DOUT0]
ORR r12, r12, #0x20 /* set pin 5 high in dout0 register */
STR r12, [r8, #OFFSET_DOUT0] /* This will do nothing ? */

Nachdem ich den Speicher für die Struktur zugewiesen und die Registerzeiger zugeordnet habe, übergebe ich die Adresse für die pdata-Struktur an den FIQ-Handler. Im FIQ-Handler habe ich Offsets fürdin0 unddout0, was ich gedacht habe0x0 und0x4 jeweils (von der Strukturgröße von 8 abgezogen).

Aber aus irgendeinem Grund kann mein FIQ den Ausgangspin nicht mehr hoch setzen - ich kann nicht herausfinden, was ich hier falsch mache. Berechne ich den Offset dort falsch? ODER ist der AnrufSTR r12, [r8, #OFFSET_DOUT0] falsch ? Die tatsächliche FIQ ist etwas länger (sie liest den Eingabezustand und die Eingabe daraus schafft einige Bedingungen), aber selbst das Setzen eines Basisbits scheint jetzt fehlzuschlagen.

Antworten auf die Frage(1)

Ihre Antwort auf die Frage